Skip to content

Generated Makefile trap 'kill 0' kills the parent process group under make -n — VS Code (Makefile Tools) crashes on folder open #57

Description

@ksenthil86

Summary

The generated Makefile's start target uses trap 'kill 0' EXIT:

https://github.com/neo4j-labs/create-context-graph/blob/main/src/create_context_graph/templates/base/Makefile.j2#L10-L15

start:
	@echo "Starting {{ domain.name }} Context Graph..."
	@trap 'kill 0' EXIT; \
		$(MAKE) dev-backend & \
		$(MAKE) dev-frontend & \
		wait

Because the recipe line contains $(MAKE), GNU make executes it even under --dry-run/-n (this is documented MAKE-variable special handling: recipe lines containing $(MAKE) are always run, -n is only propagated to the sub-makes). Under -n the sub-makes print and exit immediately, wait returns, the shell exits — and the EXIT trap fires kill 0, which SIGTERMs the entire process group of whatever invoked make.

Impact: opening a generated project in VS Code kills VS Code

VS Code's popular Makefile Tools extension (ms-vscode.makefile-tools) auto-runs make --dry-run on the default target when a folder containing a Makefile is opened ("configure on open"). start is the first target, so it is the default. The extension host spawns make inside VS Code's process group, so ~3 seconds after opening any project generated by create-context-graph, kill 0 SIGTERMs every VS Code process — all windows, the extension host, pty host, everything — at once.

From the user's perspective, VS Code hard-crashes every time they open the generated project, with no error pointing at the Makefile. We spent a while chasing antivirus/system-level red herrings before tracing the SIGTERM wave (signal 15 to the whole process family, exactly at Makefile Tools activation) back to this trap.

Anything else that runs make -n (shell completion helpers, other IDE integrations, CI dry-runs) is similarly killed.

Reproduction

In any generated project (macOS, GNU make 3.81 and 4.x):

$ make -n start; echo "exit: $?"
# → the process group receives SIGTERM; in an interactive shell your terminal tab dies.

Isolated repro showing the signal:

$ python3 -c "
import os, subprocess
p = subprocess.Popen(['make','-n','start'], preexec_fn=os.setsid)
print('returncode:', p.wait())"
returncode: -15

Or simply: open the generated folder in VS Code with the Makefile Tools extension installed → the whole VS Code app is killed within seconds, reproducibly.

Suggested fix

Kill only the jobs the recipe started, not the whole process group:

start:
	@echo "Starting {{ domain.name }} Context Graph..."
	@trap 'kill $$(jobs -p) 2>/dev/null' EXIT; \
		$(MAKE) dev-backend & \
		$(MAKE) dev-frontend & \
		wait

This preserves the intended behavior (Ctrl-C / exit tears down both dev servers) and is inert under make -n, since jobs -p only lists the recipe's own background children. Verified: make -n start returns 0 with this change, and VS Code opens the project normally.

🤖 Filed with the help of Claude Code after debugging this on a generated project.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions