Roger Lipscombe
Roger Lipscombe

Reputation: 91805

How to discover default target in make?

I've seen the question "How does “make” app know default target to build if no target is specified?", which explains that the default target is the first target that doesn't being with a '.'.

How do I get make to tell me what that target is?

Context: I've got a recursive make system, with a variety of included makefiles. If I add a new target to my top level Makefile (or to my common include), that becomes the default target. I want to add .DEFAULT_GOAL: original-default-target, but I don't know what original-default-target is.

Upvotes: 2

Views: 1258

Answers (2)

Jaredo Mills
Jaredo Mills

Reputation: 717

A reliable way, which doesn't depend on parsing debug output (which is not documented, thus subject to change) is to run make in --query and --print-database modes together, then grep for the .DEFAULT_GOAL assignment. This variable, along with some examples and other special variables, is documented at Special Variables.

make -qp | grep ^".DEFAULT_GOAL := " | tail -n 1

Since --query + --print-database mode does not try to make (not even resolve dependencies and file freshness), it has two advantages compared with Roger's answer:

  1. no recipes are run
  2. directories are not recursed, no sub-makes are spawned. You get the .DEFAULT_GOAL of the current directory's Makefile

The tail -n 1 bit is needed to reliably get correct output. The output of something like $(info .DEFAULT_GOAL := fake-goal) in the makefile is sent to stdout first. The variables and rules are printed last, after the makefile is fully parsed and variables expanded. Hence, the last instance of .DEFAULT_GOAL on stdout is the genuine one you're looking for.

Caution: A makefile is effectively a script executed on parse, whether in --query/--dry-run mode or not. Functions are expanded, so something like $(shell BOOM) is expanded before at makefile parse time. It's not possible to reliably parse a makefile and determine the default target without executing anything. Only run make on makefiles you trust, or sandbox it.

Related questions:

Upvotes: 2

Roger Lipscombe
Roger Lipscombe

Reputation: 91805

Running make -d results in a lot of debug output. If you search this for the first occurrence of 'Updating goal targets', and look at the next target mentioned, this appears to be the default target.

For example:

$ make -d | grep -A2 -m1 'goal targets'
Updating goal targets....
Considering target file 'all'.
 File 'all' does not exist.

This implies that, for this Makefile at least, the current default target is all. This can then be enforced by adding .DEFAULT_GOAL: all to the top-level Makefile.

Upvotes: 3

Related Questions