Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 8 Jan 1997 15:10:55 -0800 (PST)
From:      Steve Reid <steve@edmweb.com>
To:        freebsd-isp@freebsd.org
Subject:   Re: serious security bug in wu-ftpd v2.4 (fwd)
Message-ID:  <Pine.BSF.3.95.970108150849.256B-100000@bitbucket.edmweb.com>

next in thread | raw e-mail | index | archive | help
Since David Greenman's patch was posted here, I figure this should be
posted here as well... 

---------- Forwarded message ----------
Date: Tue, 7 Jan 1997 23:02:51 -0500 (EST)
From: Wietse Venema <wietse@porcupine.org>
Reply-To: best-of-security@suburbia.net
To: best-of-security@suburbia.net
Cc: wu-ftpd-bugs@academ.com, best-of-security@suburbia.net
Subject: BoS:  serious security bug in wu-ftpd v2.4
Resent-Date: Wed, 8 Jan 1997 18:44:21 +1100 (EST)
Resent-From: best-of-security@suburbia.net

Two brief comments on the patches that were suggested sofar.

- The patch proposed by David Greenman (clear the transflag variable
in function dologout()) makes the window of opportunity much smaller,
but does not close it. The hole still exists. It's just smaller.

- The patch posted by Dave Kinchlea ignores signals entirely and
thus may cause loss of information. It is system-call intensive.
This is the same approach that I took for an initial fix in my
logdaemon utilities.

Here is an alternative solution that delays signal delivery without
ignoring signals. It minimizes system calls (one syscall to delay
all signals, and one to undo the delay).  Tested on:  BSD/OS 2.1,
SunOS 5.5, SunOS 4.1.3_U1, FreeBSD 2.1.5, IRIX 5.3, and HP-UX 9.5.

I wonder what UNIX ftpd implementations did NOT have this hole.

	Wietse

 /*
  * delay_signaling(), enable_signaling - delay signal delivery for a while
  * 
  * Author: Wietse Venema
  */
#include <sys/types.h>
#include <sys/signal.h>
#include <syslog.h>

static sigset_t saved_sigmask;
static sigset_t block_sigmask;
static int delaying;
static int init_done;

/* init_mask - compute signal mask only once */

static void init_mask()
{
    int     sig;

    init_done = 1;
    sigemptyset(&block_sigmask);
    for (sig = 1; sig < NSIG; sig++)
	sigaddset(&block_sigmask, sig);
}

/* enable_signaling - deliver delayed signals and disable signal delay */

int     enable_signaling()
{
    if (delaying != 0) {
	delaying = 0;
	if (sigprocmask(SIG_SETMASK, &saved_sigmask, (sigset_t *) 0) < 0) {
	    syslog(LOG_ERR, "sigprocmask: %m");
	    return (-1);
	}
    }
    return (0);
}

/* delay_signaling - save signal mask and block all signals */

int     delay_signaling()
{
    if (init_done == 0)
	init_mask();
    if (delaying == 0) {
	delaying = 1;
	if (sigprocmask(SIG_BLOCK, &block_sigmask, &saved_sigmask) < 0) {
	    syslog(LOG_ERR, "sigprocmask: %m");
	    return (-1);
	}
    }
    return (0);
}

#ifdef TEST

#include <stdio.h>

void    gotsig(sig)
int     sig;
{
    printf("Got signal %d\n", sig);
}

main(argc, argv)
int     argc;
char  **argv;
{
    signal(SIGINT, gotsig);
    signal(SIGQUIT, gotsig);

    delay_signaling();
    sleep(5);
    enable_signaling();
    exit(0);
}

#endif







Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?Pine.BSF.3.95.970108150849.256B-100000>