summaryrefslogtreecommitdiffstats
path: root/src/kmk/tests/scripts/variables
diff options
context:
space:
mode:
Diffstat (limited to 'src/kmk/tests/scripts/variables')
-rw-r--r--src/kmk/tests/scripts/variables/CURDIR20
-rw-r--r--src/kmk/tests/scripts/variables/DEFAULT_GOAL87
-rw-r--r--src/kmk/tests/scripts/variables/GNUMAKEFLAGS42
-rw-r--r--src/kmk/tests/scripts/variables/INCLUDE_DIRS46
-rw-r--r--src/kmk/tests/scripts/variables/LIBPATTERNS38
-rw-r--r--src/kmk/tests/scripts/variables/MAKE24
-rw-r--r--src/kmk/tests/scripts/variables/MAKECMDGOALS52
-rw-r--r--src/kmk/tests/scripts/variables/MAKEFILES53
-rw-r--r--src/kmk/tests/scripts/variables/MAKEFILE_LIST30
-rw-r--r--src/kmk/tests/scripts/variables/MAKEFLAGS45
-rw-r--r--src/kmk/tests/scripts/variables/MAKELEVEL45
-rw-r--r--src/kmk/tests/scripts/variables/MAKE_RESTARTS61
-rw-r--r--src/kmk/tests/scripts/variables/MFILE_LIST30
-rw-r--r--src/kmk/tests/scripts/variables/SHELL103
-rw-r--r--src/kmk/tests/scripts/variables/automatic122
-rw-r--r--src/kmk/tests/scripts/variables/define282
-rw-r--r--src/kmk/tests/scripts/variables/flavors96
-rw-r--r--src/kmk/tests/scripts/variables/must_make81
-rw-r--r--src/kmk/tests/scripts/variables/negative46
-rw-r--r--src/kmk/tests/scripts/variables/private122
-rw-r--r--src/kmk/tests/scripts/variables/special150
-rw-r--r--src/kmk/tests/scripts/variables/undefine73
22 files changed, 1648 insertions, 0 deletions
diff --git a/src/kmk/tests/scripts/variables/CURDIR b/src/kmk/tests/scripts/variables/CURDIR
new file mode 100644
index 0000000..ee7cacb
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/CURDIR
@@ -0,0 +1,20 @@
+# -*-perl-*-
+
+$description = "This tests the CURDIR varaible.";
+
+$details = "Echo CURDIR both with and without -C. Also ensure overrides work.";
+
+open(MAKEFILE,"> $makefile");
+print MAKEFILE "all: ; \@echo \$(CURDIR)\n";
+close(MAKEFILE);
+
+
+# TEST #1
+# -------
+
+&run_make_with_options($makefile,"",&get_logfile);
+$answer = "$pwd\n";
+&compare_output($answer,&get_logfile(1));
+
+
+1;
diff --git a/src/kmk/tests/scripts/variables/DEFAULT_GOAL b/src/kmk/tests/scripts/variables/DEFAULT_GOAL
new file mode 100644
index 0000000..8188ce7
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/DEFAULT_GOAL
@@ -0,0 +1,87 @@
+# -*-perl-*-
+$description = "Test the .DEFAULT_GOAL special variable.";
+
+$details = "";
+
+
+# Test #1: basic logic.
+#
+run_make_test('
+# Basics.
+#
+foo: ; @:
+
+ifneq ($(.DEFAULT_GOAL),foo)
+$(error )
+endif
+
+# Reset to empty.
+#
+.DEFAULT_GOAL :=
+
+bar: ; @:
+
+ifneq ($(.DEFAULT_GOAL),bar)
+$(error )
+endif
+
+# Change to a different goal.
+#
+
+.DEFAULT_GOAL := baz
+
+baz: ; @echo $@
+',
+'',
+'baz');
+
+
+# Test #2: unknown goal.
+#
+run_make_test('
+.DEFAULT_GOAL = foo
+',
+'',
+"#MAKE#: *** No rule to make target 'foo'. Stop.",
+512);
+
+
+# Test #3: more than one goal.
+#
+run_make_test('
+.DEFAULT_GOAL := foo bar
+',
+'',
+'#MAKE#: *** .DEFAULT_GOAL contains more than one target. Stop.',
+512);
+
+
+# Test #4: Savannah bug #12226.
+#
+run_make_test('
+define rule
+foo: ; @echo $$@
+endef
+
+define make-rule
+$(eval $(rule))
+endef
+
+$(call make-rule)
+
+',
+'',
+'foo');
+
+# TEST #5: .DEFAULT_GOAL containing just whitespace (Savannah bug #25697)
+
+run_make_test('
+N =
+.DEFAULT_GOAL = $N $N # Just whitespace
+
+foo: ; @echo "boo"
+',
+ '', "#MAKE#: *** No targets. Stop.\n", 512);
+
+# This tells the test driver that the perl test script executed properly.
+1;
diff --git a/src/kmk/tests/scripts/variables/GNUMAKEFLAGS b/src/kmk/tests/scripts/variables/GNUMAKEFLAGS
new file mode 100644
index 0000000..6e50794
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/GNUMAKEFLAGS
@@ -0,0 +1,42 @@
+# -*-perl-*-
+
+$description = "Test proper behavior of GNUMAKEFLAGS";
+
+# Accept flags from GNUMAKEFLAGS as well as MAKEFLAGS
+# Results always go in MAKEFLAGS
+
+$extraENV{'GNUMAKEFLAGS'} = '-e -r -R';
+
+run_make_test(q!
+all: ; @echo $(MAKEFLAGS)
+!,
+ '', 'erR');
+
+# Long arguments mean everything is prefixed with "-"
+
+$extraENV{'GNUMAKEFLAGS'} = '--no-print-directory -e -r -R --trace';
+
+run_make_test(q!
+all: ; @echo $(MAKEFLAGS)
+!,
+ '', "#MAKEFILE#:2: target 'all' does not exist
+echo erR --trace --no-print-directory
+erR --trace --no-print-directory");
+
+# Verify that re-exec / recursion doesn't duplicate flags from GNUMAKEFLAGS
+
+unlink('x.mk');
+
+$extraENV{GNUMAKEFLAGS} = '-Itst/bad';
+
+run_make_test(q!
+recurse: ; @echo $@; echo MAKEFLAGS = $$MAKEFLAGS; echo GNUMAKEFLAGS = $$GNUMAKEFLAGS; #MAKEPATH# -f #MAKEFILE# all
+all: ; @echo $@; echo MAKEFLAGS = $$MAKEFLAGS; echo GNUMAKEFLAGS = $$GNUMAKEFLAGS
+-include x.mk
+x.mk: ; @echo $@; echo MAKEFLAGS = $$MAKEFLAGS; echo GNUMAKEFLAGS = $$GNUMAKEFLAGS; echo > $@
+!,
+ "", "x.mk\nMAKEFLAGS = -Itst/bad\nGNUMAKEFLAGS =\nrecurse\nMAKEFLAGS = -Itst/bad\nGNUMAKEFLAGS =\n#MAKE#[1]: Entering directory '#PWD#'\nall\nMAKEFLAGS = w -Itst/bad\nGNUMAKEFLAGS =\n#MAKE#[1]: Leaving directory '#PWD#'\n");
+
+unlink('x.mk');
+
+1;
diff --git a/src/kmk/tests/scripts/variables/INCLUDE_DIRS b/src/kmk/tests/scripts/variables/INCLUDE_DIRS
new file mode 100644
index 0000000..c9662e9
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/INCLUDE_DIRS
@@ -0,0 +1,46 @@
+# -*-perl-*-
+$description = "Test the .INCLUDE_DIRS special variable.";
+
+$details = "";
+
+use Cwd;
+
+$dir = cwd;
+$dir =~ s,.*/([^/]+)$,../$1,;
+
+# Test #1: The content of .INCLUDE_DIRS depends on the platform for which
+# make was built. What we know for sure is that it shouldn't be
+# empty.
+#
+run_make_test('
+ifeq ($(.INCLUDE_DIRS),)
+$(warning .INCLUDE_DIRS is empty)
+endif
+
+.PHONY: all
+all:;@:
+',
+'',
+'');
+
+
+# Test #2: Make sure -I paths end up in .INCLUDE_DIRS.
+#
+run_make_test('
+ifeq ($(dir),)
+$(warning dir is empty)
+endif
+
+ifeq ($(filter $(dir),$(.INCLUDE_DIRS)),)
+$(warning .INCLUDE_DIRS does not contain $(dir))
+endif
+
+.PHONY: all
+all:;@:
+',
+"-I$dir dir=$dir",
+'');
+
+
+# This tells the test driver that the perl test script executed properly.
+1;
diff --git a/src/kmk/tests/scripts/variables/LIBPATTERNS b/src/kmk/tests/scripts/variables/LIBPATTERNS
new file mode 100644
index 0000000..9182954
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/LIBPATTERNS
@@ -0,0 +1,38 @@
+# -*-perl-*-
+
+$description = "Test .LIBPATTERNS special variable.";
+
+$details = "";
+
+# TEST 0: basics
+
+touch('mtest_foo.a');
+
+run_make_test('
+.LIBPATTERNS = mtest_%.a
+all: -lfoo ; @echo "build $@ from $<"
+',
+ '', "build all from mtest_foo.a\n");
+
+# TEST 1: Handle elements that are not patterns.
+
+run_make_test('
+.LIBPATTERNS = mtest_foo.a mtest_%.a
+all: -lfoo ; @echo "build $@ from $<"
+',
+ '', "#MAKE#: .LIBPATTERNS element 'mtest_foo.a' is not a pattern
+build all from mtest_foo.a\n");
+
+# TEST 2: target-specific override
+
+# Uncomment this when we add support, see Savannah bug #25703
+# run_make_test('
+# .LIBPATTERNS = mbad_%.a
+# all: .LIBPATTERNS += mtest_%.a
+# all: -lfoo ; @echo "build $@ from $<"
+# ',
+# '', "build all from mtest_foo.a\n");
+
+unlink('mtest_foo.a');
+
+1;
diff --git a/src/kmk/tests/scripts/variables/MAKE b/src/kmk/tests/scripts/variables/MAKE
new file mode 100644
index 0000000..dc62160
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKE
@@ -0,0 +1,24 @@
+# -*-perl-*-
+
+$description = "Test proper behavior of the MAKE variable";
+
+$details = "DETAILS";
+
+run_make_test(q!
+TMP := $(MAKE)
+MAKE := $(subst X=$(X),,$(MAKE))
+all:
+ @echo $(TMP)
+ $(MAKE) -f #MAKEFILE# foo
+
+foo:
+ @echo $(MAKE)
+!,
+ '',
+ "#MAKEPATH#\n#MAKEPATH# -f #MAKEFILE# foo\n"
+ . "#MAKE#[1]: Entering directory '#PWD#'\n"
+ . "#MAKEPATH#\n#MAKE#[1]: Leaving directory '#PWD#'\n");
+
+rmfiles("foo");
+
+1;
diff --git a/src/kmk/tests/scripts/variables/MAKECMDGOALS b/src/kmk/tests/scripts/variables/MAKECMDGOALS
new file mode 100644
index 0000000..879283b
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKECMDGOALS
@@ -0,0 +1,52 @@
+# -*-perl-*-
+
+$description = "Test the MAKECMDGOALS variable.";
+
+$details = "\
+We construct a makefile with various targets, all of which print out
+\$(MAKECMDGOALS), then call it different ways.";
+
+open(MAKEFILE,"> $makefile");
+print MAKEFILE "\
+.DEFAULT all:
+ \@echo \$(MAKECMDGOALS)
+";
+close(MAKEFILE);
+
+# TEST #1
+
+&run_make_with_options($makefile,
+ "",
+ &get_logfile,
+ 0);
+$answer = "\n";
+&compare_output($answer,&get_logfile(1));
+
+# TEST #2
+
+&run_make_with_options($makefile,
+ "all",
+ &get_logfile,
+ 0);
+$answer = "all\n";
+&compare_output($answer,&get_logfile(1));
+
+
+# TEST #3
+
+&run_make_with_options($makefile,
+ "foo bar baz yaz",
+ &get_logfile,
+ 0);
+$answer = "foo bar baz yaz\nfoo bar baz yaz\nfoo bar baz yaz\nfoo bar baz yaz\n";
+&compare_output($answer,&get_logfile(1));
+
+
+# This tells the test driver that the perl test script executed properly.
+1;
+
+
+
+
+
+
diff --git a/src/kmk/tests/scripts/variables/MAKEFILES b/src/kmk/tests/scripts/variables/MAKEFILES
new file mode 100644
index 0000000..b23da8e
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKEFILES
@@ -0,0 +1,53 @@
+# -*-perl-*-
+
+$description = "Test the MAKEFILES variable.";
+
+$makefile2 = &get_tmpfile;
+$makefile3 = &get_tmpfile;
+
+open(MAKEFILE,"> $makefile");
+print MAKEFILE 'all: ; @echo DEFAULT RULE: M2=$(M2) M3=$(M3)', "\n";
+close(MAKEFILE);
+
+
+open(MAKEFILE,"> $makefile2");
+print MAKEFILE <<EOF;
+M2 = m2
+NDEF: ; \@echo RULE FROM MAKEFILE 2
+EOF
+close(MAKEFILE);
+
+
+open(MAKEFILE,"> $makefile3");
+print MAKEFILE <<EOF;
+M3 = m3
+NDEF3: ; \@echo RULE FROM MAKEFILE 3
+EOF
+close(MAKEFILE);
+
+
+&run_make_with_options($makefile, "MAKEFILES='$makefile2 $makefile3'",
+ &get_logfile);
+$answer = "DEFAULT RULE: M2=m2 M3=m3\n";
+&compare_output($answer,&get_logfile(1));
+
+# TEST 2: Verify that included makefiles don't set the default goal.
+# See Savannah bug #13401.
+
+create_file('xx-inc.mk', '
+include_goal: ; @echo $@
+include xx-ind.mk
+');
+
+create_file('xx-ind.mk', '
+indirect_goal: ; @echo $@
+');
+
+run_make_test(q!
+top: ; @echo $@
+!,
+ 'MAKEFILES=xx-inc.mk', "top\n");
+
+unlink(qw(xx-inc.mk xx-ind.mk));
+
+1;
diff --git a/src/kmk/tests/scripts/variables/MAKEFILE_LIST b/src/kmk/tests/scripts/variables/MAKEFILE_LIST
new file mode 100644
index 0000000..076e42d
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKEFILE_LIST
@@ -0,0 +1,30 @@
+# -*-perl-*-
+
+$description = "Test the MAKEFILE_LIST variable.";
+
+$makefile2 = &get_tmpfile;
+
+open(MAKEFILE,"> $makefile");
+print MAKEFILE <<EOF;
+m1 := \$(MAKEFILE_LIST)
+include $makefile2
+m3 := \$(MAKEFILE_LIST)
+
+all:
+\t\@echo \$(m1)
+\t\@echo \$(m2)
+\t\@echo \$(m3)
+EOF
+close(MAKEFILE);
+
+
+open(MAKEFILE,"> $makefile2");
+print MAKEFILE "m2 := \$(MAKEFILE_LIST)\n";
+close(MAKEFILE);
+
+
+&run_make_with_options($makefile, "", &get_logfile);
+$answer = "$makefile\n$makefile $makefile2\n$makefile $makefile2\n";
+&compare_output($answer,&get_logfile(1));
+
+1;
diff --git a/src/kmk/tests/scripts/variables/MAKEFLAGS b/src/kmk/tests/scripts/variables/MAKEFLAGS
new file mode 100644
index 0000000..0fac74a
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKEFLAGS
@@ -0,0 +1,45 @@
+# -*-perl-*-
+
+$description = "Test proper behavior of MAKEFLAGS";
+
+$details = "DETAILS";
+
+# Normal flags aren't prefixed with "-"
+run_make_test(q!
+all: ; @echo $(MAKEFLAGS)
+!,
+ '-e -r -R', 'erR');
+
+# Long arguments mean everything is prefixed with "-"
+run_make_test(q!
+all: ; @echo $(MAKEFLAGS)
+!,
+ '--no-print-directory -e -r -R --trace', "#MAKEFILE#:2: target 'all' does not exist
+echo erR --trace --no-print-directory
+erR --trace --no-print-directory");
+
+
+# Recursive invocations of make should accumulate MAKEFLAGS values.
+# Savannah bug #2216
+run_make_test(q!
+MSG = Fails
+all:
+ @echo '$@: MAKEFLAGS=$(MAKEFLAGS)'
+ @MSG=Works $(MAKE) -e -f #MAKEFILE# jump
+jump:
+ @echo '$@ $(MSG): MAKEFLAGS=$(MAKEFLAGS)'
+ @$(MAKE) -f #MAKEFILE# print
+print:
+ @echo '$@ $(MSG): MAKEFLAGS=$(MAKEFLAGS)'
+.PHONY: all jump print
+!,
+ '--no-print-directory',
+ 'all: MAKEFLAGS= --no-print-directory
+jump Works: MAKEFLAGS=e --no-print-directory
+print Works: MAKEFLAGS=e --no-print-directory');
+
+1;
+
+### Local Variables:
+### eval: (setq whitespace-action (delq 'auto-cleanup whitespace-action))
+### End:
diff --git a/src/kmk/tests/scripts/variables/MAKELEVEL b/src/kmk/tests/scripts/variables/MAKELEVEL
new file mode 100644
index 0000000..0db3a68
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKELEVEL
@@ -0,0 +1,45 @@
+# -*-perl-*-
+
+$description = "The following test creates a makefile to test
+makelevels in Make. It prints \$(MAKELEVEL) and then
+prints the environment variable MAKELEVEL";
+
+open(MAKEFILE,"> $makefile");
+
+# The Contents of the MAKEFILE ...
+
+if (!$is_kmk) {
+ print MAKEFILE <<EOF;
+all:
+\t\@echo MAKELEVEL is \$(MAKELEVEL)
+\techo \$\$MAKELEVEL
+EOF
+} else {
+ print MAKEFILE <<EOF;
+all:
+\t\@echo KMK_LEVEL is \$(KMK_LEVEL)
+\techo \$\$KMK_LEVEL
+EOF
+}
+
+# END of Contents of MAKEFILE
+
+close(MAKEFILE);
+
+# RUN MAKE
+
+&run_make_with_options($makefile,"",&get_logfile);
+
+# SET ANSWER
+
+if (!$is_kmk) {
+ $answer = "MAKELEVEL is 0\necho \$MAKELEVEL\n1\n";
+} else {
+ $answer = "KMK_LEVEL is 0\necho \$KMK_LEVEL\n1\n";
+}
+
+# COMPARE RESULTS
+
+&compare_output($answer,&get_logfile(1));
+
+1;
diff --git a/src/kmk/tests/scripts/variables/MAKE_RESTARTS b/src/kmk/tests/scripts/variables/MAKE_RESTARTS
new file mode 100644
index 0000000..01bf55e
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MAKE_RESTARTS
@@ -0,0 +1,61 @@
+# -*-perl-*-
+
+$description = "Test the MAKE_RESTARTS variable.";
+
+# Test basic capability
+
+run_make_test('
+all: ; @:
+$(info MAKE_RESTARTS=$(MAKE_RESTARTS))
+include foo.x
+foo.x: ; @touch $@
+',
+ '', 'MAKE_RESTARTS=
+MAKE_RESTARTS=1');
+
+rmfiles('foo.x');
+
+# Test multiple restarts
+
+run_make_test('
+all: ; @:
+$(info MAKE_RESTARTS=$(MAKE_RESTARTS))
+include foo.x
+foo.x: ; @echo "include bar.x" > $@
+bar.x: ; @touch $@
+',
+ '', 'MAKE_RESTARTS=
+MAKE_RESTARTS=1
+MAKE_RESTARTS=2');
+
+rmfiles('foo.x', 'bar.x');
+
+# Test multiple restarts and make sure the variable is cleaned up
+
+run_make_test('
+recurse:
+ @echo recurse MAKE_RESTARTS=$$MAKE_RESTARTS
+ @$(MAKE) -f #MAKEFILE# all
+all:
+ @echo all MAKE_RESTARTS=$$MAKE_RESTARTS
+$(info MAKE_RESTARTS=$(MAKE_RESTARTS))
+include foo.x
+foo.x: ; @echo "include bar.x" > $@
+bar.x: ; @touch $@
+',
+ '', "MAKE_RESTARTS=
+MAKE_RESTARTS=1
+MAKE_RESTARTS=2
+recurse MAKE_RESTARTS=
+#MAKE#[1]: Entering directory '#PWD#'
+MAKE_RESTARTS=
+all MAKE_RESTARTS=
+#MAKE#[1]: Leaving directory '#PWD#'");
+
+rmfiles('foo.x', 'bar.x');
+
+1;
+
+### Local Variables:
+### eval: (setq whitespace-action (delq 'auto-cleanup whitespace-action))
+### End:
diff --git a/src/kmk/tests/scripts/variables/MFILE_LIST b/src/kmk/tests/scripts/variables/MFILE_LIST
new file mode 100644
index 0000000..076e42d
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/MFILE_LIST
@@ -0,0 +1,30 @@
+# -*-perl-*-
+
+$description = "Test the MAKEFILE_LIST variable.";
+
+$makefile2 = &get_tmpfile;
+
+open(MAKEFILE,"> $makefile");
+print MAKEFILE <<EOF;
+m1 := \$(MAKEFILE_LIST)
+include $makefile2
+m3 := \$(MAKEFILE_LIST)
+
+all:
+\t\@echo \$(m1)
+\t\@echo \$(m2)
+\t\@echo \$(m3)
+EOF
+close(MAKEFILE);
+
+
+open(MAKEFILE,"> $makefile2");
+print MAKEFILE "m2 := \$(MAKEFILE_LIST)\n";
+close(MAKEFILE);
+
+
+&run_make_with_options($makefile, "", &get_logfile);
+$answer = "$makefile\n$makefile $makefile2\n$makefile $makefile2\n";
+&compare_output($answer,&get_logfile(1));
+
+1;
diff --git a/src/kmk/tests/scripts/variables/SHELL b/src/kmk/tests/scripts/variables/SHELL
new file mode 100644
index 0000000..9d56796
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/SHELL
@@ -0,0 +1,103 @@
+# -*-perl-*-
+
+$description = "Test proper handling of SHELL.";
+
+# Find the default value when SHELL is not set. On UNIX it will be /bin/sh,
+# but on other platforms who knows?
+resetENV();
+delete $ENV{SHELL};
+$mshell = `echo 'all:;\@echo \$(SHELL)' | $make_path -f-`;
+chop $mshell;
+
+# According to POSIX, the value of SHELL in the environment has no impact on
+# the value in the makefile.
+# Note %extraENV takes precedence over the default value for the shell.
+
+$extraENV{SHELL} = '/dev/null';
+run_make_test('all:;@echo "$(SHELL)"', '', $mshell);
+
+# According to POSIX, any value of SHELL set in the makefile should _NOT_ be
+# exported to the subshell! I wanted to set SHELL to be $^X (perl) in the
+# makefile, but make runs $(SHELL) -c 'commandline' and that doesn't work at
+# all when $(SHELL) is perl :-/. So, we just add an extra initial /./ which
+# works well on UNIX and seems to work OK on at least some non-UNIX systems.
+
+$extraENV{SHELL} = $mshell;
+
+run_make_test("SHELL := /./$mshell\n".'
+all:;@echo "$(SHELL) $$SHELL"
+', '', "/./$mshell $mshell");
+
+# As a GNU make extension, if make's SHELL variable is explicitly exported,
+# then we really _DO_ export it.
+
+$extraENV{SHELL} = $mshell;
+
+run_make_test("export SHELL := /./$mshell\n".'
+all:;@echo "$(SHELL) $$SHELL"
+', '', "/./$mshell /./$mshell");
+
+
+# Test out setting of SHELL, both exported and not, as a target-specific
+# variable.
+
+$extraENV{SHELL} = $mshell;
+
+run_make_test("all: SHELL := /./$mshell\n".'
+all:;@echo "$(SHELL) $$SHELL"
+', '', "/./$mshell $mshell");
+
+$extraENV{SHELL} = $mshell;
+
+# bird: This was wrong at some point, see Savannah bug #24655. Was first fixed in kBuild.
+run_make_test("
+SHELL := /././$mshell
+one: two
+two: export SHELL := /./$mshell\n".'
+one two:;@echo "$@: $(SHELL) $$SHELL"
+', '', "two: /./$mshell /./$mshell\none: /././$mshell $mshell\n");
+
+# Test .SHELLFLAGS
+
+# We don't know the output here: on Solaris for example, every line printed
+# by the shell in -x mode has a trailing space (!!)
+my $script = 'true; true';
+my $flags = '-xc';
+my $out = `/bin/sh $flags '$script' 2>&1`;
+
+run_make_test(qq!
+.SHELLFLAGS = $flags
+all: ; \@$script
+!,
+ '', $out);
+
+# Do it again but add spaces to SHELLFLAGS
+
+# Some shells (*shakes fist at Solaris*) cannot handle multiple flags in
+# separate arguments.
+my $t = `/bin/sh -e -c true 2>/dev/null`;
+my $multi_ok = $? == 0;
+
+if ($multi_ok) {
+ $flags = '-x -c';
+ run_make_test(qq!
+.SHELLFLAGS = $flags
+all: ; \@$script
+!,
+ '', $out);
+}
+
+# We can't just use "false" because on different systems it provides a
+# different exit code--once again Solaris: false exits with 255 not 1
+$script = 'true; false; true';
+$flags = '-xec';
+$out = `/bin/sh $flags '$script' 2>&1`;
+my $err = $? >> 8;
+
+run_make_test(qq!
+.SHELLFLAGS = $flags
+all: ; \@$script
+!,
+ '', "$out#MAKE#: *** [#MAKEFILE#:3: all] Error $err\n", 512);
+
+1;
diff --git a/src/kmk/tests/scripts/variables/automatic b/src/kmk/tests/scripts/variables/automatic
new file mode 100644
index 0000000..2304fa0
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/automatic
@@ -0,0 +1,122 @@
+# -*-perl-*-
+
+$description = "Test automatic variable setting.";
+
+$details = "";
+
+use Cwd;
+
+$dir = cwd;
+$dir =~ s,.*/([^/]+)$,../$1,;
+
+open(MAKEFILE, "> $makefile");
+print MAKEFILE "dir = $dir\n";
+print MAKEFILE <<'EOF';
+.SUFFIXES:
+.SUFFIXES: .x .y .z
+$(dir)/foo.x : baz.z $(dir)/bar.y baz.z
+ @echo '$$@ = $@, $$(@D) = $(@D), $$(@F) = $(@F)'
+ @echo '$$* = $*, $$(*D) = $(*D), $$(*F) = $(*F)'
+ @echo '$$< = $<, $$(<D) = $(<D), $$(<F) = $(<F)'
+ @echo '$$^ = $^, $$(^D) = $(^D), $$(^F) = $(^F)'
+ @echo '$$+ = $+, $$(+D) = $(+D), $$(+F) = $(+F)'
+ @echo '$$? = $?, $$(?D) = $(?D), $$(?F) = $(?F)'
+ touch $@
+
+$(dir)/bar.y baz.z : ; touch $@
+EOF
+close(MAKEFILE);
+
+# TEST #0 -- simple test
+# -------
+
+# Touch these into the past
+&utouch(-10, qw(foo.x baz.z));
+
+&run_make_with_options($makefile, "", &get_logfile);
+$answer = "touch $dir/bar.y
+\$\@ = $dir/foo.x, \$(\@D) = $dir, \$(\@F) = foo.x
+\$* = $dir/foo, \$(*D) = $dir, \$(*F) = foo
+\$< = baz.z, \$(<D) = ., \$(<F) = baz.z
+\$^ = baz.z $dir/bar.y, \$(^D) = . $dir, \$(^F) = baz.z bar.y
+\$+ = baz.z $dir/bar.y baz.z, \$(+D) = . $dir ., \$(+F) = baz.z bar.y baz.z
+\$? = $dir/bar.y, \$(?D) = $dir, \$(?F) = bar.y
+touch $dir/foo.x\n";
+&compare_output($answer, &get_logfile(1));
+
+unlink(qw(foo.x bar.y baz.z));
+
+# TEST #1 -- test the SysV emulation of $$@ etc.
+# -------
+
+$makefile2 = &get_tmpfile;
+
+open(MAKEFILE, "> $makefile2");
+print MAKEFILE "dir = $dir\n";
+print MAKEFILE <<'EOF';
+.SECONDEXPANSION:
+.SUFFIXES:
+.DEFAULT: ; @echo '$@'
+
+$(dir)/foo $(dir)/bar: $@.x $$@.x $$$@.x $$$$@.x $$(@D).x $$(@F).x
+
+$(dir)/x.z $(dir)/y.z: $(dir)/%.z : $@.% $$@.% $$$@.% $$$$@.% $$(@D).% $$(@F).%
+
+$(dir)/biz: $$(@).x $${@}.x $${@D}.x $${@F}.x
+EOF
+
+close(MAKEFILE);
+
+&run_make_with_options($makefile2, "-j1 $dir/foo $dir/bar", &get_logfile);
+$answer = ".x\n$dir/foo.x\nx\n\$@.x\n$dir.x\nfoo.x\n$dir/bar.x\nbar.x\n";
+&compare_output($answer, &get_logfile(1));
+
+&run_make_with_options($makefile2, "-j1 $dir/x.z $dir/y.z", &get_logfile);
+$answer = ".x\n$dir/x.z.x\nx\n\$@.x\n$dir.x\nx.z.x\n.y\n$dir/y.z.y\n\y\n\$@.y\n$dir.y\ny.z.y\n";
+&compare_output($answer, &get_logfile(1));
+
+&run_make_with_options($makefile2, "-j1 $dir/biz", &get_logfile);
+$answer = "$dir/biz.x\n$dir.x\nbiz.x\n";
+&compare_output($answer, &get_logfile(1));
+
+# TEST #2 -- test for Savannah bug #12320.
+#
+run_make_test('
+.SUFFIXES: .b .src
+
+mbr.b: mbr.src
+ @echo $*
+
+mbr.src: ; @:',
+ '',
+ 'mbr');
+
+# TEST #3 -- test for Savannah bug #8154
+# Make sure that nonexistent prerequisites are listed in $?, since they are
+# considered reasons for the target to be rebuilt.
+#
+# See also Savannah bugs #16002 and #16051.
+
+touch('foo');
+
+run_make_test('
+foo: bar ; @echo "\$$? = $?"
+bar: ;',
+ '',
+ '$? = bar');
+
+unlink('foo');
+
+# TEST #4: ensure prereq ordering is correct when the commmand target has none
+# See Savannah bug #21198
+
+run_make_test('
+all : A B
+all : ; @echo $@ -- $^ -- $<
+all : C D
+all : E F
+A B C D E F G H : ; @:
+',
+ '', "all -- A B C D E F -- A\n");
+
+1;
diff --git a/src/kmk/tests/scripts/variables/define b/src/kmk/tests/scripts/variables/define
new file mode 100644
index 0000000..7324cbc
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/define
@@ -0,0 +1,282 @@
+# -*-perl-*-
+
+$description = "Test define/endef variable assignments.";
+
+$details = "";
+
+# TEST 0: old-style basic define/endef
+
+run_make_test('
+define multi
+@echo hi
+echo there
+endef
+
+all: ; $(multi)
+',
+ '', "hi\necho there\nthere\n");
+
+# TEST 1: Various new-style define/endef
+
+run_make_test('
+FOO = foo
+
+define multi =
+echo hi
+@echo $(FOO)
+endef # this is the end
+
+define simple :=
+@echo $(FOO)
+endef
+
+define posix ::=
+@echo $(FOO)
+endef
+
+append = @echo a
+
+define append +=
+
+@echo b
+endef
+
+define cond ?= # this is a conditional
+@echo first
+endef
+
+define cond ?=
+@echo second
+endef
+
+FOO = there
+
+all: ; $(multi)
+ $(simple)
+ $(posix)
+ $(append)
+ $(cond)
+',
+ '', "echo hi\nhi\nthere\nfoo\nfoo\na\nb\nfirst\n");
+
+# TEST 1a: Various new-style define/endef, with no spaces
+
+run_make_test('
+FOO = foo
+
+define multi=
+echo hi
+@echo $(FOO)
+endef # this is the end
+
+define simple:=
+@echo $(FOO)
+endef
+
+define posix::=
+@echo $(FOO)
+endef
+
+append = @echo a
+
+define append+=
+
+@echo b
+endef
+
+define cond?= # this is a conditional
+@echo first
+endef
+
+define cond?=
+@echo second
+endef
+
+FOO = there
+
+all: ; $(multi)
+ $(simple)
+ $(posix)
+ $(append)
+ $(cond)
+',
+ '', "echo hi\nhi\nthere\nfoo\nfoo\na\nb\nfirst\n");
+
+# TEST 2: define in true section of conditional (containing conditional)
+
+run_make_test('
+FOO = foo
+NAME = def
+def =
+ifdef BOGUS
+ define $(subst e,e,$(NAME)) =
+ ifeq (1,1)
+ FOO = bar
+ endif
+ endef
+endif
+
+$(eval $(def))
+all: ; @echo $(FOO)
+',
+ 'BOGUS=1', "bar\n");
+
+# TEST 3: define in false section of conditional (containing conditional)
+
+run_make_test(undef, '', "foo\n");
+
+# TEST 4: nested define (supported?)
+
+run_make_test('
+define outer
+ define inner
+ A = B
+ endef
+endef
+
+$(eval $(outer))
+
+outer: ; @echo $(inner)
+',
+ '', "A = B\n");
+
+# TEST 5: NEGATIVE: Missing variable name
+
+run_make_test('
+NAME =
+define $(NAME) =
+ouch
+endef
+all: ; @echo ouch
+',
+ '', "#MAKEFILE#:3: *** empty variable name. Stop.\n", 512);
+
+# TEST 6: NEGATIVE: extra text after define
+
+run_make_test('
+NAME =
+define NAME = $(NAME)
+ouch
+endef
+all: ; @echo ok
+',
+ '', "#MAKEFILE#:3: extraneous text after 'define' directive\nok\n");
+
+# TEST 7: NEGATIVE: extra text after endef
+
+run_make_test('
+NAME =
+define NAME =
+ouch
+endef $(NAME)
+all: ; @echo ok
+',
+ '', "#MAKEFILE#:5: extraneous text after 'endef' directive\nok\n");
+
+# TEST 8: NEGATIVE: missing endef
+
+run_make_test('
+NAME =
+all: ; @echo ok
+define NAME =
+ouch
+endef$(NAME)
+',
+ '', "#MAKEFILE#:4: *** missing 'endef', unterminated 'define'. Stop.\n", 512);
+
+# -------------------------
+# Make sure that prefix characters apply properly to define/endef values.
+#
+# There's a bit of oddness here if you try to use a variable to hold the
+# prefix character for a define. Even though something like this:
+#
+# define foo
+# echo bar
+# endef
+#
+# all: ; $(V)$(foo)
+#
+# (where V=@) can be seen by the user to be obviously different than this:
+#
+# define foo
+# $(V)echo bar
+# endef
+#
+# all: ; $(foo)
+#
+# and the user thinks it should behave the same as when the "@" is literal
+# instead of in a variable, that can't happen because by the time make
+# expands the variables for the command line and sees it begins with a "@" it
+# can't know anymore whether the prefix character came before the variable
+# reference or was included in the first line of the variable reference.
+
+# TEST #5
+# -------
+
+run_make_test('
+define FOO
+$(V1)echo hello
+$(V2)echo world
+endef
+all: ; @$(FOO)
+', '', 'hello
+world');
+
+# TEST #6
+# -------
+
+run_make_test(undef, 'V1=@ V2=@', 'hello
+world');
+
+# TEST #7
+# -------
+
+run_make_test('
+define FOO
+$(V1)echo hello
+$(V2)echo world
+endef
+all: ; $(FOO)
+', 'V1=@', 'hello
+echo world
+world');
+
+# TEST #8
+# -------
+
+run_make_test(undef, 'V2=@', 'echo hello
+hello
+world');
+
+# TEST #9
+# -------
+
+run_make_test(undef, 'V1=@ V2=@', 'hello
+world');
+
+# TEST #10
+# -------
+# Test the basics; a "@" internally to the variable applies to only one line.
+# A "@" before the variable applies to the entire variable.
+
+run_make_test('
+define FOO
+@echo hello
+echo world
+endef
+define BAR
+echo hello
+echo world
+endef
+
+all: foo bar
+foo: ; $(FOO)
+bar: ; @$(BAR)
+', '', 'hello
+echo world
+world
+hello
+world
+');
+
+1;
diff --git a/src/kmk/tests/scripts/variables/flavors b/src/kmk/tests/scripts/variables/flavors
new file mode 100644
index 0000000..ba133ea
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/flavors
@@ -0,0 +1,96 @@
+# -*-perl-*-
+
+$description = "Test various flavors of make variable setting.";
+
+$details = "";
+
+# TEST 0: Recursive
+
+run_make_test('
+ugh = Goodbye
+foo = $(bar)
+bar = ${ugh}
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Hello\n");
+
+# TEST 1: Simple
+
+run_make_test('
+bar = Goodbye
+foo := $(bar)
+bar = ${ugh}
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Goodbye\n");
+
+# TEST 2: Append to recursive
+
+run_make_test('
+foo = Hello
+ugh = Goodbye
+foo += $(bar)
+bar = ${ugh}
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Hello Hello\n");
+
+# TEST 3: Append to simple
+
+run_make_test('
+foo := Hello
+ugh = Goodbye
+bar = ${ugh}
+foo += $(bar)
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Hello Goodbye\n");
+
+# TEST 4: Conditional pre-set
+
+run_make_test('
+foo = Hello
+ugh = Goodbye
+bar = ${ugh}
+foo ?= $(bar)
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Hello\n");
+
+# TEST 5: Conditional unset
+
+run_make_test('
+ugh = Goodbye
+bar = ${ugh}
+foo ?= $(bar)
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Hello\n");
+
+# TEST 6: Simple using POSIX syntax
+run_make_test('
+bar = Goodbye
+foo ::= $(bar)
+bar = ${ugh}
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Goodbye\n");
+
+# TEST 7: POSIX syntax no spaces
+run_make_test('
+bar = Goodbye
+foo::=$(bar)
+bar = ${ugh}
+ugh = Hello
+all: ; @echo $(foo)
+',
+ '', "Goodbye\n");
+
+1;
diff --git a/src/kmk/tests/scripts/variables/must_make b/src/kmk/tests/scripts/variables/must_make
new file mode 100644
index 0000000..83a8275
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/must_make
@@ -0,0 +1,81 @@
+# $Id: must_make 2413 2010-09-11 17:43:04Z bird $ -*-perl-*-
+## @file
+# .MUST_MAKE target variable.
+#
+
+#
+# Copyright (c) 2008-2010 knut st. osmundsen <bird-kBuild-spamx@anduin.net>
+#
+# This file is part of kBuild.
+#
+# kBuild is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# kBuild is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with kBuild. If not, see <http://www.gnu.org/licenses/>
+#
+#
+
+$description = "Tests the .MUST_MAKE target variable";
+
+$details = "The .MUST_MAKE target variable is expanded when make is deciding
+whether a file needs to be made or not. If it returns a non-empty string,
+when stripped, it will force the file to be made. If it returns an empty
+string GNU make decides the normal way. Note that .MUST_MAKE does NOT have
+to be expanded if make already knows the file needs building. Also, note
+that for multi target rules it may be invoked for each file.";
+
+if ($is_kmk) {
+
+ # TEST #0 - check to see that it gets called and is made.
+ # -------------------------------------------------------
+ &touch('foobar.1');
+ run_make_test('
+
+foobar.1: .MUST_MAKE = $(info mustmake:{@=$@,<=$<})FORCE
+foobar.1: ;touch $@
+',
+'',
+'mustmake:{@=foobar.1,<=}
+touch foobar.1'
+);
+ unlink('foobar.1');
+
+ # TEST #1 - check to see that it gets called and isn't made.
+ # ----------------------------------------------------------
+ &touch('foobar.1');
+ run_make_test('
+
+foobar.1: .MUST_MAKE = $(info mustmake:{@=$@,<=$<})
+foobar.1: ;touch $@
+',
+'',
+'mustmake:{@=foobar.1,<=}
+#MAKE#: `foobar.1\' is up to date.'
+);
+ unlink('foobar.1');
+
+ # TEST #2 - check to see that it doesn't get called unnecessary.
+ # --------------------------------------------------------------
+ run_make_test('
+foobar.1: .MUST_MAKE = $(info mustmake:{@=$@,<=$})FORCE
+foobar.1: ;@echo making $@
+',
+'',
+'making foobar.1');
+
+}
+
+
+
+# Indicate that we're done.
+1;
+
+
diff --git a/src/kmk/tests/scripts/variables/negative b/src/kmk/tests/scripts/variables/negative
new file mode 100644
index 0000000..16a72b8
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/negative
@@ -0,0 +1,46 @@
+# -*-perl-*-
+
+$description = "Run some negative tests (things that should fail).";
+
+# TEST #0
+# Check that non-terminated variable references are detected (and
+# reported using the best filename/lineno info
+run_make_test('
+foo = bar
+x = $(foo
+y = $x
+
+all: ; @echo $y
+',
+ '', '#MAKEFILE#:3: *** unterminated variable reference. Stop.',
+ 512);
+
+# TEST #1
+# Bogus variable value passed on the command line.
+run_make_test(undef,
+ 'x=\$\(other',
+ '#MAKEFILE#:4: *** unterminated variable reference. Stop.',
+ 512);
+
+# TEST #2
+# Again, but this time while reading the makefile.
+run_make_test('
+foo = bar
+x = $(foo
+y = $x
+
+z := $y
+
+all: ; @echo $y
+',
+ '', '#MAKEFILE#:3: *** unterminated variable reference. Stop.',
+ 512);
+
+# TEST #3
+# Bogus variable value passed on the command line.
+run_make_test(undef,
+ 'x=\$\(other',
+ '#MAKEFILE#:4: *** unterminated variable reference. Stop.',
+ 512);
+
+1;
diff --git a/src/kmk/tests/scripts/variables/private b/src/kmk/tests/scripts/variables/private
new file mode 100644
index 0000000..8967ffb
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/private
@@ -0,0 +1,122 @@
+# -*-perl-*-
+
+$description = "Test 'private' variables.";
+
+$details = "";
+
+# 1: Simple verification that private variables are not inherited
+&run_make_test('
+a:
+F = g
+a: F = a
+b: private F = b
+
+a b c: ; @echo $@: F=$(F)
+a: b
+b: c
+',
+ '', "c: F=a\nb: F=b\na: F=a\n");
+
+# 2: Again, but this time we start with "b" so "a"'s variable is not in scope
+&run_make_test(undef, 'b', "c: F=g\nb: F=b\n");
+
+# 3: Verification with pattern-specific variables
+&run_make_test('
+t.a:
+
+F1 = g
+F2 = g
+%.a: private F1 = a
+%.a: F2 = a
+
+t.a t.b: ; @echo $@: F1=$(F1) / F2=$(F2)
+t.a: t.b
+',
+ '', "t.b: F1=g / F2=a\nt.a: F1=a / F2=a\n");
+
+# 4: Test private global variables
+&run_make_test('
+a:
+private F = g
+G := $(F)
+a:
+b: F = b
+
+a b: ; @echo $@: F=$(F) / G=$(G)
+a: b
+',
+ '', "b: F=b / G=g\na: F= / G=g\n");
+
+# 5: Multiple conditions on the same variable. Test export.
+delete $ENV{'_X'};
+&run_make_test('
+_X = x
+a: export override private _X = a
+a: ; @echo _X=$(_X) / _X=$$_X
+',
+ '', "_X=a / _X=a");
+
+# 6: Test override.
+&run_make_test(undef, '_X=c', "_X=a / _X=a\n");
+
+# 7: Ensure keywords still work as targets
+&run_make_test('
+a: export override private foo bar
+foo bar export override private: ; @echo $@
+',
+ '', "export\noverride\nprivate\nfoo\nbar\n");
+
+# 8: Ensure keywords still work as variables
+&run_make_test('
+private = g
+a: private = a
+a: b
+a b: ; @echo $@=$(private)
+',
+ '', "b=a\na=a\n");
+
+# 9: make sure private suppresses inheritance
+run_make_test(q!
+DEFS = FOO
+all: bar1
+bar1: private DEFS += 1
+bar3: private DEFS += 3
+bar1: bar2
+bar2: bar3
+bar1 bar2 bar3: ; @echo '$@: $(DEFS)'
+!,
+ '', "bar3: FOO 3\nbar2: FOO\nbar1: FOO 1\n");
+
+# 10: Test append with pattern-specific variables and private
+
+run_make_test(q!
+IA = global
+PA = global
+PS = global
+S = global
+PS = global
+SV = global
+b%: IA += b%
+b%: private PA += b%
+b%: private PS = b%
+bar: all
+bar: IA += bar
+bar: private PA += bar
+bar: private PS = bar
+a%: IA += a%
+a%: private PA += a%
+a%: private PS = a%
+all: IA += all
+all: private PA += all
+all: private PS = all
+
+bar all: ; @echo '$@: IA=$(IA)'; echo '$@: PA=$(PA)'; echo '$@: PS=$(PS)'
+!,
+ '', "all: IA=global b% bar a% all
+all: PA=global a% all
+all: PS=all
+bar: IA=global b% bar
+bar: PA=global b% bar
+bar: PS=bar\n");
+
+1;
diff --git a/src/kmk/tests/scripts/variables/special b/src/kmk/tests/scripts/variables/special
new file mode 100644
index 0000000..7e8a64f
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/special
@@ -0,0 +1,150 @@
+# -*-perl-*-
+
+$description = "Test special GNU make variables.";
+
+$details = "";
+
+&run_make_test('
+
+X1 := $(sort $(filter FOO BAR,$(.VARIABLES)))
+
+FOO := foo
+
+X2 := $(sort $(filter FOO BAR,$(.VARIABLES)))
+
+BAR := bar
+
+all: ; @echo X1 = $(X1); echo X2 = $(X2); echo LAST = $(sort $(filter FOO BAR,$(.VARIABLES)))
+',
+ '', "X1 =\nX2 = FOO\nLAST = BAR FOO\n");
+
+# SV 45728: Test that undefining a variable is reflected properly
+
+&run_make_test('
+FOO := foo
+BAR := bar
+$(info one: $(sort $(filter FOO BAR BAZ,$(.VARIABLES))))
+undefine BAR
+BAZ := baz
+$(info two: $(sort $(filter FOO BAR BAZ,$(.VARIABLES))))
+all:;@:
+',
+ '', "one: BAR FOO\ntwo: BAZ FOO\n");
+
+# $makefile2 = &get_tmpfile;
+# open(MAKEFILE, "> $makefile2");
+
+# print MAKEFILE <<'EOF';
+
+# X1 := $(sort $(.TARGETS))
+
+# all: foo
+# @echo X1 = $(X1)
+# @echo X2 = $(X2)
+# @echo LAST = $(sort $(.TARGETS))
+
+# X2 := $(sort $(.TARGETS))
+
+# foo:
+
+# EOF
+
+# close(MAKEFILE);
+
+# # TEST #2
+# # -------
+
+# &run_make_with_options($makefile2, "", &get_logfile);
+# $answer = "X1 =\nX2 = all\nLAST = all foo\n";
+# &compare_output($answer, &get_logfile(1));
+
+# Test the .RECIPEPREFIX variable
+# kmk: This test isn't -j1 safe, haven't bother looking into why yet.
+&run_make_test('
+define foo
+: foo-one\
+foo-two
+: foo-three
+ : foo-four
+endef
+
+orig: ; : orig-one
+ : orig-two \
+orig-three \
+ orig-four \
+ orig-five \\\\
+ : orig-six
+ $(foo)
+
+.RECIPEPREFIX = >
+test: ; : test-one
+>: test-two \
+test-three \
+>test-four \
+> test-five \\\\
+>: test-six
+>$(foo)
+
+.RECIPEPREFIX =
+reset: ; : reset-one
+ : reset-two \
+reset-three \
+ reset-four \
+ reset-five \\\\
+ : reset-six
+ $(foo)
+',
+ '-j1 orig test reset',
+ ': orig-one
+: orig-two \
+orig-three \
+orig-four \
+ orig-five \\\\
+: orig-six
+: foo-one foo-two
+: foo-three
+: foo-four
+: test-one
+: test-two \
+test-three \
+test-four \
+ test-five \\\\
+: test-six
+: foo-one foo-two
+: foo-three
+: foo-four
+: reset-one
+: reset-two \
+reset-three \
+reset-four \
+ reset-five \\\\
+: reset-six
+: foo-one foo-two
+: foo-three
+: foo-four');
+
+# Test that the "did you mean TAB" message is printed properly
+
+run_make_test(q!
+$x.
+!,
+ '', '#MAKEFILE#:2: *** missing separator. Stop.', 512);
+
+run_make_test(q!
+foo:
+ bar
+!,
+ '', '#MAKEFILE#:3: *** missing separator (did you mean TAB instead of 8 spaces?). Stop.', 512);
+
+run_make_test(q!
+.RECIPEPREFIX = :
+foo:
+ bar
+!,
+ '', '#MAKEFILE#:4: *** missing separator. Stop.', 512);
+
+1;
+
+### Local Variables:
+### eval: (setq whitespace-action (delq 'auto-cleanup whitespace-action))
+### End:
diff --git a/src/kmk/tests/scripts/variables/undefine b/src/kmk/tests/scripts/variables/undefine
new file mode 100644
index 0000000..38707b8
--- /dev/null
+++ b/src/kmk/tests/scripts/variables/undefine
@@ -0,0 +1,73 @@
+# -*-perl-*-
+
+$description = "Test variable undefine.";
+
+$details = "";
+
+# TEST 0: basic undefine functionality
+
+run_make_test('
+a = a
+b := b
+define c
+c
+endef
+
+$(info $(flavor a) $(flavor b) $(flavor c))
+
+n := b
+
+undefine a
+undefine $n
+undefine c
+
+$(info $(flavor a) $(flavor b) $(flavor c))
+
+
+all: ;@:
+',
+'', "recursive simple recursive\nundefined undefined undefined");
+
+
+# TEST 1: override
+
+run_make_test('
+undefine a
+override undefine b
+
+$(info $(flavor a) $(flavor b))
+
+
+all: ;@:
+',
+'a=a b=b', "recursive undefined");
+
+1;
+
+# TEST 2: undefine in eval (make sure we undefine from the global var set)
+
+run_make_test('
+define undef
+$(eval undefine $$1)
+endef
+
+a := a
+$(call undef,a)
+$(info $(flavor a))
+
+
+all: ;@:
+',
+'', "undefined");
+
+
+# TEST 3: Missing variable name
+
+run_make_test('
+a =
+undefine $a
+all: ;@echo ouch
+',
+'', "#MAKEFILE#:3: *** empty variable name. Stop.\n", 512);
+
+1;