From eugen@hq.delikates-nk.ru  Fri Feb  5 06:36:18 2010
Return-Path: <eugen@hq.delikates-nk.ru>
Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34])
	by hub.freebsd.org (Postfix) with ESMTP id 831B910656C3
	for <FreeBSD-gnats-submit@freebsd.org>; Fri,  5 Feb 2010 06:36:18 +0000 (UTC)
	(envelope-from eugen@hq.delikates-nk.ru)
Received: from hq.delikates-nk.ru (delikates-nk.ru [81.26.177.74])
	by mx1.freebsd.org (Postfix) with ESMTP id D06438FC15
	for <FreeBSD-gnats-submit@freebsd.org>; Fri,  5 Feb 2010 06:36:17 +0000 (UTC)
Received: from hq.delikates-nk.ru (localhost [127.0.0.1])
	by hq.delikates-nk.ru (8.14.3/8.14.3) with ESMTP id o156MJfZ060762
	for <FreeBSD-gnats-submit@freebsd.org>; Fri, 5 Feb 2010 13:22:35 +0700 (KRAT)
	(envelope-from eugen@hq.delikates-nk.ru)
Received: (from root@localhost)
	by hq.delikates-nk.ru (8.14.3/8.14.3/Submit) id o156MJ1b060758;
	Fri, 5 Feb 2010 13:22:19 +0700 (KRAT)
	(envelope-from eugen)
Message-Id: <201002050622.o156MJ1b060758@hq.delikates-nk.ru>
Date: Fri, 5 Feb 2010 13:22:19 +0700 (KRAT)
From: Eugene Grosbein <egrosbein@rdtc.ru>
To: FreeBSD-gnats-submit@freebsd.org
Cc:
Subject: [patch] stock ftpd does not handle "filesize" limit right
X-Send-Pr-Version: 3.113
X-GNATS-Notify:

>Number:         143570
>Category:       bin
>Synopsis:       [patch] stock ftpd(8) does not handle "filesize" limit right
>Confidential:   no
>Severity:       non-critical
>Priority:       medium
>Responsible:    ed
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:  
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Fri Feb 05 06:40:01 UTC 2010
>Closed-Date:    
>Last-Modified:  Sun Mar 31 22:10:00 UTC 2013
>Originator:     Eugene Grosbein
>Release:        FreeBSD 6.4-STABLE i386
>Organization:
RDTC JSC
>Environment:
System: FreeBSD hq.delikates-nk.ru 6.4-STABLE FreeBSD 6.4-STABLE #8: Mon Feb 1 22:28:06 KRAT 2010 root@hq.delikates-nk.ru:/usr/local/obj/usr/local/src/sys/HQ i386

>Description:
	There are some problems with stock ftpd concerning
	"filesize" limit processing.

	1. ftpd calls setusercontext() for authenticated user
	with LOGIN_SETRESOURCES flag too early, before it updates wtmp.
	It wtmp is large enough and user has filesize limit low,
	ftpd's write to wtmp fails.

	2. ftpd may not revert to superuser's context at the end
	of user session and therefore fail to note session end in wtmp
	(see above).

	3. If ftpd hits limit while writing to disk file at user's request
	it is instantly killed with SIGXFSZ. Instead, it should process it
	gracefully, report an error to the user and contiue with the session.

>How-To-Repeat:

	Add new login class with "filesize=NNN" to /etc/login.conf
	(don't forget to run cap_mkdb /etc/login.conf after).
	assign this class to a user and try to login to ftp server
	as this user:

	- if your wtmp file size is greater than NNN, you'll be instantly
	disconnected;
	- otherwise, try to upload a file bigger than NNN in size,
	your connection will break after uploading NNN bytes.

>Fix:

--- libexec/ftpd/ftpd.c.orig	2010-02-05 11:19:23.000000000 +0700
+++ libexec/ftpd/ftpd.c	2010-02-05 13:02:10.000000000 +0700
@@ -428,6 +428,10 @@
 		}
 	}
 
+	/* handge filesize limit gracefully */
+	sa.sa_handler = SIG_IGN;
+	(void)sigaction(SIGXFSZ, &sa, NULL);
+
 	if (daemon_mode) {
 		int *ctl_sock, fd, maxfd = -1, nfds, i;
 		fd_set defreadfds, readfds;
@@ -1183,14 +1187,16 @@
 #endif
 
 	(void) seteuid(0);
-	if (logged_in && dowtmp)
-		ftpd_logwtmp(ttyline, "", NULL);
-	pw = NULL;
 #ifdef	LOGIN_CAP
 	setusercontext(NULL, getpwuid(0), 0,
 		       LOGIN_SETPRIORITY|LOGIN_SETRESOURCES|LOGIN_SETUMASK|
 		       LOGIN_SETMAC);
 #endif
+
+	if (logged_in && dowtmp)
+		ftpd_logwtmp(ttyline, "", NULL);
+	pw = NULL;
+
 #ifdef USE_PAM
 	if (pamh) {
 		if ((e = pam_setcred(pamh, PAM_DELETE_CRED)) != PAM_SUCCESS)
@@ -1463,7 +1469,7 @@
 	}
 	setusercontext(lc, pw, 0,
 		LOGIN_SETLOGIN|LOGIN_SETGROUP|LOGIN_SETPRIORITY|
-		LOGIN_SETRESOURCES|LOGIN_SETUMASK|LOGIN_SETMAC);
+		LOGIN_SETUMASK|LOGIN_SETMAC);
 #else
 	setlogin(pw->pw_name);
 	(void) initgroups(pw->pw_name, pw->pw_gid);
@@ -1485,6 +1491,10 @@
 		    (struct sockaddr *)&his_addr);
 	logged_in = 1;
 
+#ifdef	LOGIN_CAP
+	setusercontext(lc, pw, 0,LOGIN_SETRESOURCES);
+#endif
+
 	if (guest && stats && statfd < 0)
 #ifdef VIRTUAL_HOSTING
 		statfd = open(thishost->statfile, O_WRONLY|O_APPEND);
@@ -2743,6 +2753,13 @@
 dologout(int status)
 {
 
+	(void) seteuid(0);
+#ifdef	LOGIN_CAP
+	setusercontext(NULL, getpwuid(0), 0,
+		       LOGIN_SETPRIORITY|LOGIN_SETRESOURCES|LOGIN_SETUMASK|
+		       LOGIN_SETMAC);
+#endif
+
 	if (logged_in && dowtmp) {
 		(void) seteuid(0);
 		ftpd_logwtmp(ttyline, "", NULL);
>Release-Note:
>Audit-Trail:

From: Eugene Grosbein <egrosbein@rdtc.ru>
To: bug-followup@freebsd.org
Cc:  
Subject: Re: bin/143570: [patch] stock ftpd does not handle "filesize" limit right
Date: Fri, 5 Feb 2010 14:05:41 +0700

 Here is better looking edition of the patch above:
 fixed spelling error in a comment, change for dologout() fuction corrected.
 
 --- libexec/ftpd/ftpd.c.orig	2010-02-05 11:19:23.000000000 +0700
 +++ libexec/ftpd/ftpd.c	2010-02-05 13:57:43.000000000 +0700
 @@ -428,6 +428,10 @@
  		}
  	}
  
 +	/* handle filesize limit gracefully */
 +	sa.sa_handler = SIG_IGN;
 +	(void)sigaction(SIGXFSZ, &sa, NULL);
 +
  	if (daemon_mode) {
  		int *ctl_sock, fd, maxfd = -1, nfds, i;
  		fd_set defreadfds, readfds;
 @@ -1183,14 +1187,16 @@
  #endif
  
  	(void) seteuid(0);
 -	if (logged_in && dowtmp)
 -		ftpd_logwtmp(ttyline, "", NULL);
 -	pw = NULL;
  #ifdef	LOGIN_CAP
  	setusercontext(NULL, getpwuid(0), 0,
  		       LOGIN_SETPRIORITY|LOGIN_SETRESOURCES|LOGIN_SETUMASK|
  		       LOGIN_SETMAC);
  #endif
 +
 +	if (logged_in && dowtmp)
 +		ftpd_logwtmp(ttyline, "", NULL);
 +	pw = NULL;
 +
  #ifdef USE_PAM
  	if (pamh) {
  		if ((e = pam_setcred(pamh, PAM_DELETE_CRED)) != PAM_SUCCESS)
 @@ -1463,7 +1469,7 @@
  	}
  	setusercontext(lc, pw, 0,
  		LOGIN_SETLOGIN|LOGIN_SETGROUP|LOGIN_SETPRIORITY|
 -		LOGIN_SETRESOURCES|LOGIN_SETUMASK|LOGIN_SETMAC);
 +		LOGIN_SETUMASK|LOGIN_SETMAC);
  #else
  	setlogin(pw->pw_name);
  	(void) initgroups(pw->pw_name, pw->pw_gid);
 @@ -1485,6 +1491,10 @@
  		    (struct sockaddr *)&his_addr);
  	logged_in = 1;
  
 +#ifdef	LOGIN_CAP
 +	setusercontext(lc, pw, 0, LOGIN_SETRESOURCES);
 +#endif
 +
  	if (guest && stats && statfd < 0)
  #ifdef VIRTUAL_HOSTING
  		statfd = open(thishost->statfile, O_WRONLY|O_APPEND);
 @@ -2745,6 +2755,11 @@
  
  	if (logged_in && dowtmp) {
  		(void) seteuid(0);
 +#ifdef	LOGIN_CAP
 +		setusercontext(NULL, getpwuid(0), 0,
 +		       LOGIN_SETPRIORITY|LOGIN_SETRESOURCES|LOGIN_SETUMASK|
 +		       LOGIN_SETMAC);
 +#endif
  		ftpd_logwtmp(ttyline, "", NULL);
  	}
  	/* beware of flushing buffers after a SIGPIPE */
Responsible-Changed-From-To: freebsd-bugs->ed 
Responsible-Changed-By: ed 
Responsible-Changed-When: Mon Aug 16 16:23:40 UTC 2010 
Responsible-Changed-Why:  
Mine! Mine! 

http://www.freebsd.org/cgi/query-pr.cgi?pr=143570 

From: Eugene Grosbein <egrosbein@rdtc.ru>
To: bug-followup@FreeBSD.ORG
Cc: ed@FreeBSD.ORG
Subject: Re: bin/143570: [patch] stock ftpd(8) does not handle "filesize"
 limit right
Date: Mon, 01 Aug 2011 00:10:42 +0700

 Hi!
 
 Do you plan to deal with this PR?
 If no, please change "Responsible" so it may be taken by someone else.
 
 Eugene Grosbein
 

From: Eugene Grosbein <egrosbein@rdtc.ru>
To: ed@freebsd.org
Cc: bug-followup@freebsd.org
Subject: Re: bin/143570: [patch] stock ftpd(8) does not handle "filesize"
 limit right
Date: Sat, 09 Jun 2012 00:40:22 +0700

 Hi!
 
 Just notifying you of this nearly 2 years old PR you had once taken.
 Please commit the patch or give responsibility away.
 
 Eugene Grosbein

From: Eugene Grosbein <eugen@eg.sd.rdtc.ru>
To: bug-followup@freebsd.org
Cc: ed@freebsd.org
Subject: Re: bin/143570: [patch] stock ftpd(8) does not handle "filesize" limit right
Date: Mon, 1 Apr 2013 03:26:26 +0700

 Hi!
 
 Here is same patch modified for 8.4-PRERELEASE.
 Please note you took this PR over 3 years ago.
 
 Please commit or assign it back to port@ so someone else could take it.
 
 --- libexec/ftpd/ftpd.c.orig	2013-04-01 03:05:36.000000000 +0700
 +++ libexec/ftpd/ftpd.c	2013-04-01 03:14:05.000000000 +0700
 @@ -424,6 +424,10 @@
  		}
  	}
  
 +	/* handle filesize limit gracefully */
 +	sa.sa_handler = SIG_IGN;
 +	(void)sigaction(SIGXFSZ, &sa, NULL);
 +
  	if (daemon_mode) {
  		int *ctl_sock, fd, maxfd = -1, nfds, i;
  		fd_set defreadfds, readfds;
 @@ -1187,14 +1191,14 @@
  #endif
  
  	(void) seteuid(0);
 -	if (logged_in && dowtmp)
 -		ftpd_logwtmp(wtmpid, NULL, NULL);
 -	pw = NULL;
  #ifdef	LOGIN_CAP
  	setusercontext(NULL, getpwuid(0), 0, LOGIN_SETALL & ~(LOGIN_SETLOGIN |
  		       LOGIN_SETUSER | LOGIN_SETGROUP | LOGIN_SETPATH |
  		       LOGIN_SETENV));
  #endif
 +	if (logged_in && dowtmp)
 +		ftpd_logwtmp(wtmpid, NULL, NULL);
 +	pw = NULL;
  #ifdef USE_PAM
  	if (pamh) {
  		if ((e = pam_setcred(pamh, PAM_DELETE_CRED)) != PAM_SUCCESS)
 @@ -1466,7 +1470,7 @@
  		}
  	}
  	setusercontext(lc, pw, 0, LOGIN_SETALL &
 -		       ~(LOGIN_SETUSER | LOGIN_SETPATH | LOGIN_SETENV));
 +		       ~(LOGIN_SETRESOURCES | LOGIN_SETUSER | LOGIN_SETPATH | LOGIN_SETENV));
  #else
  	setlogin(pw->pw_name);
  	(void) initgroups(pw->pw_name, pw->pw_gid);
 @@ -1508,6 +1512,10 @@
  		    (struct sockaddr *)&his_addr);
  	logged_in = 1;
  
 +#ifdef	LOGIN_CAP
 +	setusercontext(lc, pw, 0, LOGIN_SETRESOURCES);
 +#endif
 +
  	if (guest && stats && statfd < 0)
  #ifdef VIRTUAL_HOSTING
  		statfd = open(thishost->statfile, O_WRONLY|O_APPEND);
 @@ -2758,6 +2766,11 @@
  
  	if (logged_in && dowtmp) {
  		(void) seteuid(0);
 +#ifdef		LOGIN_CAP
 + 	        setusercontext(NULL, getpwuid(0), 0, LOGIN_SETALL & ~(LOGIN_SETLOGIN |
 +		       LOGIN_SETUSER | LOGIN_SETGROUP | LOGIN_SETPATH |
 +		       LOGIN_SETENV));
 +#endif
  		ftpd_logwtmp(wtmpid, NULL, NULL);
  	}
  	/* beware of flushing buffers after a SIGPIPE */

From: Eugene Grosbein <egrosbein@rdtc.ru>
To: bug-followup@freebsd.org
Cc: ed@freebsd.org
Subject: Re: bin/143570: [patch] stock ftpd(8) does not handle "filesize"
 limit right
Date: Mon, 01 Apr 2013 05:00:31 +0700

 01.04.2013 03:26, Eugene Grosbein :
 > Hi!
 > 
 > Here is same patch modified for 8.4-PRERELEASE.
 
 In fact, this patch is for 9.1-STABLE, not 8.4-PRERELEASE.
 
>Unformatted:
