NetBSD Problem Report #49575

From www@NetBSD.org  Thu Jan 15 15:46:44 2015
Return-Path: <www@NetBSD.org>
Received: from mail.netbsd.org (mail.netbsd.org [149.20.53.66])
	(using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits))
	(Client CN "mail.netbsd.org", Issuer "Postmaster NetBSD.org" (verified OK))
	by mollari.NetBSD.org (Postfix) with ESMTPS id 3C546A65C8
	for <gnats-bugs@gnats.NetBSD.org>; Thu, 15 Jan 2015 15:46:44 +0000 (UTC)
Message-Id: <20150115154643.44FDBA65C9@mollari.NetBSD.org>
Date: Thu, 15 Jan 2015 15:46:43 +0000 (UTC)
From: lenzi.sergio@gmail.com
Reply-To: lenzi.sergio@gmail.com
To: gnats-bugs@NetBSD.org
Subject: the system does not parse /etc/login.conf  setenv=EXINIT=set\\ ai\\ showmode\\ number
X-Send-Pr-Version: www-1.0

>Number:         49575
>Category:       lib
>Synopsis:       the system does not parse /etc/login.conf  setenv=EXINIT=set\\ ai\\ showmode\\ number
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    lib-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Thu Jan 15 15:50:00 +0000 2015
>Last-Modified:  Fri Jan 16 00:40:00 +0000 2015
>Originator:     sergio lenzi
>Release:        7.99.4, 6.1.X
>Organization:
http://www.k1.com.br
>Environment:
NetBSD netbsd.lenzicasa 7.99.4 NetBSD 7.99.4 (LZT) #8: Tue Jan 13 01:33:50 BRST 2015  lzt@netbsd.lenzicasa:/usr/obj/sys/arch/i386/compile/LZT i386
>Description:
in the file /etc/login.conf
there is an option to set up environment during login

The logic on libutil and sshd  does not tread white spaces as described in man(5) login.conf
>How-To-Repeat:

put a line in the :default: section of /etc/login.conf

       :setenv[EXINIT=set\\ ai\\ showmode\\ number:\

logout, login again and try to use vi editor...

you will see that the environemnt (env) is full of garbage...
>Fix:

2 patches....

this form does not accept patch files...

to whom do I send the patches????

>Audit-Trail:
From: David Holland <dholland-bugs@netbsd.org>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: lib/49575: the system does not parse /etc/login.conf
 setenv=EXINIT=set\\ ai\\ showmode\\ number
Date: Thu, 15 Jan 2015 23:21:23 +0000

 On Thu, Jan 15, 2015 at 03:50:00PM +0000, lenzi.sergio@gmail.com wrote:
  > 2 patches....
  > 
  > this form does not accept patch files...
  > 
  > to whom do I send the patches????

 Email them as a comment on the PR, by mailing to gnats-bugs (at
 netbsd) and making sure the Subject: line begines with "Re:
 lib/49575".

 Just include them in the message. Don't MIME-attach them; gnats can't
 deal.

 One of these days we'll get ourselves a better bug database.

 -- 
 David A. Holland
 dholland@netbsd.org

From: sergio de Almeida Lenzi <lenzi.sergio@gmail.com>
To: NETBSD BUGS <gnats-bugs@NetBSD.org>
Cc: 
Subject: Re: lib/49575: the system does not parse /etc/login.conf
 setenv=EXINIT=set\\ ai\\ showmode\\ number FIX
Date: Thu, 15 Jan 2015 22:37:23 -0200

 These are diff against /usr/src
 to apply:
 cd /usr/src
 patch < this_file
 than rebuild the system install & reboot
 this patch create a file=login.conf.sample in the /usr/src
 look the line :setenv=EXINIT ......
 it now parses correctly the line as described in man login.conf
 ===================================================================



 diff -up lib/libutil/login_cap.c.orig lib/libutil/login_cap.c
 --- lib/libutil/login_cap.c.orig	2015-01-15 09:43:20.000000000 -0200
 +++ lib/libutil/login_cap.c	2015-01-15 11:15:18.000000000 -0200
 @@ -493,51 +493,54 @@ envset(void *envp __unused, const char *
  int
  setuserenv(login_cap_t *lc, envfunc_t senv, void *envp)
  {
 -	const char *stop = ", \t";
 -	size_t i, count;
 -	char *ptr;
 -	char **res;
 +	const char *value=NULL;
 +	char *buf, *q;
  	char *str = login_getcapstr(lc, "setenv", NULL, NULL);

 -	if (str == NULL || *str == '\0')
 +	if ((!str) || (!(*str)))
  		return 0;
 -	
 -	/*
 -	 * count the sub-strings, this may over-count since we don't
 -	 * account for escaped delimiters.
 -	 */
 -	for (i = 1, ptr = str; *ptr; i++) {
 -		ptr += strcspn(ptr, stop);
 -		if (*ptr)
 -			ptr++;
 -	}
 -
 -	/* allocate ptr array and string */
 -	count = i;
 -	res = malloc(count * sizeof(*res) + strlen(str) + 1);

 -	if (!res)
 +	if (!(buf = calloc(strlen(str) + 1,1)))
  		return -1;
 -	
 -	ptr = (char *)(void *)&res[count];
 -	(void)strcpy(ptr, str);
 -
 -	/* split string */
 -	for (i = 0; (res[i] = stresep(&ptr, stop, '\\')) != NULL; )
 -		if (*res[i])
 -			i++;
 -	
 -	count = i;
 -
 -	for (i = 0; i < count; i++) {
 -		if ((ptr = strchr(res[i], '=')) != NULL)
 -			*ptr++ = '\0';
 -		else 
 -			ptr = NULL;
 -		(void)(*senv)(envp, res[i], ptr ? ptr : "", 1);
 -	}
 -	
 -	free(res);
 +	q=buf;
 +	do {
 +		size_t n;
 +
 +		n = strcspn(str, "=\\, \t");
 +		memcpy(q, str, n);
 +		q += n;
 +		str += n;
 +
 +		switch (*str) {
 +		case '=':
 +			if (!value) {
 +				*q++= '\0';
 +				value = q;
 +			} else {
 +				*q++ = *str;
 +			}
 +			break;
 +		case '\\':
 +			str++;
 +			if (*str) {
 +				*q++ = *str;    
 +				break;
 +			}
 +		case ',':
 +		case ' ':
 +		case '\t':
 +		case '\0':
 +			if (buf[0]) {
 +				*q = '\0';
 +				(void)(*senv)(envp, buf, value ? value : "", 1);
 +			}
 +			value = NULL;
 +			q = buf;
 +			*q = '\0';
 +			break;
 +                }
 +	} while (*str++);
 +	free(buf);
  	return 0;
  }

 @@ -708,7 +711,11 @@ setusercontext(login_cap_t *lc, struct p
  		}

  	if (flags & LOGIN_SETENV)
 -		setuserenv(lc, envset, NULL);
 +		if (setuserenv(lc, envset, NULL) < 0) {
 +			syslog(LOG_ERR, "setuserenv(): %m");
 +			login_close(flc);
 +			return (-1);
 +		}

  	if (flags & LOGIN_SETPATH)
  		setuserpath(lc, pwd ? pwd->pw_dir : "", envset, NULL);
 diff -up crypto/external/bsd/openssh/dist/session.c.orig crypto/external/bsd/openssh/dist/session.c
 --- crypto/external/bsd/openssh/dist/session.c.orig	2015-01-15 10:38:51.000000000 -0200
 +++ crypto/external/bsd/openssh/dist/session.c	2015-01-15 11:04:23.000000000 -0200
 @@ -996,53 +996,54 @@ child_set_env(char ***envp, u_int *envsi
  static void
  lc_setuserenv(char ***env, u_int *envsize, login_cap_t *lcp)
  {
 -	const char *stop = ", \t";
 -	int i, count;
 -	char *ptr;
 -	char **res;
 +	const char *value=NULL;
 +	char *buf, *q;
  	char *str = login_getcapstr(lcp, "setenv", NULL, NULL);

 -	if (str == NULL || *str == '\0')
 +	if ((!str) || (!(*str)))
  		return;
 -	
 -	/* count the sub-strings */
 -	for (i = 1, ptr = str; *ptr; i++) {
 -		ptr += strcspn(ptr, stop);
 -		if (*ptr)
 -			ptr++;
 -	}
 -
 -	/* allocate ptr array and string */
 -	count = i;
 -	res = malloc(count * sizeof(char *) + strlen(str) + 1);

 -	if (!res)
 +	if (!(buf = calloc(strlen(str) + 1,1)))
  		return;
 -	
 -	ptr = (char *)res + count * sizeof(char *);
 -	strcpy(ptr, str);
 -
 -	/* split string */
 -	for (i = 0; *ptr && i < count; i++) {
 -		res[i] = ptr;
 -		ptr += strcspn(ptr, stop);
 -		if (*ptr)
 -			*ptr++ = '\0';
 -	}
 -	
 -	res[i] = NULL;
 -
 -	for (i = 0; i < count && res[i]; i++) {
 -		if (*res[i] != '\0') {
 -			if ((ptr = strchr(res[i], '=')) != NULL)
 -				*ptr++ = '\0';
 -			else 
 -				ptr = __UNCONST("");
 -			child_set_env(env, envsize, res[i], ptr);
 -		}
 -	}
 -	
 -	free(res);
 +	q=buf;
 +	do {
 +		size_t n;
 +
 +		n = strcspn(str, "=\\, \t");
 +		memcpy(q, str, n);
 +		q += n;
 +		str += n;
 +
 +		switch (*str) {
 +		case '=':
 +			if (!value) {
 +				*q++= '\0';
 +				value = q;
 +			} else {
 +				*q++ = *str;
 +			}
 +			break;
 +		case '\\':
 +			str++;
 +			if (*str) {
 +				*q++ = *str;    
 +				break;
 +			}
 +		case ',':
 +		case ' ':
 +		case '\t':
 +		case '\0':
 +			if (buf[0]) {
 +				*q = '\0';
 +				child_set_env(env, envsize, buf, value);
 +			}
 +			value = NULL;
 +			q = buf;
 +			*q = '\0';
 +			break;
 +                }
 +	} while (*str++);
 +	free(buf);
  	return;
  }
  #endif
 --- /dev/null	2015-01-15 21:10:52.000000000 -0200
 +++ login.conf.sample	2015-01-15 14:51:48.000000000 -0200
 @@ -0,0 +1,48 @@
 +# $NetBSD: login.conf,v 1.5 2013/04/30 21:03:43 mbalmer Exp $
 +
 +# Based on:
 +# OpenBSD: login.conf,v 1.22 2005/08/12 18:48:20 millert Exp 
 +
 +#
 +# Sample login.conf file.  See login.conf(5) for details.
 +#
 +
 +#
 +# The default values
 +# Any value changed in the daemon class should be reset in default
 +# class.
 +#
 +default:\
 +	:path=/usr/bin /bin /usr/sbin /sbin /usr/X11R7/bin /usr/X11R6/bin /usr/pkg/bin /usr/pkg/sbin /usr/local/bin:\
 +	:umask=022:\
 +	:datasize-max=infinity:\
 +	:datasize-cur=infinity:\
 +	:openfiles=16384:\
 +	:maxproc=2048:\
 +	:maxthread=8192:\
 +	:stacksize-cur=infinity:\
 +	:setenv=EXINIT=set\\ ai\\ showmode\\ number:\
 +	:copyright=/dev/null:
 +
 +#
 +# Settings used by /etc/rc and root
 +# This must be set properly for daemons started as root by inetd as well.
 +# Be sure reset these values back to system defaults in the default class!
 +#
 +#daemon:\
 +#	:ignorenologin:\
 +#	:datasize=infinity:\
 +#	:maxproc=infinity:\
 +#	:openfiles-cur=128:\
 +#	:stacksize-cur=8M:
 +#
 +#
 +# Staff have fewer restrictions and can login even when nologins are set.
 +#
 +#staff:\
 +#	:datasize-cur=512M:\
 +#	:datasize-max=infinity:\
 +#	:maxproc-max=256:\
 +#	:maxproc-cur=128:\
 +#	:ignorenologin:\
 +#	:requirehome@:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2014 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.