Using response file on windows

648 views
Skip to first unread message

vinay hegde

unread,
Jan 18, 2017, 12:53:03 PM1/18/17
to ninja-build
Hi, 
I am new to Ninja & I am trying to use response file in a simple ninja build file (build.ninja). The content of the build file is like below.

rule cc
  command = cmd /c echo @$out.rsp
  rspfile = $out.rsp
  rspfile_content = "hi"
build xyz: cc

When I run ninja, I am getting the following output.
[1/1] cmd /c echo @xyz.rsp
@xyz.rsp

This means that, the response file xyz.rsp is used as an argument to echo command, but the content of the response file is not read. 
Any thing wrong in the syntax? Please guide me.


Regards
Vinay Hegde

Neil Mitchell

unread,
Jan 18, 2017, 1:11:49 PM1/18/17
to vinay hegde, ninja-build
Hi Vinay,

It's not the Ninja that is wrong, it's the echo call. In Windows, if
you write "echo @hello" it will literally echo "@hello" back at you.
Ninja gives support for creating the response files, but it does
nothing to make the programs you are calling support the @foo.txt
syntax. It just so happens most GNU utilities do, but it's far from
universal.

On Windows, you could do: cmd /c type $out.rsp

Thanks, Neil
> --
> You received this message because you are subscribed to the Google Groups
> "ninja-build" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to ninja-build...@googlegroups.com.
> For more options, visit https://groups.google.com/d/optout.

Neil Mitchell

unread,
Jan 19, 2017, 2:23:14 AM1/19/17
to vinay hegde, ninja-build
Perhaps you want cmd /c $out.bat, and to use .bat for your response
file? The first step is to experiment with cmd to see what works.

Thanks, Neil

On Thu, Jan 19, 2017 at 6:50 AM, vinay hegde <vin...@gmail.com> wrote:
> Hi Neil,
> Thank you for the quick reply. if I use 'cmd /c type $out.rsp', it will
> simply list content. It will not be run as commands. Please guide me.
> I assume, it's a a common problem for everyone. i.e. running long commands
> on windows.
> Does Ninja allow running multiple commands? i.e. for example, having two
> 'command = ' under a rule.
>
>
> Regards
> Vinay
> --
> Regards
> Vinay Hegde

Neil Mitchell

unread,
Jan 22, 2017, 8:52:07 AM1/22/17
to vinay hegde, ninja-build
Someone probably needs to do actual investigation, so passing it back
to the mailing list (I'm not a hardcore Ninja user - more an observer)

Thanks, Neil


On Sun, Jan 22, 2017 at 6:00 AM, vinay hegde <vin...@gmail.com> wrote:
> HI Neil,
> No luck with .bat also. I used the following code in ninja.build.
>
> #cmd1,cmd2,cmd3,cmd4 are the variables
> cmd1 = <some long command>
> cmd2 = <some long command>
> cmd3 = <some long command>
> cmd4 = <some long command>
>
> rule cc
> command = cmd /c @xyz.bat
> rspfile = xyz.bat
> rspfile_content = $cmd1 && $cmd2 && $cmd3 && $cmd4
>
> build foo.o: cc
>
>
> When I run nija, only partial/few commands are executed (for example: only
> cmd1 & cmd2 are executed). This means that, due long path issue, commands
> are not executed properly (as multiple commands are chained using &&).
>
> My understanding about the response file was that, file extension can be
> anything (need not be .bat) & the response content will be read by make. But
> here it's not the case and we are executing .bat as any other script.
>
> Am I missing something? I am still not clear, how other Ninja users work on
> Windows? Long path is a known issue in windows & I believe there is a
> standard way of tackling this issue in Ninja.( I feel what we are trying is
> kind of a workaround). Need your guidance. Thanks in advance.
>
> Regards
> Vinay
>
> On Thu, Jan 19, 2017 at 12:53 PM, Neil Mitchell <ndmit...@gmail.com>
> --
> Regards
> Vinay Hegde

Scott Graham

unread,
Jan 22, 2017, 8:16:13 PM1/22/17
to Neil Mitchell, vinay hegde, ninja-build
I suspect you're still subject the line length limits in a .bat as you're doing here.

I would suggest using something else to run the commands (say, python) or breaking up the 4 commands into separate rules, assuming they have inputs and outputs that could create a dependency tree amongst them.


>> >> > For more options, visit https://groups.google.com/d/optout.
>> >
>> >
>> >
>> >
>> > --
>> > Regards
>> > Vinay Hegde
>
>
>
>
> --
> Regards
> Vinay Hegde

--
You received this message because you are subscribed to the Google Groups "ninja-build" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ninja-build+unsubscribe@googlegroups.com.

vinay hegde

unread,
Jan 23, 2017, 7:38:39 AM1/23/17
to Scott Graham, Neil Mitchell, ninja-build
Hi Graham,
Thank you for the reply.Yes, as you mentioned, we can place all our commands in any script (say Python) & call python from Ninja. But for every target generation, I would have set of commands & it would be very difficult to maintain/create script for every target & then deleting them once done. But as in response file, house keeping is done by Ninja itself At least the Ninja manual says so (see below). So, I wanted to configure my ninja file to use response file. Please guide me.


rspfilerspfile_content

if present (both), Ninja will use a response file for the given command, i.e. write the selected string (rspfile_content) to the given file (rspfile) before calling the command and delete the file after successful execution of the command.

This is particularly useful on Windows OS, where the maximal length of a command line is limited and response files must be used instead.

Use it like in the following example:

rule link
  command = link.exe /OUT$out [usual link flags here] @$out.rsp
  rspfile = $out.rsp
  rspfile_content = $in

build myapp.exe: link a.obj b.obj [possibly many other .obj files]

Regards
Vinay


--
Regards
Vinay Hegde

Scott Graham

unread,
Jan 23, 2017, 11:20:42 AM1/23/17
to vinay hegde, Neil Mitchell, ninja-build
@rsp files are only useful if the target binary understands them, as in the case of link.exe in the docs. It's not a useful way to run multiple commands using only cmd.

Scott Graham

unread,
Jan 23, 2017, 11:33:01 AM1/23/17
to ninja-build, vinay hegde
Not that I know of.

On Mon, Jan 23, 2017 at 8:29 AM, vinay hegde <vin...@gmail.com> wrote:
OK. Let me try this (response file) for linking objects to generate a target.
Does Ninja support multiple command syntax or any other alternate? i.e. for example,

rule cc
   command = cmd /c echo hi
   command = cmd /c echo hello

 build xyz: cc

Regards
Vinay


--
Regards
Vinay Hegde

Nico Weber

unread,
Jan 23, 2017, 11:38:12 AM1/23/17
to Scott Graham, ninja-build, vinay hegde
Not directly, but you can emulate it by having one edge per command, and having them depend on each other through a dummy file that the earlier command touches at the end of its thing.

vinay hegde

unread,
Jan 23, 2017, 11:49:07 AM1/23/17
to Scott Graham, ninja-build
Thanks. Just to give you a background on the build system which I work on, We use OMake (A make utility from IBM Rational) as build tool & we have a wrapper tool on top of Omake to generate a required make file as input to Omake. The Make file will be generated on the fly, when we run/start the build.
As you know, Make (any Make flavor) allows multiple commands to run. i.e.
<Target> : <dependencies>
<TAB><commands which can be multi line>


Now What I am trying is that, translate the make file to Ninja build file. Challenge here is to have multiple commands.
I feel, this is a very basic requirement & any build tool should support the multi line commands. Because, most of the target generation process includes execution of multiple commands. for example, task like copy, archive, rename etc.
May be I am still missing fundamental idea about Ninja. Please guide me.

--
Regards
Vinay Hegde

Evan Martin

unread,
Jan 23, 2017, 2:26:00 PM1/23/17
to vinay hegde, Scott Graham, ninja-build
Ninja supports
1) passing a command line directly to CreateProcess, or
2) writing out a file containing an arbitrary string and then doing #1
Both of those are as simple as passing a string to a system API.  Because of this, Ninja does not understand anything about the contents of those strings, such as how to split them into multiple command executions.

If we get into the business of executing multiple commands, we then have to begin wondering about issues like: how do we show progress?  Do we check error codes while command are running?  What guarantees do we make about interrupts?  That is why it is nice to keep Ninja's model simple.

The model is simple but it is also powerful enough to have worked for many complex build systems, including Chrome's and Android's.  It would be nice to figure out a way to structure your build such that you don't require additional Ninja features.

Nico's idea is the best: if you have a build step that copies a file from one location to another, write a build rule for the copy.

But here's a hacky idea: use rspfile to generate a .bat file that contains your commands.

rule mybigcommand
  command = cmd that executes $out.bat
  rspfile = $out.bat
  rspfile_content = overlong command line here

Reply all
Reply to author
Forward
0 new messages