Module Name:    src
Committed By:   sjg
Date:           Thu Nov 19 00:30:25 UTC 2009

Modified Files:
        src/usr.bin/make: make.1 nonints.h parse.c var.c
        src/usr.bin/make/unit-tests: Makefile test.exp
Added Files:
        src/usr.bin/make/unit-tests: unexport unexport-env

Log Message:
PR: make.unexport
Reviewed by:


To generate a diff of this commit:
cvs rdiff -u -r1.164 -r1.165 src/usr.bin/make/make.1
cvs rdiff -u -r1.56 -r1.57 src/usr.bin/make/nonints.h
cvs rdiff -u -r1.159 -r1.160 src/usr.bin/make/parse.c
cvs rdiff -u -r1.154 -r1.155 src/usr.bin/make/var.c
cvs rdiff -u -r1.24 -r1.25 src/usr.bin/make/unit-tests/Makefile
cvs rdiff -u -r1.29 -r1.30 src/usr.bin/make/unit-tests/test.exp
cvs rdiff -u -r0 -r1.1 src/usr.bin/make/unit-tests/unexport \
    src/usr.bin/make/unit-tests/unexport-env

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/usr.bin/make/make.1
diff -u src/usr.bin/make/make.1:1.164 src/usr.bin/make/make.1:1.165
--- src/usr.bin/make/make.1:1.164	Thu Oct 15 02:27:44 2009
+++ src/usr.bin/make/make.1	Thu Nov 19 00:30:24 2009
@@ -1,4 +1,4 @@
-.\"	$NetBSD: make.1,v 1.164 2009/10/15 02:27:44 joerg Exp $
+.\"	$NetBSD: make.1,v 1.165 2009/11/19 00:30:24 sjg Exp $
 .\"
 .\" Copyright (c) 1990, 1993
 .\"	The Regents of the University of California.  All rights reserved.
@@ -29,7 +29,7 @@
 .\"
 .\"	from: @(#)make.1	8.4 (Berkeley) 3/19/94
 .\"
-.Dd October 1, 2009
+.Dd November 15, 2009
 .Dt MAKE 1
 .Os
 .Sh NAME
@@ -1274,17 +1274,53 @@
 character of a line.
 The possible conditionals are as follows:
 .Bl -tag -width Ds
-.It Ic .export Ar variable
+.It Ic .export Ar variable ...
 Export the specified global variable.
-If no variable is provided, all globals are exported
+If no variable list is provided, all globals are exported
 except for internal variables (those that start with
 .Ql \&. ) .
 This is not affected by the
 .Fl X
 flag, so should be used with caution.
+.Pp
 Appending a variable name to
 .Va .MAKE.EXPORTED
 is equivalent to exporting a variable.
+.It Ic .unexport Ar variable ...
+The opposite of
+.Ql .export .
+The specified global
+.Va variable 
+will be removed from 
+.Va .MAKE.EXPORTED .
+If no variable list is provided, all globals are unexported,
+and
+.Va .MAKE.EXPORTED 
+deleted.
+.It Ic .unexport-env
+Unexport all globals previously exported and
+clear the environment inherited from the parent.
+This operation will cause a memory leak of the original environment, 
+so should be used sparingly.  Testing for 
+.Va .MAKE.LEVEL
+being 0, would make sense.
+Also note that any variables which originated in the parent environment 
+should be explicitly preserved if desired.
+For example:
+.Bd -literal -offset indent
+.Li .if ${.MAKE.LEVEL} == 0
+PATH := ${PATH}
+.Li .unexport-env
+.Li .export PATH
+.Li .endif
+.Pp
+.Ed
+Would result in an environment containing only 
+.Ql Ev PATH ,
+which is the minimal useful environment.
+Actually
+.Ql Ev .MAKE.LEVEL 
+will also be pushed into the new environment.
 .It Ic .undef Ar variable
 Un-define the specified global variable.
 Only global variables may be un-defined.

Index: src/usr.bin/make/nonints.h
diff -u src/usr.bin/make/nonints.h:1.56 src/usr.bin/make/nonints.h:1.57
--- src/usr.bin/make/nonints.h:1.56	Wed Jan 28 21:38:13 2009
+++ src/usr.bin/make/nonints.h	Thu Nov 19 00:30:24 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: nonints.h,v 1.56 2009/01/28 21:38:13 dsl Exp $	*/
+/*	$NetBSD: nonints.h,v 1.57 2009/11/19 00:30:24 sjg Exp $	*/
 
 /*-
  * Copyright (c) 1988, 1989, 1990, 1993
@@ -193,3 +193,4 @@
 void Var_Dump(GNode *);
 void Var_ExportVars(void);
 void Var_Export(char *, int);
+void Var_UnExport(char *);

Index: src/usr.bin/make/parse.c
diff -u src/usr.bin/make/parse.c:1.159 src/usr.bin/make/parse.c:1.160
--- src/usr.bin/make/parse.c:1.159	Fri Nov  6 20:20:56 2009
+++ src/usr.bin/make/parse.c	Thu Nov 19 00:30:25 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: parse.c,v 1.159 2009/11/06 20:20:56 dsl Exp $	*/
+/*	$NetBSD: parse.c,v 1.160 2009/11/19 00:30:25 sjg Exp $	*/
 
 /*
  * Copyright (c) 1988, 1989, 1990, 1993
@@ -69,14 +69,14 @@
  */
 
 #ifndef MAKE_NATIVE
-static char rcsid[] = "$NetBSD: parse.c,v 1.159 2009/11/06 20:20:56 dsl Exp $";
+static char rcsid[] = "$NetBSD: parse.c,v 1.160 2009/11/19 00:30:25 sjg Exp $";
 #else
 #include <sys/cdefs.h>
 #ifndef lint
 #if 0
 static char sccsid[] = "@(#)parse.c	8.3 (Berkeley) 3/19/94";
 #else
-__RCSID("$NetBSD: parse.c,v 1.159 2009/11/06 20:20:56 dsl Exp $");
+__RCSID("$NetBSD: parse.c,v 1.160 2009/11/19 00:30:25 sjg Exp $");
 #endif
 #endif /* not lint */
 #endif
@@ -2510,6 +2510,9 @@
 			continue;
 		    Var_Export(cp, 1);
 		    continue;
+		} else if (strncmp(cp, "unexport", 8) == 0) {
+		    Var_UnExport(cp);
+		    continue;
 		}
 	    }
 

Index: src/usr.bin/make/var.c
diff -u src/usr.bin/make/var.c:1.154 src/usr.bin/make/var.c:1.155
--- src/usr.bin/make/var.c:1.154	Tue Sep  8 17:29:20 2009
+++ src/usr.bin/make/var.c	Thu Nov 19 00:30:25 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: var.c,v 1.154 2009/09/08 17:29:20 sjg Exp $	*/
+/*	$NetBSD: var.c,v 1.155 2009/11/19 00:30:25 sjg Exp $	*/
 
 /*
  * Copyright (c) 1988, 1989, 1990, 1993
@@ -69,14 +69,14 @@
  */
 
 #ifndef MAKE_NATIVE
-static char rcsid[] = "$NetBSD: var.c,v 1.154 2009/09/08 17:29:20 sjg Exp $";
+static char rcsid[] = "$NetBSD: var.c,v 1.155 2009/11/19 00:30:25 sjg Exp $";
 #else
 #include <sys/cdefs.h>
 #ifndef lint
 #if 0
 static char sccsid[] = "@(#)var.c	8.3 (Berkeley) 3/19/94";
 #else
-__RCSID("$NetBSD: var.c,v 1.154 2009/09/08 17:29:20 sjg Exp $");
+__RCSID("$NetBSD: var.c,v 1.155 2009/11/19 00:30:25 sjg Exp $");
 #endif
 #endif /* not lint */
 #endif
@@ -527,6 +527,9 @@
 	if ((v->flags & VAR_EXPORTED)) {
 	    unsetenv(v->name);
 	}
+	if (strcmp(MAKE_EXPORTED, v->name) == 0) {
+	    var_exportedVars = VAR_EXPORTED_NONE;
+	}
 	if (v->name != ln->name)
 		free(v->name);
 	Hash_DeleteEntry(&ctxt->context, ln);
@@ -711,6 +714,107 @@
     free(av);
 }
 
+
+/*
+ * This is called when .unexport[-env] is seen.
+ */
+void
+Var_UnExport(char *str)
+{
+    char tmp[BUFSIZ];
+    char *vlist;
+    char *cp;
+    Boolean unexport_env;
+    int n;
+
+    if (!str || !str[0]) {
+	return; 			/* assert? */
+    }
+
+    vlist = NULL;
+
+    str += 8;
+    unexport_env = (strncmp(str, "-env", 4) == 0);
+    if (unexport_env) {
+	extern char **environ;
+	static char **savenv;
+	char **newenv;
+
+	cp = getenv(MAKE_LEVEL);	/* we should preserve this */
+	if (environ == savenv) {
+	    /* we have been here before! */
+	    newenv = bmake_realloc(environ, 2 * sizeof(char *));
+	} else {
+	    if (savenv) {
+		free(savenv);
+		savenv = NULL;
+	    }
+	    newenv = bmake_malloc(2 * sizeof(char *));
+	}
+	if (!newenv)
+	    return;
+	/* Note: we cannot safely free() the original environ. */
+	environ = savenv = newenv;
+	newenv[0] = NULL;
+	newenv[1] = NULL;
+	setenv(MAKE_LEVEL, cp, 1);
+    } else {
+	for (; *str != '\n' && isspace((unsigned char) *str); str++)
+	    continue;
+	if (str[0] && str[0] != '\n') {
+	    vlist = str;
+	}
+    }
+
+    if (!vlist) {
+	/* Using .MAKE.EXPORTED */
+	n = snprintf(tmp, sizeof(tmp), "${" MAKE_EXPORTED ":O:u}");
+	if (n < (int)sizeof(tmp)) {
+	    vlist = Var_Subst(NULL, tmp, VAR_GLOBAL, 0);
+	}
+    }
+    if (vlist) {
+	Var *v;
+	char **av;
+	char *as;
+	int ac;
+	int i;
+
+	av = brk_string(vlist, &ac, FALSE, &as);
+	for (i = 0; i < ac; i++) {
+	    v = VarFind(av[i], VAR_GLOBAL, 0);
+	    if (!v)
+		continue;
+	    if (!unexport_env &&
+		(v->flags & (VAR_EXPORTED|VAR_REEXPORT)) == VAR_EXPORTED) {
+		unsetenv(v->name);
+	    }
+	    v->flags &= ~(VAR_EXPORTED|VAR_REEXPORT);
+	    /*
+	     * If we are unexporting a list,
+	     * remove each one from .MAKE.EXPORTED.
+	     * If we are removing them all,
+	     * just delete .MAKE.EXPORTED below.
+	     */
+	    if (vlist == str) {
+		n = snprintf(tmp, sizeof(tmp),
+			     "${" MAKE_EXPORTED ":N%s}", v->name);
+		if (n < (int)sizeof(tmp)) {
+		    cp = Var_Subst(NULL, tmp, VAR_GLOBAL, 0);
+		    Var_Set(MAKE_EXPORTED, cp, VAR_GLOBAL, 0);
+		    free(cp);
+		}
+	    }
+	}
+	free(as);
+	free(av);
+	if (vlist != str) {
+	    Var_Delete(MAKE_EXPORTED, VAR_GLOBAL);
+	    free(vlist);
+	}
+    }
+}
+
 /*-
  *-----------------------------------------------------------------------
  * Var_Set --

Index: src/usr.bin/make/unit-tests/Makefile
diff -u src/usr.bin/make/unit-tests/Makefile:1.24 src/usr.bin/make/unit-tests/Makefile:1.25
--- src/usr.bin/make/unit-tests/Makefile:1.24	Wed Oct  7 16:40:30 2009
+++ src/usr.bin/make/unit-tests/Makefile	Thu Nov 19 00:30:25 2009
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile,v 1.24 2009/10/07 16:40:30 sjg Exp $
+# $NetBSD: Makefile,v 1.25 2009/11/19 00:30:25 sjg Exp $
 #
 # Unit tests for make(1)
 # The main targets are:
@@ -34,6 +34,8 @@
 	posix \
 	qequals \
 	ternary \
+	unexport \
+	unexport-env \
 	varcmd
 
 all: ${SUBFILES}

Index: src/usr.bin/make/unit-tests/test.exp
diff -u src/usr.bin/make/unit-tests/test.exp:1.29 src/usr.bin/make/unit-tests/test.exp:1.30
--- src/usr.bin/make/unit-tests/test.exp:1.29	Wed Oct  7 16:40:30 2009
+++ src/usr.bin/make/unit-tests/test.exp	Thu Nov 19 00:30:25 2009
@@ -302,6 +302,10 @@
 The answer is known
 The answer is 42
 The answer is 42
+UT_DOLLAR=This is $UT_FU
+UT_FU=fubar
+UT_TEST=unexport
+UT_TEST=unexport-env
 default FU=<v>fu</v> FOO=<v>foo</v> VAR=<v></v>
 two FU=<v>bar</v> FOO=<v>goo</v> VAR=<v></v>
 three FU=<v>bar</v> FOO=<v>goo</v> VAR=<v></v>

Added files:

Index: src/usr.bin/make/unit-tests/unexport
diff -u /dev/null src/usr.bin/make/unit-tests/unexport:1.1
--- /dev/null	Thu Nov 19 00:30:25 2009
+++ src/usr.bin/make/unit-tests/unexport	Thu Nov 19 00:30:25 2009
@@ -0,0 +1,8 @@
+# $Id: unexport,v 1.1 2009/11/19 00:30:25 sjg Exp $
+
+# pick up a bunch of exported vars
+.include "export"
+
+.unexport UT_ZOO UT_FOO
+
+UT_TEST = unexport
Index: src/usr.bin/make/unit-tests/unexport-env
diff -u /dev/null src/usr.bin/make/unit-tests/unexport-env:1.1
--- /dev/null	Thu Nov 19 00:30:25 2009
+++ src/usr.bin/make/unit-tests/unexport-env	Thu Nov 19 00:30:25 2009
@@ -0,0 +1,14 @@
+# $Id: unexport-env,v 1.1 2009/11/19 00:30:25 sjg Exp $
+
+# pick up a bunch of exported vars
+.include "export"
+
+# an example of setting up a minimal environment.
+PATH = /bin:/usr/bin:/sbin:/usr/sbin
+
+# now clobber the environment to just PATH and UT_TEST
+UT_TEST = unexport-env
+
+# this removes everything
+.unexport-env
+.export PATH UT_TEST

Reply via email to