I have a command that I'm calling from code:

execvp('generate', ...)

which is an executable program that my code communicates with via stdin, stdout and stderr. This works fine, not a single problem.

I want to change this so I can set resource limits on generate. So I've tried calling:

ulimit -t 1 && generate

But I get a broken pipe when I try to communicate with it.

So I put the line above in a shell script generate_wrapper:

ulimit -t 1 && generate

And I get a broken pipe when I try to communicate with it.


$ echo "foo" | generate_wrapper
$ echo "foo" | generate

both give me the correct, identical output. I figured it might be the &&, so I tried just the bare command:


But it still works from the CL, and I still get a broken pipe when I try to communicate with it from code.

I tried to explicitly route the fds, and got:

generate >&1 2>&2 <&0

But no, I still get a broken pipe when I try to communicate with it from code.

So obviously I haven't a clue what I'm doing. Can you help? How do I write a wrapper so I can ulimit a spawned subprocess (rlimit isn't available for pids in my host language) and still communicate with it?

  • I think this should either either get moved to Unix&Linux or StackOverflow since it is about programming and access to Unix resources, not a general computer user question. Don't re-ask, just wait and see. I've flagged it for a moderator to migrate. – Caleb Jun 29 '11 at 11:44
  • Oh, the broken pipe in all cases is an EPIPE, rather than a SIGPIPE: "Error: EPIPE, Broken pipe" – Ian Jun 29 '11 at 11:44
  • Caleb, wasn't sure which way to go, but here did seem to be more questions on piping stuff around bash. – Ian Jun 29 '11 at 11:45
  • 2
    @lan: That's because new unix users frequently don't understand how the basics of pipes work and on the unix.SE that's kind of assumed knowledge. However your question is a little more advanced than that and involves access from another language and ulimit stuff. That's time for Unix expert advice ... it's more of a programmer question than a usage question. – Caleb Jun 29 '11 at 11:47
  • pipes, shells scripts and ulimit. O my! – sealz Jun 29 '11 at 11:52

Any reason you don't want to call ulimit (2) in the generating code before execvp?

From the man page:

#include <ulimit.h>
long ulimit (int cmd, ...);

The ulimit() function will get and set process limits.


EPIPE with its "broken pipe" error message is raised when the SIGPIPE signal is set to be ignored and a writing process tries to write further output to the already closed reading end of the pipe where, in your case, generate has all file descriptors referring to its stdin closed.

If there is a parent process that has set the SIGPIPE signal to be ignored, the child process will inherit this behaviour (... and in non-interactive shells this cannot be undone).

So, in your case, the program that calls your generate executable has set the SIGPIPE signal to be ignored. Then, when your generate program in your generate_wrapper has processed input for one second (ulimit -t 1) generate will exit and close its stdin. If your writing process with ignored SIGPIPE then attempts to write further data to the now closed stdin of generate the write system call will fail and you will see EPIPE with its "broken pipe" error message (see man 2 write).

As for a wrapper to reduce CPU resource consumption use tools such as cstream or mbuffer.

# test: ulimit -t
#help ulimit
time -p bash -c 'yes | head -100000000 | wc -c'
time -p bash -c 'ulimit -t 1; yes | head -100000000 | wc -c'

# cstream test
#top -u
yes | cstream -b 100000 -t 100000 -o -
yes | cstream -b 100000 -t 100000 | cat -n

# generate_wrapper
cstream -b 100000 -t 100000 | generate

execvp does not handle system commands but only direct binaries. Also script files are only masked system commands in this way.

I think you need to use system() if you wish to run commands instead of binaries.

dmckee's idea about calling ulimit() before execvp() is also a sound one. This will however affect everything the process does from here on.

  • Unfortunately I neither have rlimit or ulimit available. So the question stands. Can it be done? – Ian Jul 13 '11 at 22:30

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.