1
0
mirror of https://git.FreeBSD.org/ports.git synced 2024-10-18 19:49:40 +00:00

Unbreak this port (it was using a function called sendfile())

PR:		13414
Submitted by:	Ade Lovett <ade@lovett.com>
This commit is contained in:
Chris Piazza 1999-08-28 16:44:55 +00:00
parent 3f546e7a41
commit e1a019e5ed
Notes: svn2git 2021-03-31 03:12:20 +00:00
svn path=/head/; revision=21061
2 changed files with 154 additions and 234 deletions

View File

@ -1,22 +1,14 @@
*** Makefile Thu Oct 6 17:41:10 1994
--- Makefile Mon Mar 20 12:39:08 1995
***************
*** 4,11 ****
PROG= tftpd
MAN8= tftpd.8
! ETCDIR?=${DESTDIR}/etc
! BINDIR?=${DESTDIR}/usr/libexec
CFLAGS+=-DCONFIGFILE='"${ETCDIR}/tftpd.conf"'
--- 4,12 ----
PROG= tftpd
MAN8= tftpd.8
! ETCDIR=${DESTDIR}/usr/local/etc
! BINDIR=${DESTDIR}/usr/local/libexec
! MANDIR=${DESTDIR}/usr/local/man/man
CFLAGS+=-DCONFIGFILE='"${ETCDIR}/tftpd.conf"'
--- Makefile.orig Thu Oct 6 19:41:10 1994
+++ Makefile Fri Aug 27 13:05:53 1999
@@ -4,8 +4,9 @@
PROG= tftpd
MAN8= tftpd.8
-ETCDIR?=${DESTDIR}/etc
-BINDIR?=${DESTDIR}/usr/libexec
+ETCDIR=${PREFIX}/etc
+BINDIR=${PREFIX}/libexec
+MANDIR=${PREFIX}/man/man
CFLAGS+=-DCONFIGFILE='"${ETCDIR}/tftpd.conf"'

View File

@ -1,212 +1,140 @@
From: Christian.Schroeder@Inf-Technik.TU-Ilmenau.DE (Ch. Schroeder)
Message-Id: <9510171319.AA19401@pegasus>
Subject: yale tftpd
To: pst@cisco.com
Date: Tue, 17 Oct 1995 14:19:32 +0100 (MET)
Hello Paul,
Some days ago I foung the yale tftp daemon (3.0) on the INTERNET and I want to
use it because I have to follow symbolic links from the tftp root directory
to some bootfiles in other directories in the local filesystem.
But I found, that there are some security holes (?) in the code, specially
if the daemon checks the pathname of the requested file. That is dangereous
if no default access rules are specified.
i.e:
config file:
------------
defaultDirectory /tftpboot
rootDirectory /tftpboot
accessList 1 readonly 141.24.20.0 0.0.3.255
defaultAccessList 1
The following reqeusts were successfully and I think, that shouldn't be so.
tftp> get /etc/passwd ./foo
Error code 1: File not found
tftp> get /tftpboot/../../etc/passwd ./foo
Received 474 bytes in 0.3 seconds
tftp> get ../../etc/passwd ./foo
Received 474 bytes in 0.1 seconds
tftp>
I found also some Problems when I dont secify a rootDirectory.
Specially the "../.." parts are only removed, if a root directory
is specified AND the path starts with "/" AND the path doesn't start
with the virtual root directory (e.g. /tftpboot). restrict rules can
be skipped with leading ../.. etc.
Therefore I made some changes in tftpd.c an got better results.
tftp> get /etc/passwd ./foo
Error code 1: File not found
tftp> get /tftpboot/../../etc/passwd ./foo
Error code 2: Access violation
tftp> get ../../etc/passwd ./foo
Error code 1: File not found
tftp>
It would be very nice, if you could check my modifications and
mail me your meaning back. (Excuse please my ugly english)
Christian
Here's the diff File ( diff -bw -c tftpd.c tftpd.c.patched ):
*** tftpd.c Tue Oct 17 14:09:01 1995
--- tftpd.c.patched Tue Oct 17 11:57:30 1995
***************
*** 459,475 ****
/* Rule 2:
*/
! if (tftpRootDirectory != 0 && IS_ROOTED(filename)) {
char _tmp[1024];
int maxPath;
int rootLen;
! rootLen = strlen (tftpRootDirectory);
/* make sure the pathname doesn't already contain
* the virtual root.
*/
- if (strncmp(filename,tftpRootDirectory,rootLen) != 0) {
/* Insure our temporary space is big enough */
maxPath = ((sizeof _tmp) - 1) - rootLen;
--- 459,483 ----
/* Rule 2:
*/
! if ((tftpRootDirectory != 0 && IS_ROOTED(filename)) ||
! (tftpDefaultDirectory != 0 && IS_ROOTED(filename))) {
char _tmp[1024];
+ char* realRootDir;
int maxPath;
int rootLen;
! if (tftpRootDirectory != 0 ) {
! realRootDir = tftpRootDirectory;
! }
! else {
! realRootDir = tftpDefaultDirectory;
! }
+ rootLen = strlen (realRootDir);
+
/* make sure the pathname doesn't already contain
* the virtual root.
*/
/* Insure our temporary space is big enough */
maxPath = ((sizeof _tmp) - 1) - rootLen;
***************
*** 481,486 ****
--- 489,496 ----
return EACCESS;
}
+ if (strncmp(filename,realRootDir,rootLen) != 0) {
+
/* Squeeze out any '.' or '..' components */
strcpy (tmpPath, filename);
if (realPath (tmpPath, _tmp) < 0) {
***************
*** 492,511 ****
/* Create the full pathname, prefixed by the
* virtual root.
*/
! strcpy (tmpPath, tftpRootDirectory);
strcat (tmpPath, _tmp);
filename = tmpPath;
}
}
/* Rule 3:
*/
! if (!IS_ROOTED(filename) && tftpDefaultDirectory == 0) {
! strcpy (tmpPath, tftpRootDirectory);
! strcat (tmpPath, "/");
strcat (tmpPath, filename);
filename = tmpPath;
}
/* Check access lists */
/* Rules 4&5:
--- 502,554 ----
/* Create the full pathname, prefixed by the
* virtual root.
*/
! strcpy (tmpPath, realRootDir);
strcat (tmpPath, _tmp);
filename = tmpPath;
}
+ else {
+ /* Squeeze out any '.' or '..' components */
+ strcpy (tmpPath, filename);
+ if (realPath (tmpPath, _tmp) < 0) {
+ if (tftpDebugLevel > 1)
+ syslog (LOG_DEBUG, "realPath fails");
+ return EACCESS;
}
+ /* Create the full pathname */
+ strcpy (tmpPath,_tmp);
+ filename = tmpPath;
+ if (strncmp(filename,realRootDir,rootLen) != 0) {
+ if (tftpDebugLevel > 1) {
+ syslog(LOG_DEBUG, "file=%s; invalid access denied", filename);
+ return EACCESS;
+ }
+ }
+ }
+ }
/* Rule 3:
*/
! if ((!IS_ROOTED(filename) && tftpRootDirectory != 0) ||
! (!IS_ROOTED(filename) && tftpDefaultDirectory != 0)) {
! char _tmp[1024];
strcat (tmpPath, filename);
+ /* Squeeze out any '.' or '..' components */
+ strcpy (tmpPath, filename);
+ if (realPath (tmpPath, _tmp) < 0) {
+ if (tftpDebugLevel > 1)
+ syslog (LOG_DEBUG, "realPath fails");
+ return EACCESS;
+ }
+ if ( tftpDefaultDirectory == 0 ) {
+ strcpy (tmpPath, tftpRootDirectory);
+ }
+ else {
+ strcpy (tmpPath, tftpDefaultDirectory);
+ }
+ strcat (tmpPath, _tmp);
filename = tmpPath;
}
+
/* Check access lists */
/* Rules 4&5:
--
***
(o o)
---------------------------------------ooO--(_)--Ooo----------------------
| | |
| | Christian Schroeder (Dr.-Ing.) |
| | |
| _/_/_/ _/_/_/ | Technische Universitaet Ilmenau |
| _/ _/ _/ _/ | Fakultaet Elektrotechnik/Informationstechnik |
| _/ _/ | Mikroelektronische Schaltungen u. Systeme |
| _/ _/_/_/ | Postfach 0565 |
| _/ _/ | 98684 ILMENAU |
| _/ _/ _/ _/ | |
| _/_/_/ _/_/_/ | Phone : +49 (0) 3677/69-1165/1168/1169 |
| | FAX : +49 (0) 3677/69-1163 |
| | E-Mail : schroeder@Inf-Technik.TU-Ilmenau.DE |
--------------------------------------------------------------------------
--- tftpd.c.orig Mon Mar 20 14:14:39 1995
+++ tftpd.c Fri Aug 27 12:46:59 1999
@@ -294,7 +294,10 @@
}
int validate_access();
-int sendfile(), recvfile();
+
+struct formats;
+int tftpsendfile(struct formats *);
+int tftprecvfile(struct formats *);
struct formats {
char *f_mode;
@@ -303,8 +306,8 @@
int (*f_recv)();
int f_convert;
} formats[] = {
- { "netascii", validate_access, sendfile, recvfile, 1 },
- { "octet", validate_access, sendfile, recvfile, 0 },
+ { "netascii", validate_access, tftpsendfile, tftprecvfile, 1 },
+ { "octet", validate_access, tftpsendfile, tftprecvfile, 0 },
#ifdef notdef
{ "mail", validate_user, sendmail, recvmail, 1 },
#endif
@@ -459,17 +462,25 @@
/* Rule 2:
*/
- if (tftpRootDirectory != 0 && IS_ROOTED(filename)) {
+ if ((tftpRootDirectory != 0 && IS_ROOTED(filename)) ||
+ (tftpDefaultDirectory != 0 && IS_ROOTED(filename))) {
char _tmp[1024];
+ char* realRootDir;
int maxPath;
int rootLen;
- rootLen = strlen (tftpRootDirectory);
+ if (tftpRootDirectory != 0 ) {
+ realRootDir = tftpRootDirectory;
+ }
+ else {
+ realRootDir = tftpDefaultDirectory;
+ }
+
+ rootLen = strlen (realRootDir);
/* make sure the pathname doesn't already contain
* the virtual root.
*/
- if (strncmp(filename,tftpRootDirectory,rootLen) != 0) {
/* Insure our temporary space is big enough */
maxPath = ((sizeof _tmp) - 1) - rootLen;
@@ -481,6 +492,8 @@
return EACCESS;
}
+ if (strncmp(filename,realRootDir,rootLen) != 0) {
+
/* Squeeze out any '.' or '..' components */
strcpy (tmpPath, filename);
if (realPath (tmpPath, _tmp) < 0) {
@@ -492,21 +505,54 @@
/* Create the full pathname, prefixed by the
* virtual root.
*/
- strcpy (tmpPath, tftpRootDirectory);
+ strcpy (tmpPath, realRootDir);
strcat (tmpPath, _tmp);
filename = tmpPath;
}
+ else {
+ /* Squeeze out any '.' or '..' components */
+ strcpy (tmpPath, filename);
+ if (realPath (tmpPath, _tmp) < 0) {
+ if (tftpDebugLevel > 1)
+ syslog (LOG_DEBUG, "realPath fails");
+ return EACCESS;
+ }
+ /* Create the full pathname */
+ strcpy (tmpPath,_tmp);
+ filename = tmpPath;
+ if (strncmp(filename,realRootDir,rootLen) != 0) {
+ if (tftpDebugLevel > 1) {
+ syslog(LOG_DEBUG, "file=%s; invalid access denied", filename);
+ return EACCESS;
+ }
+ }
+ }
}
/* Rule 3:
*/
- if (!IS_ROOTED(filename) && tftpDefaultDirectory == 0) {
- strcpy (tmpPath, tftpRootDirectory);
- strcat (tmpPath, "/");
+ if ((!IS_ROOTED(filename) && tftpRootDirectory != 0) ||
+ (!IS_ROOTED(filename) && tftpDefaultDirectory != 0)) {
+ char _tmp[1024];
strcat (tmpPath, filename);
+ /* Squeeze out any '.' or '..' components */
+ strcpy (tmpPath, filename);
+ if (realPath (tmpPath, _tmp) < 0) {
+ if (tftpDebugLevel > 1)
+ syslog (LOG_DEBUG, "realPath fails");
+ return EACCESS;
+ }
+ if ( tftpDefaultDirectory == 0 ) {
+ strcpy (tmpPath, tftpRootDirectory);
+ }
+ else {
+ strcpy (tmpPath, tftpDefaultDirectory);
+ }
+ strcat (tmpPath, _tmp);
filename = tmpPath;
}
+
/* Check access lists */
/* Rules 4&5:
*/
@@ -593,7 +639,7 @@
/*
* Send the requested file.
*/
-sendfile(pf)
+tftpsendfile(pf)
struct formats *pf;
{
struct tftphdr *dp, *r_init();
@@ -664,7 +710,7 @@
/*
* Receive a file.
*/
-recvfile(pf)
+tftprecvfile(pf)
struct formats *pf;
{
struct tftphdr *dp, *w_init();