xref: /csrg-svn/lib/libc/stdlib/setenv.c (revision 42121)
133130Sbostic /*
233130Sbostic  * Copyright (c) 1987 Regents of the University of California.
333130Sbostic  * All rights reserved.
433130Sbostic  *
533130Sbostic  * Redistribution and use in source and binary forms are permitted
634821Sbostic  * provided that the above copyright notice and this paragraph are
734821Sbostic  * duplicated in all such forms and that any documentation,
834821Sbostic  * advertising materials, and other materials related to such
934821Sbostic  * distribution and use acknowledge that the software was developed
1034821Sbostic  * by the University of California, Berkeley.  The name of the
1134821Sbostic  * University may not be used to endorse or promote products derived
1234821Sbostic  * from this software without specific prior written permission.
1334821Sbostic  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
1434821Sbostic  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
1534821Sbostic  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
1633130Sbostic  */
1733130Sbostic 
1833130Sbostic #if defined(LIBC_SCCS) && !defined(lint)
19*42121Sbostic static char sccsid[] = "@(#)setenv.c	5.3 (Berkeley) 05/16/90";
2033130Sbostic #endif /* LIBC_SCCS and not lint */
2133130Sbostic 
22*42121Sbostic #include <stddef.h>
23*42121Sbostic #include <stdlib.h>
2433130Sbostic 
2533130Sbostic /*
2633130Sbostic  * setenv --
2733130Sbostic  *	Set the value of the environmental variable "name" to be
2833130Sbostic  *	"value".  If rewrite is set, replace any current value.
2933130Sbostic  */
3033130Sbostic setenv(name, value, rewrite)
3133130Sbostic 	register char *name, *value;
3233130Sbostic 	int rewrite;
3333130Sbostic {
3433130Sbostic 	extern char **environ;
3533130Sbostic 	static int alloced;			/* if allocated space before */
3633130Sbostic 	register char *C;
3733130Sbostic 	int l_value, offset;
38*42121Sbostic 	char *_findenv();
3933130Sbostic 
4033130Sbostic 	if (*value == '=')			/* no `=' in value */
4133130Sbostic 		++value;
4233130Sbostic 	l_value = strlen(value);
4333130Sbostic 	if ((C = _findenv(name, &offset))) {	/* find if already exists */
4433130Sbostic 		if (!rewrite)
4533130Sbostic 			return(0);
4633130Sbostic 		if (strlen(C) >= l_value) {	/* old larger; copy over */
4733130Sbostic 			while (*C++ = *value++);
4833130Sbostic 			return(0);
4933130Sbostic 		}
5033130Sbostic 	}
5133130Sbostic 	else {					/* create new slot */
5233130Sbostic 		register int	cnt;
5333130Sbostic 		register char	**P;
5433130Sbostic 
5533130Sbostic 		for (P = environ, cnt = 0; *P; ++P, ++cnt);
5633130Sbostic 		if (alloced) {			/* just increase size */
5733130Sbostic 			environ = (char **)realloc((char *)environ,
58*42121Sbostic 			    (size_t)(sizeof(char *) * (cnt + 2)));
5933130Sbostic 			if (!environ)
6033130Sbostic 				return(-1);
6133130Sbostic 		}
6233130Sbostic 		else {				/* get new space */
6333130Sbostic 			alloced = 1;		/* copy old entries into it */
64*42121Sbostic 			P = (char **)malloc((size_t)(sizeof(char *) *
6533130Sbostic 			    (cnt + 2)));
6633130Sbostic 			if (!P)
6733130Sbostic 				return(-1);
6833130Sbostic 			bcopy(environ, P, cnt * sizeof(char *));
6933130Sbostic 			environ = P;
7033130Sbostic 		}
7133130Sbostic 		environ[cnt + 1] = NULL;
7233130Sbostic 		offset = cnt;
7333130Sbostic 	}
7433130Sbostic 	for (C = name; *C && *C != '='; ++C);	/* no `=' in name */
7533130Sbostic 	if (!(environ[offset] =			/* name + `=' + value */
76*42121Sbostic 	    malloc((size_t)((int)(C - name) + l_value + 2))))
7733130Sbostic 		return(-1);
7833130Sbostic 	for (C = environ[offset]; (*C = *name++) && *C != '='; ++C);
7933130Sbostic 	for (*C++ = '='; *C++ = *value++;);
8033130Sbostic 	return(0);
8133130Sbostic }
8233130Sbostic 
8333130Sbostic /*
8433130Sbostic  * unsetenv(name) --
8533130Sbostic  *	Delete environmental variable "name".
8633130Sbostic  */
8733130Sbostic void
8833130Sbostic unsetenv(name)
8933130Sbostic 	char	*name;
9033130Sbostic {
91*42121Sbostic 	extern char **environ;
92*42121Sbostic 	register char **P;
93*42121Sbostic 	int offset;
9433130Sbostic 
9533130Sbostic 	while (_findenv(name, &offset))		/* if set multiple times */
9633130Sbostic 		for (P = &environ[offset];; ++P)
9733130Sbostic 			if (!(*P = *(P + 1)))
9833130Sbostic 				break;
9933130Sbostic }
100