Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
534 views
in Technique[技术] by (71.8m points)

build - prefixing make output with target name - like ant does

Assuming I have the following Makefile:

.PHONY: mytarget
mytarget:
    echo "Hello World!"

running make mytarget gives the following output:

echo "Hello World!"
Hello World!

what I would like to see is something like the below

[mytarget] echo "Hello World!"
[mytarget] Hello World!

Is this possible?

I've been searching http://www.gnu.org/software/make/manual/make.html but haven't yet found a solution (granted, I haven't yet read the whole manual)

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

I'm not sure that there is something readily available for what you want in GNUmake (based on your link, I assume that we are speaking about this flavor). You can emulate it somehow, but I'm afraid no solution will be perfect.

use debug flags

make --debug=j mytarget will let make output information about each command it is about to launch, including the target that triggers it. In your case, the result will be:

Live child 0x021d2360 (mytarget) PID 10747 
echo Hello World!
Hello World!
Reaping winning child 0x021d2360 PID 10747 
Removing child 0x021d2360 PID 10747 from chain.

You have the information, but it's not really pretty, and I guess that parallel runs (-j options) won't produce a correct output.

Change SHELL

You can set the SHELL variable to tell make which interpreter is supposed to be used for launching the command. This can be (ab)used to perform an echo before actually launching the command. with the following line in the Makefile

SHELL=/bin/sh -c 'echo -n "[$@]: " && $$@'

we obtain

echo "Hello World!"
[mytarget]: "Hello World!"

This is not perfect, as the echoing of the whole line is done directly by make and thus not impacted by SHELL

change the command itself

If you can modify the commands themselves, it is possible to let make expand them so that the final output is what you want:

echo_target=@echo -n '[$@]: ' && echo $(1) && echo -n '[$@]: ' && $(1)

.PHONY: all bla

mytarget:
    $(call echo_target, echo "Hello World!")

will result in

[mytarget]: echo Hello World!
[mytarget]: Hello World!

but this requires adding the call to each command of your Makefile

Update: stitching it together

As mentioned by Natan Reisner, the SHELL command proposed above is not correct for arguments that contain spaces. As a matter of fact, it also occured to me that you can use SHELL to do the echoing before launching the command: Here is a new proposal that work with arguments containing spaces, and echoes the command with $@ prepended:

 SHELL=/bin/sh -c 'echo -n "[$@] " && echo "$$@" && echo -n "[$@] " && eval "$$@"'

on the following target

mytarget:
    echo 'Hello World!'
    @touch foo bar
    @ls -l "foo bar"

we obtain this result

echo 'Hello World!'
[mytarget] echo 'Hello World!'
[mytarget] Hello World!
[mytarget] echo foo bar
[mytarget] foo bar
[mytarget] touch foo bar
[mytarget] [mytarget] ls -l "foo bar"
[mytarget] -rw-rw-r-- 1 virgile virgile 0 juil. 23 08:44 foo bar

Note that there is still an issue for commands that do not produce any output, such as touch. This could probably be mitigated by redirecting the output of the command in a variable, and echoing only if the resulting length is non-zero.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...