Gri Commands

1: Introduction
2: Simple example
3: Fancy example
4: Running Gri
5: Programming Gri
6: General Issues
7: X-Y Plots
8: Contour Plots
9: Image Plots
10: Examples
11: Handling Data
12: Gri Commands
13: Gri Extras
14: Evolution of Gri
15: Installing Gri
16: Gri Bugs
17: System Tools
18: Acknowledgments
19: License
20: Newsgroup

21: Concept Index

12.48: The `system' Command

`system \system-command'

Tell the operating system to perform the indicated action. Whatever string follows the word `system' is passed directly to the operating system, after substitution of synonyms if any exist.

If your system command contains double-slashes, you must protect them from Gri (which will interpret them as comments) by enclosing in double-quotes, e.g. `system cat A | sed -e "s/foo#g" | cat > B'. (In the particular case of the `sed' command you could also do `system cat A | sed -e "s:foo::g" | cat > B'.

Note that `rpn' expressions are not evaluated, and variable values are not substituted before passing the string to the operating system. The exit status is stored in the builtin variable `..exit_status..'.

There are two ways to use the system:

  • Assign output to synonym: The form `\synonym = system ...' does the system command and then inserts the output from that command into the indicated synonym.)

  • Just run a command: The command `system ls' will list the files in the current directory.

For long commands, there are two approaches, the second preferred:

  • Use continuation lines: String a lot of information onto one effective system line, using the `\' line-continuation character at the ends of lines. The problem is that it's very easy to lose one of these backslashes. The next method is better.

  • Here-is syntax The here-is syntax of many unix shells is also provided. If the system command contains the characters `<<' followed by a word (with no space between!) then Gri will issue a system command which includes not only this line but also all succeeding lines, until a line is found which matches the indicated word precisely (with no leading space allowed). The `<< "WORD"' syntax is also supported, meaning that the operating system is being told not to mess with the dollar-signs -- needed in perl.

    Note: Be careful using this inside a new-command. Gri Recognizes the end of the body of a new-command by a line with `}' in the first column, and no non-white characters thereafter. If you system command happens to use a line with a curly brace (as in a loop in perl, for example), you must put whitespace before the brace. This won't affect the system command, but it will let Gri correctly realize that this is not the end of the new-command. For more information on new-commands see Parsing.

    Caution: Before sending the string to the system, Gri first translates any synonyms present. Be careful with this, since system commands calling awk, etc, very often use backslashes for the newline character `\n' within strings. If you have a synonym whose name starts with `\n', you can get a conflict. For example, the awk command `print "foo\nbar";' should print a line with `foo' on it, followed by a line with `bar' on it, but it will instead print a single line with `fooMISTAKE', if you had previously defined a synonym as `\nbar = "MISTAKE"'. One way to avoid this mistake is to make sure any `\n' characters appear at the end of strings, and then simply avoid having a synonym named `\n'.

    Here is a Perl example.
    \m = "Foo bar"
    system perl <<"EOF"
    $a = 100;
    print "foo bar is \m, and a is $a\n";
    print "BETTER: foo bar is \m, and a is $a\n";
    print "Q: was a 100?\n";
    EOF
    

    which, written more safely (partially avoiding the string `\n'), is
    \message = "Foo bar"
    system perl <<"EOF"
    $a = 100;
    print "foo bar is \message, and a is $a\n";
    print "Q: was a 100?\n";
    EOF
    

    Here is an Awk example. Note that the commandline flags `-f -' are required to force awk to take commands from standard input. Note also the absence of a final newline in the string; Awk does not require one, while Perl does. (Finally, as usual, note that the synonym `\.awk.' is being used instead of `awk', to ensure portability.)
    \m = "Foo bar"
    system \.awk. -f - <<"EOF"
    BEGIN{
    a = 100;
    print "foobar is \m, and a=", a, "\n";
    }
    EOF
    

    which, written more safely (avoiding the string `\n'), is
    \message = "Foo bar"
    system \.awk. -f - <<"EOF"
    BEGIN{
    a = 100;
    print "foobar is \message, and a=", a;
    }
    EOF
    

    To get the awkscript to read it's input from a named file, do e.g.
    system \.awk. -f - tst.dat <<"EOF"
    {print $1;}
    EOF
    

    where the file `tst.dat' contains lines the first item of which will be printed to the screen by this awkscript.

Some more examples:

  • To get the first 10 lines of a file called `foo.dat' inserted into another file called `bar.dat', you might do the following. Only the first method works; the second will fail because `.n.' will not be translated before passing to the operating system.
    \num = "-10"
    system head \num foo.dat > bar.dat
    # Following fails since .num. 
    # will not be translated
    .num. = -10
    system head .num. foo.dat > bar.dat
    

  • Issue a unix command to get a listing of files in the current working directory, and pipe them into the `more' system command.
    system ls -l *c | more
    

  • Store the date and time into a synonym, and use it in a title:
    \time = system date
    ...
    draw title "Plotted at time \time"
    

  • Use `awk' to prepare a two-column table of x, ranging from 0 to 1 in steps of 0.1, and sin(x). The table is stored in a file whose suffix is the process ID of the Gri job. This file is then opened, and the data plotted. Finally, a system command is issued to remove the temporary file.
    system \.awk. 'BEGIN { \
        for (x=0; x<1; x+=0.1) { \
          printf("%f %f\n", x, sin(x)) \
        } \
      }'  > tmp.\.pid.
    open tmp.\.pid.
    read columns x y
    close
    system rm tmp.\.pid.
    draw curve
    quit
    

    (Note the use of `\.awk.', a builtin synonym naming the awk program on your system.)

    NOTE Under unix, this command calls the Bourne shell, not the C-shell that is often used interactively. For many simple uses, the only difference from normal interactive use will be that `~' is not expanded to the home directory. For example, you'd do
    system \.awk. -f $HOME/foo/bar/cmd.gawk
    

    instead of the
    system \.awk. -f ~/foo/bar/cmd.gawk
    

    that you might expect from interactive C-shell usage. (Note the use of `\.awk.', a builtin synonym naming the awk program on your system.)

    RETURN VALUE: Sets `\.return_value' to system status, `N status'