spaz has asked for the wisdom of the Perl Monks concerning the following question:

Somebody explain this please!

Through the course of my program, I need to use RCS to check out a file. Read it, modify the contents, write the changes back out, and check the file back in.
Everything works except for checking it back in with 'ci', which tries to be interactive.
From my shell I found that if I do input redirection via "< /dev/null", everything works and I'm not prompted. Yet when I replicate this in my code:
my $ci = "/usr/bin/ci"; system( "$ci", "-u", "-zLT", "$file", "< /dev/null" );
I get a prompt (from the interactive part) and then the following error after skipping the interactive part
ci: < /dev/RCS/null: No such file or directory
Can anybody shed some light?

Replies are listed 'Best First'.
Re: Input redirection
by Fastolfe (Vicar) on Dec 14, 2000 at 03:21 UTC
    Since breaking things up bypasses the shell (definitely a good thing), your "< /dev/null" bit will be passed as-is as an argument to ci, which is not what you want. The shell is what does your pipes and redirections for these types of things.

    To simulate the same behavior, just close STDIN before calling system (assuming you don't need it):

    close(STDIN); system($ci, '-u', '-zLT', $file);
    If you do need STDIN, and still need your multiple-argument form of system, consider saving STDIN, closing it, and re-opening it when you're done:
    open(STDSAVE, "<&STDIN"); close(STDIN); system(...); open(STDIN, "<&STDSAVE");
    Incidentally, does the -q flag allow you to do this in a "batch"/non-interactive mode without worrying about this sort of thing?
      I solved a similar problem by using the /dev/null approach and surrounding the ci command with "back-ticks" instead of using the "system" command.

      As an aside: using '-q' will stop the query if RCSdetects no differences between what you're trying to check in and what's already checked in - it silently aborts the checkin.

      If you want to force a checkin anyway, use '-f' instead.

      Hope this is useful!

Re: Input redirection
by chipmunk (Parson) on Dec 14, 2000 at 02:58 UTC
    If you call system() with multiple arguments, the shell is bypassed; the first argument to system() is the command, and the other arguments are passed directly to the command. In order to get the redirection, you need to call system with a single argument: system("$ci -u -zLT $file < /dev/null");

    The documentation for system explains this in more detail.