module Shell:sig..end
call, signal handlers
 are automatically installed by Shell_sys.install_job_handlers, unless
 this installation has already been performed. You can configure these
 handlers by Shell_sys.configure_job_handlers. The handlers remain
 in effect even after call returns.
 Note that this has a global side effect on the whole process, because
 there is only one set of signal handlers.
Shell_sys.job abstraction.exception Subprocess_error of (string * Unix.process_status) list
type 
type 
type 
val command : ?cmdname:string ->
       ?arguments:string array ->
       ?chdir:string ->
       ?environment:Shell_sys.environment ->
       ?descriptors:Unix.file_descr list ->
       ?assignments:assignment list -> string -> Shell_sys.commandcall. The anonymous
 string argument is the name of the executable to invoke. If the name
 contains a '/', it is simply interpreted as the filename of the
 executable. Otherwise the command is searched in the current PATH.
cmdname : The name of the command passed in argv[0]. By
   default, this argument is derived from the name of the executable.arguments : The arguments of the command (starting with the
   first real argument, skipping cmdname). By default  [] .chdir : Before the command is executed it is changed to
   this directory.environment : The environment of the command. By default, the
   current environmentdescriptors : The list of file descriptors to share with the
   current process; all other file descriptors will be closed.
   By default,  [stdin; stdout; stderr] .assignments : The list of descriptor assignments. The assignments
   are applied one after the other. By default empty.val cmd : ?cmdname:string ->
       ?chdir:string ->
       ?environment:Shell_sys.environment ->
       ?descriptors:Unix.file_descr list ->
       ?assignments:assignment list ->
       string -> string list -> Shell_sys.commandcommand but with a slightly different interface: Use
  cmd "ls" [ "/dir/file" ]  command ~arguments:[|"/dir/file"|] "ls" 
 The named arguments have the same meanings as in command.
val call : ?ignore_error_code:bool ->
       ?mode:Shell_sys.group_mode ->
       ?stdin:producer ->
       ?stdout:consumer ->
       ?stderr:consumer -> Shell_sys.command list -> unit [c1;c2;...;cN]  is passed, this corresponds to the pipeline
  c1 | c2 | ... | cN  (in shell notation).
 The function returns normally if all processes can be started and
 terminate regularly with exit code 0. If a process terminates with
 some other exit code, and ignore_error_code is set, the function
 returns normally, too. The latter does not apply if a process terminates
 because of a signal (which triggers always the exception
 Subprocess_error).
 If a process terminates with an exit code other than 0 and 
 ignore_error_code is not set (the default), or if a process is
 terminated because of a signal, the exception Subprocess_error
 will be raised. For every command the process result is included
 in the exception argument.
 If a process cannot be started (e.g. because of insufficient 
 resources), the function will try to shut down the already running
 part of the pipeline by sending SIGTERM to these processes.
 It is not checked whether the processes actually terminate (no
 "wait" for them); an appropriate exception will be raised.
 In the case that it is not even possible to perform these cleanup
 actions, the exception Shell_sys.Fatal_error will be raised.
 When the function raises an exception other than Subprocess_error,
 a serious error condition has happened, and it is recommended
 to exit the program as soon as possible.
ignore_error_code : If true, exit codes other than 0 of the
   subprocesses are ignored. This does not apply to signals, however.
   By default false.mode : See Shell_sys.run_job for a detailed description
   of this parameter. By default Same_as_caller.stdin : If present, the first process of the pipeline reads
   input data from this procucer. By default, there is no such 
   producer.stdout : If present, the last process of the pipeline writes
   output data to this consumer. By default, there is no such
   consumer.stderr : If present, all processes of the pipeline write
   their error messages to this consumer. By default, there is no
   such consumer.val setup_job : ?stdin:producer ->
       ?stdout:consumer ->
       ?stderr:consumer ->
       Shell_sys.command list -> Shell_sys.job * Unix.file_descr listcall, but does not execute it. In addition to
 the job, the file descriptors are returned that must be closed 
 when the job is done.val postprocess_job : ?ignore_error_code:bool -> Shell_sys.job_instance -> unitSubprocess_error when there is an error that cannot be ignored.
 As error conditions are considered non-zero exit codes of any
 called processes, or signals terminating any of the called processes.
ignore_error_code : If true, exit codes other than 0 of the
   subprocesses are ignored. This does not apply to signals, however.
   By default false.val assign : src:Unix.file_descr -> target:Unix.file_descr -> assignmentsrc or reading from src
 will actually write to target or read from target
 (i.e., the target descriptor is duplicated and replaces
 the src descriptor just before the process is launched.)
 Note that assignments work only if the descriptors are shared
 with the called process, so they must also be contained in the
 descriptors list of command or cmd. Furthermore, the
 close-on-exec flag must not be set.
val (>&) : Unix.file_descr -> Unix.file_descr -> assignmentassign, but infix notation. For example,
 stdout >& stderr creates an assignment such that all output
 to stdout is redirected to stderr.
 f >& g is the same as assign ~src:f target:g. It should
 be used for output assignments (as in the Bourne shell).
val (<&) : Unix.file_descr -> Unix.file_descr -> assignmentassign, but infix notation. For example,
 stdin <& f creates an assignment such that the called process
 reads from the open file descriptor f.
 f <& g is the same as assign ~src:f target:g. It should
 be used for input assignments (as in the Bourne shell).
val assigned_pair : assignment -> Unix.file_descr * Unix.file_descr(target,src).val stdin : Unix.file_descrval stdout : Unix.file_descrval stderr : Unix.file_descrval from_string : ?pos:int -> ?len:int -> ?epipe:(unit -> unit) -> string -> producers. After these data
 are sent, the pipeline is closed.
pos : The position in s where the data slice to transfer begins.
    By default 0.len : The length of the data slice to transfer. By default,
    all bytes from the start position pos to the end of the
    string are taken.epipe : This function is called when the pipeline breaks
    (EPIPE). Default: the empty function. EPIPE exceptions are
    always caught, and implicitly handled by closing the pipeline.val from_stream : ?epipe:(unit -> unit) -> string Stream.t -> producer
epipe : This function is called when the pipeline breaks
    (EPIPE). Default: the empty function. EPIPE exceptions are
    always caught, and implicitly handled by closing the pipeline.val from_function : producer:(Unix.file_descr -> bool) -> unit -> producerShell_sys.add_producer for the meaning of the producer
  function.val from_file : string -> producerval from_fd : Unix.file_descr -> producerval from_dev_null : producer/dev/null.val to_buffer : Buffer.t -> consumerval to_function : consumer:(Unix.file_descr -> bool) -> unit -> consumerShell_sys.add_consumer for the meaning of the consumer
  function.val to_file : ?append:bool -> string -> consumerappend is given, the file is
 truncated and overwritten. If append is true, the data are
 appended to the file. By default, append is false.val to_fd : Unix.file_descr -> consumerval to_dev_null : consumer/dev/null.
 The following examples show toploop sessions using Shell.
Call the command "ls" without redirection:
 # call [ command "ls" ];;
 IDEAS       s1.ml~      shell.mli~      shell_sys.ml~  unix_exts.ml
 META        shell.a     shell.ml~       shell_sys.o    unix_exts.mli
 Makefile    shell.cma   shell_sys.cmi   t              unix_exts.mli~
 Makefile~   shell.cmi   shell_sys.cmo   testjob        unix_exts.ml~
 depend      shell.cmo   shell_sys.cmx   testjob~       unix_exts.o
 libshell.a  shell.cmxa  shell_sys.ml    unix_exts.cmi  unix_exts_c.c
 log         shell.ml    shell_sys.mli   unix_exts.cmo  unix_exts_c.c~
 s1.ml       shell.mli   shell_sys.mli~  unix_exts.cmx  unix_exts_c.o
 \- : unit = ()
 
 The output of "ls" is collected in the buffer b:
 
 # let b = Buffer.create 10;;
 val b : Buffer.t = <abstr>
 # call ~stdout:(to_buffer b) [ command "ls" ];;
 \- : unit = ()
 # Buffer.contents b;;
 \- : string =
 "IDEAS\nMETA\nMakefile\nMakefile~\ndepend\n..."
 
Because "/a" does not exist, "ls" will fail. The command writes the message to stderr (not redirected here), and returns with an exit code of 1, triggering an exception:
 # call [ command ~arguments:[| "/a" |] "ls" ];;
 /bin/ls: /a: No such file or directory
 Uncaught exception: Shell.Subprocess_error ["/bin/ls", Unix.WEXITED 1].
 
 Here, the message written to stderr is collected in b:
 
 # Buffer.clear b;;
 \- : unit = ()
 # call ~stderr:(to_buffer b) [ command ~arguments:[| "/a" |] "ls" ];;
 Uncaught exception: Shell.Subprocess_error ["/bin/ls", Unix.WEXITED 1].
 # Buffer.contents b;;
 \- : string = "/bin/ls: /a: No such file or directory\n"
 
Here, the output of "cat" becomes the input of "sort":
 # call [ command ~arguments:[|"META"|] "cat"; command "sort" ];;
 archive(byte) = "shell.cma"
 archive(native) = "shell.cmxa"
 description = "Unix shell functions"
 linkopts = "-cclib -lshell"
 requires = "unix str"
 version = "0.0"
 \- : unit = ()
 
 The same, but the output of "sort" is collected in the buffer b:
 
 # Buffer.clear b;;
 \- : unit = ()
 # call ~stdout:(to_buffer b) [ command ~arguments:[|"META"|] "cat"; command "sort" ];;
 \- : unit = ()
 # Buffer.contents b;;
 \- : string =
 "archive(byte) = \"shell.cma\"\narchive(native) = \"shell.cmxa\"\ndescription = \"Unix shell functions\"\nlinkopts = \"-cclib -lshell\"\nrequires = \"unix str\"\nversion = \"0.0\"\n"
 
 The contents of the string s are written to the input of "sort":
 
 # let s = "f\na\nd\nc\n";;
 val s : string = "f\na\nd\nc\n"
 # call ~stdin:(from_string s) [ command "sort" ];;
 a
 c
 d
 f
 \- : unit = ()
 
 It is possible to have several redirections. Here, the string s is
 sorted by "sort", and the output is collected in the buffer b:
 
 # Buffer.clear b;;
 \- : unit = ()
 # call ~stdout:(to_buffer b) ~stdin:(from_string s) [ command "sort" ];;
 \- : unit = ()
 # Buffer.contents b;;
 \- : string = "a\nc\nd\nf\n"
 
 Here, the output and errors of "ls" are both collected in the buffer
 b:
 
 # Buffer.clear b;;
 \- : unit = ()
 # call ~stdout:(to_buffer b) 
        [ command 
            ~assignments:[ stderr >& stdout ] 
            ~arguments:[| "/a" |] 
            "ls" ];;
 Uncaught exception: Shell.Subprocess_error ["/bin/ls", Unix.WEXITED 1].
 # Buffer.contents b;;
 \- : string = "/bin/ls: /a: No such file or directory\n"
 
Of course, all features can be combined arbitrarily.
Note that error reporting is better than in a traditional shell, because the exit codes of all started commands are returned. (Shells usually only return the exit code of the last command of a pipeline.)
 For non-standard pipelines, you can also use the functions in
 Shell_sys. "call" is a simple concatenation of Shell_sys invocations.