Module | Open4 |
In: |
lib/open4.rb
|
stolen directly from Open3::open3.rb!
open4.rb: Spawn a program like popen, but with stderr, and pid, too. You might also want to use this if you want to bypass the shell. (By passing multiple args, which IO#popen does not allow)
Usage:
require "open4" stdin, stdout, stderr, pid = Open4.popen4('nroff -man') or include Open4 stdin, stdout, stderr, pid = popen4('nroff -man')
# File lib/open4.rb, line 18 18: def popen4(*cmd) 19: #--{{{ 20: pw = IO::pipe # pipe[0] for read, pipe[1] for write 21: pr = IO::pipe 22: pe = IO::pipe 23: 24: verbose = $VERBOSE 25: begin 26: $VERBOSE = nil # shut up warning about forking in threads, world writable 27: # dirs, etc 28: cid = 29: fork{ 30: # child 31: pw[1].close 32: STDIN.reopen(pw[0]) 33: pw[0].close 34: 35: pr[0].close 36: STDOUT.reopen(pr[1]) 37: pr[1].close 38: 39: pe[0].close 40: STDERR.reopen(pe[1]) 41: pe[1].close 42: 43: STDOUT.sync = true 44: STDERR.sync = true 45: 46: exec(*cmd) 47: } 48: ensure 49: $VERBOSE = verbose 50: end 51: 52: pw[0].close 53: pr[1].close 54: pe[1].close 55: pi = [pw[1], pr[0], pe[0]] 56: pw[1].sync = true 57: if defined? yield 58: begin 59: yield(cid, *pi) 60: return(Process::waitpid2(cid).last) 61: ensure 62: pi.each{|p| p.close unless p.closed?} 63: end 64: end 65: [cid, pw[1], pr[0], pe[0]] 66: #--}}} 67: end