Provided by: manpages-zh_1.5.2-1_all bug

NAME

       perlfaq8 -  (2003/01/26 17:44:04 )

DESCRIPTION

       Perl FAQ  (IPC) ()

        perl  FAQ  (perlvms,perlplan9...) perl

        exec() ?

         system()

       Keyboard
               Term::Cap
               Term::ReadKey               CPAN
               Term::ReadLine::Gnu         CPAN
               Term::ReadLine::Perl        CPAN
               Term::Screen                CPAN

       Screen
               Term::Cap
               Curses                      CPAN
               Term::ANSIColor             CPAN

       Mouse
               Tk                          CPAN

       Some of these specific cases are shown below.

       How do I print something out in color?

       In general, you don't, because you don't know whether the recipient has
       a color-aware display device.  If you know that they have an ANSI
       terminal that understands color, you can use the Term::ANSIColor module
       from CPAN:

           use Term::ANSIColor;
           print color("red"), "Stop!\n", color("reset");
           print color("green"), "Go!\n", color("reset");

       Or like this:

           use Term::ANSIColor qw(:constants);
           print RED, "Stop!\n", RESET;
           print GREEN, "Go!\n", RESET;

       How do I read just one key without waiting for a return key?

       Controlling input buffering is a remarkably system-dependent matter.
       On many systems, you can just use the stty command as shown in "getc"
       in perlfunc, but as you see, that's already getting you into
       portability snags.

           open(TTY, "+</dev/tty") or die "no tty: $!";
           system "stty  cbreak </dev/tty >/dev/tty 2>&1";
           $key = getc(TTY);           # perhaps this works
           # OR ELSE
           sysread(TTY, $key, 1);      # probably this does
           system "stty -cbreak </dev/tty >/dev/tty 2>&1";

       The Term::ReadKey module from CPAN offers an easy-to-use interface that
       should be more efficient than shelling out to stty for each key.  It
       even includes limited support for Windows.

           use Term::ReadKey;
           ReadMode('cbreak');
           $key = ReadKey(0);
           ReadMode('normal');

       However, using the code requires that you have a working C compiler and
       can use it to build and install a CPAN module.  Here's a solution using
       the standard POSIX module, which is already on your systems (assuming
       your system supports POSIX).

           use HotKey;
           $key = readkey();

       And here's the HotKey module, which hides the somewhat mystifying calls
       to manipulate the POSIX termios structures.

           # HotKey.pm
           package HotKey;

           @ISA = qw(Exporter);
           @EXPORT = qw(cbreak cooked readkey);

           use strict;
           use POSIX qw(:termios_h);
           my ($term, $oterm, $echo, $noecho, $fd_stdin);

           $fd_stdin = fileno(STDIN);
           $term     = POSIX::Termios->new();
           $term->getattr($fd_stdin);
           $oterm     = $term->getlflag();

           $echo     = ECHO | ECHOK | ICANON;
           $noecho   = $oterm & ~$echo;

           sub cbreak {
               $term->setlflag($noecho);  # ok, so i don't want echo either
               $term->setcc(VTIME, 1);
               $term->setattr($fd_stdin, TCSANOW);
           }

           sub cooked {
               $term->setlflag($oterm);
               $term->setcc(VTIME, 0);
               $term->setattr($fd_stdin, TCSANOW);
           }

           sub readkey {
               my $key = '';
               cbreak();
               sysread(STDIN, $key, 1);
               cooked();
               return $key;
           }

           END { cooked() }

           1;

       How do I check whether input is ready on the keyboard?

       The easiest way to do this is to read a key in nonblocking mode with
       the Term::ReadKey module from CPAN, passing it an argument of -1 to
       indicate not to block:

           use Term::ReadKey;

           ReadMode('cbreak');

           if (defined ($char = ReadKey(-1)) ) {
               # input was waiting and it was $char
           } else {
               # no input was waiting
           }

           ReadMode('normal');                  # restore normal tty settings

       How do I clear the screen?

       If you only have do so infrequently, use "system":

           system("clear");

       If you have to do this a lot, save the clear string so you can print it
       100 times without calling a program 100 times:

           $clear_string = `clear`;
           print $clear_string;

       If you're planning on doing other screen manipulations, like cursor
       positions, etc, you might wish to use Term::Cap module:

           use Term::Cap;
           $terminal = Term::Cap->Tgetent( {OSPEED => 9600} );
           $clear_string = $terminal->Tputs('cl');

       How do I get the screen size?

       If you have Term::ReadKey module installed from CPAN, you can use it to
       fetch the width and height in characters and in pixels:

           use Term::ReadKey;
           ($wchar, $hchar, $wpixels, $hpixels) = GetTerminalSize();

       This is more portable than the raw "ioctl", but not as illustrative:

           require 'sys/ioctl.ph';
           die "no TIOCGWINSZ " unless defined &TIOCGWINSZ;
           open(TTY, "+</dev/tty")                     or die "No tty: $!";
           unless (ioctl(TTY, &TIOCGWINSZ, $winsize='')) {
               die sprintf "$0: ioctl TIOCGWINSZ (%08x: $!)\n", &TIOCGWINSZ;
           }
           ($row, $col, $xpixel, $ypixel) = unpack('S4', $winsize);
           print "(row,col) = ($row,$col)";
           print "  (xpixel,ypixel) = ($xpixel,$ypixel)" if $xpixel || $ypixel;
           print "\n";

       ( WWW  )

        perlfunc  "crypt" "no echo"  ioctl()  POSIX  POSIX  stty

        CPAN  Term::ReadKey

           use Term::ReadKey;

           ReadMode('noecho');
           $password = ReadLine(0);

        Unix  /dev ;

       lockfiles

       open mode
             perlfunc  open   sysopen()  Fcntl  perl
           "O_RDWR|O_NDELAY|O_NOCTTY" perlfunc  sysopen

       end of line
            "\r" "\n" perl "\r" "\n"  Unix  ASCII  "\015"  "\012"   ("\015")
           ("0x0D")  ("\cM")

               print DEV "atv1\012";       # wrong, for some devices
               print DEV "atv1\015";       # right, for some devices

            "\n"  UnixDOS/Win  Macintosh "\015\012"    socket  (autoflushing)

       flushing output
            print()  select()  $|  perlvar  "$|"  perlfunc  "select" perlfaq5,
           ``How do I flush/unbuffer an output filehandle?  Why must I do
           this?''):

               $oldh = select(DEV);
               $| = 1;
               select($oldh);

               select((select(DEV), $| = 1)[0]);

           Or if you don't mind pulling in a few thousand lines of code just
           because you're afraid of a little $| variable:

               use IO::Handle;
               DEV->autoflush(1);

           As mentioned in the previous item, this still doesn't work when
           using socket I/O between Unix and Macintosh.  You'll need to hard
           code your line terminators, in that case.

       non-blocking input
            read()  sysread()   alarm 4  select()     perlfunc  select

       While trying to read from his caller-id box, the notorious Jamie
       Zawinski <jwz@netscape.com>, after much gnashing of teeth and fighting
       with sysread, sysopen, POSIX's tcgetattr business, and various other
       functions that go bump in the night, finally came up with this:

           sub open_modem {
               use IPC::Open2;
               my $stty = `/bin/stty -g`;
               open2( \*MODEM_IN, \*MODEM_OUT, "cu -l$modem_device -s2400 2>&1");
               # starting cu hoses /dev/tty's stty settings, even when it has
               # been opened on a pipe...
               system("/bin/stty $stty");
               $_ = <MODEM_IN>;
               chomp;
               if ( !m/^Connected/ ) {
                   print STDERR "$0: cu printed `$_' instead of `Connected'\n";
               }
           }

        Unix  - Unix   Crack

        passwd(1)

       Several modules can start other processes that do not block your Perl
       program.  You can use IPC::Open3, Parallel::Jobs, IPC::Run, and some of
       the POE modules.  See CPAN for more details.

           system("cmd &")

        fork perlfunc  fork  perlipc   Unix

       STDIN, STDOUT, and STDERR are shared
            STDINSTDOUT  STDERR    (pipe)   open

           SIGCHLD SIGPIPE  SIGCHLD  SIGPIPE  SIGPIPE  system("cmd&")

               $SIG{CHLD} = sub { wait };

               $SIG{CHLD} = 'IGNORE';

           You can also use a double fork. You immediately wait() for your
           first child, and the init daemon will wait() for your grandchild
           once it exits.

                   unless ($pid = fork) {
                           unless (fork) {
                       exec "what you really wanna do";
                       die "exec failed!";
                           }
                   exit 0;
                   }
               waitpid($pid,0);

            Signals  system("prog &")

       /

        ``''  Signals

        C  [re-entrant]  print() stdio   (dump core)  syswrite()  print()

        malloc()

           $Interrupted = 0;   #
           $SIG{INT} = sub {
               $Interrupted++;
               syswrite(STDERR, "ouch\n", 5);
           }

        < FH>read()connect()  wait()  Signals  flock()

        Unix  shadow

        perl  perlfunc  getpw*()  passwd(5)  pwd_mkdb(8) pwd_mkdb(5)

        date(1)   UnixMS-DOSWindows  NT VMS  set time

           $ENV{TZ} = "MST7MDT";                  # unixish
           $ENV{'SYS$TIMEZONE_DIFFERENTIAL'}="-5" # vms
           system "trn comp.lang.perl.misc";

        sleep()  alarm() ?

        sleep()  select  select()  Time::HiRes  BSD::Itimer  ( CPAN  Perl 5.8
       Time::HiRes ).

        Time::HiRes CPAN  Perl 5.8

        Perl  syscall()  gettimeofday(2)

           require 'sys/syscall.ph';

           $TIMEVAL_T = "LL";

           $done = $start = pack($TIMEVAL_T, ());

           syscall(&SYS_gettimeofday, $start, 0) != -1
                      or die "gettimeofday: $!";

              ##########################
              # DO YOUR OPERATION HERE #
              ##########################

           syscall( &SYS_gettimeofday, $done, 0) != -1
                  or die "gettimeofday: $!";

           @start = unpack($TIMEVAL_T, $start);
           @done  = unpack($TIMEVAL_T, $done);

           # fix microseconds
           for ($done[1], $start[1]) { $_ /= 1_000_000 }

           $delta_time = sprintf "%.4f", ($done[0]  + $done[1]  )
                                                   -
                                        ($start[0] + $start[1] );

        atexit() setjmp()/longjmp()

        Perl  END  atexit() (thread)  END  perlmod

       For example, you can use this to make sure your filter program managed
       to finish its output without filling up the disk:

           END {
               close(STDOUT) || die "stdout close failed: $!";
           }

       END  END

               use sigtrap qw(die normal-signals);

       Perl  eval()  eval()  setjmp die() longjmp  Signals  Camel flock()

        exceptions.pl  perl

        atexit()  rmexit() CPAN  AtExit

        sockets System V (Solaris)

        Sys-V  Solaris 2.X socket  perl   ``use Socket''

        SunOS  Solaris

        Perl C

        -  C  Perl  [h2xs, xsubpp]   syscall() syscall  perlfunc

        perl  CPAN On Windows, try Win32::API.  On Macs, try Mac::Carbon.  If
       no module has an interface to the C function, you can inline a bit of C
       in your Perl source with Inline::C.

        ioctl() syscall()

        perl  h2ph  C   cpp(1) &SYS_getitimer  errno.h syscall.h socket.h
       ioctl.h  *.ph

           1.
           2.  cd /usr/include
           3.  h2ph *.h */*.h

        h2xs  perl C  Perl  (extensions) h2xs  perlxstut

        h2xs perlxstut  MakeMaker  make perl  make   perl

        setuid perl

        setuid Perl perlsec

        (pipe)

       IPC::Open2 perl pipe() fork()  exec()  (  IPC::Open2 ) perlipc
       "Bidirectional Communication with Another Process" "Bidirectional
       Communication with Yourself"

       You may also use the IPC::Open3 module (part of the standard perl
       distribution), but be warned that it has a different order of arguments
       from IPC::Open2 (see IPC::Open3).

        system()

        system()  (``)  system()   16   (``)   STDOUT

           $exit_status   = system("mail-users");
           $output_string = `ls`;

        STDERR

           system $cmd;                #  system()
           $output = `$cmd`;           #  backticks (``)
           open (PIPE, "cmd |");       #  open()

        system() STDOUT  STDERR  script  STDOUT, STDERR open()    STDOUT

        IPC::Open3 .  Benjamin Goldberg provides some sample code:

       To capture a program's STDOUT, but discard its STDERR:

           use IPC::Open3;
           use File::Spec;
           use Symbol qw(gensym);
           open(NULL, ">", File::Spec->devnull);
           my $pid = open3(gensym, \*PH, ">&NULL", "cmd");
           while( <PH> ) { }
           waitpid($pid, 0);

       To capture a program's STDERR, but discard its STDOUT:

           use IPC::Open3;
           use File::Spec;
           use Symbol qw(gensym);
           open(NULL, ">", File::Spec->devnull);
           my $pid = open3(gensym, ">&NULL", \*PH, "cmd");
           while( <PH> ) { }
           waitpid($pid, 0);

       To capture a program's STDERR, and let its STDOUT go to our own STDERR:

           use IPC::Open3;
           use Symbol qw(gensym);
           my $pid = open3(gensym, ">&STDERR", \*PH, "cmd");
           while( <PH> ) { }
           waitpid($pid, 0);

       To read both a command's STDOUT and its STDERR separately, you can
       redirect them to temp files, let the command run, then read the temp
       files:

           use IPC::Open3;
           use Symbol qw(gensym);
           use IO::File;
           local *CATCHOUT = IO::File->new_tempfile;
           local *CATCHERR = IO::File->new_tempfile;
           my $pid = open3(gensym, ">&CATCHOUT", ">&CATCHERR", "cmd");
           waitpid($pid, 0);
           seek $_, 0, 0 for \*CATCHOUT, \*CATCHERR;
           while( <CATCHOUT> ) {}
           while( <CATCHERR> ) {}

       But there's no real need for *both* to be tempfiles... the following
       should work just as well, without deadlocking:

           use IPC::Open3;
           use Symbol qw(gensym);
           use IO::File;
           local *CATCHERR = IO::File->new_tempfile;
           my $pid = open3(gensym, \*CATCHOUT, ">&CATCHERR", "cmd");
           while( <CATCHOUT> ) {}
           waitpid($pid, 0);
           seek CATCHERR, 0, 0;
           while( <CATCHERR> ) {}

       And it'll be faster, too, since we can begin processing the program's
       stdout immediately, rather than waiting for the program to finish.

        (file descriptor)

           open(STDOUT, ">logfile");
           system("ls");

        Bourne shell

           $output = `$cmd 2>some_file`;
           open (PIPE, "cmd 2>some_file |");

        STDERR  STDOUT

           $output = `$cmd 2>&1`;
           open (PIPE, "cmd 2>&1 |");

          STDERR  STDOUT  shell

           open(STDERR, ">&STDOUT");
           $alloutput = `cmd args`;  # stderr still escapes

       open()  STDERR  open()  STDOUT  STDOUT STDERR   STDOUT

          Bourne shell (sh(1))  csh(1) Perl  system() Bourne shell"Far More
       Than You Ever Wanted To Know"
       http://www.cpan.org/misc/olddoc/FMTEYEWTK.tgz .   STDERR  STDOUT:

           $output = `cmd 2>&1`;                       # either with backticks
           $pid = open(PH, "cmd 2>&1 |");              # or with an open pipe
           while (<PH>) { }                            #    plus a read

       To capture a command's STDOUT but discard its STDERR:

           $output = `cmd 2>/dev/null`;                # either with backticks
           $pid = open(PH, "cmd 2>/dev/null |");       # or with an open pipe
           while (<PH>) { }                            #    plus a read

       To capture a command's STDERR but discard its STDOUT:

           $output = `cmd 2>&1 1>/dev/null`;           # either with backticks
           $pid = open(PH, "cmd 2>&1 1>/dev/null |");  # or with an open pipe
           while (<PH>) { }                            #    plus a read

       To exchange a command's STDOUT and STDERR in order to capture the
       STDERR but leave its STDOUT to come out our old STDERR:

           $output = `cmd 3>&1 1>&2 2>&3 3>&-`;        # either with backticks
           $pid = open(PH, "cmd 3>&1 1>&2 2>&3 3>&-|");# or with an open pipe
           while (<PH>) { }                            #    plus a read

       To read both a command's STDOUT and its STDERR separately, it's easiest
       and safest to redirect them separately to files, and then read from
       those files when the program is done:

           system("program args 1>/tmp/program.stdout 2>/tmp/program.stderr");

       Ordering is important in all these examples.  That's because the shell
       processes file descriptor redirections in strictly left to right order.

           system("prog args 1>tmpfile 2>&1");
           system("prog args 2>&1 1>tmpfile");

       The first command sends both standard out and standard error to the
       temporary file.  The second command sends only the old standard output
       there, and the old standard error shows up on the old standard out.

        open()

       If the second argument to a piped open() contains shell metacharacters,
       perl fork()s, then exec()s a shell to decode the metacharacters and
       eventually run the desired program.  If the program couldn't be run,
       it's the shell that gets the message, not Perl. All your Perl program
       can find out is whether the shell itself could be successfully started.
       You can still capture the shell's STDERR and check it for error
       messages.  See "How can I capture STDERR from an external command?"
       elsewhere in this document, or use the IPC::Open3 module.

       If there are no shell metacharacters in the argument of open(), Perl
       runs the command directly, without using the shell, and can correctly
       report whether the command started.

       Perl  "system"

       Writing backticks in your program sends a clear message to the readers
       of your code that you wanted to collect the output of the command.  Why
       send a clear message that isn't true?

           `cat /etc/termcap`;

       ) $?

           print `cat /etc/termcap`;

           system("cat /etc/termcap") == 0
               or die "cat program failed!";

       system()  shell  (wildcard)

        shell

           @ok = `grep @opts '$search_string' @filenames`;

        Perl 5.8.0  open() system()  exec()  shell

          open( GREP, "-|", 'grep', @opts, $search_string, @filenames );
          chomp(@ok = <GREP>);
          close GREP;

           my @ok = ();
           if (open(GREP, "-|")) {
               while (<GREP>) {
                   chomp;
                   push(@ok, $_);
               }
               close GREP;
           } else {
               exec 'grep', @opts, $search_string, @filenames;
           }

        system() exec()  shell  perlipc  "Safe Pipe Opens"

       Note that if you're use Microsoft, no solution to this vexing issue is
       even possible.  Even if Perl were to emulate fork(), you'd still be
       stuck, because Microsoft does not have a argc/argv-style API.

        EOFUnix ^DMS-DOS ^Z STDIN

        stdio  set error  eof  POSIX  clearerr()

       1

               $where = tell(LOG);
               seek(LOG, $where, 0);

       2    seek()

       3    seek()

       4    stdio  sysread

        shell perl

        Perl  shell   Perl  shell->perl    shell  [pipeline datastream
       paradigm]

       perl telnet ftp

        Net::FTPTCP::Client  NET::Telnet CPAN
       http://www.perl.com/CPAN/scripts/netstuff/telnet.emul.shar  telnet
       Net::Telnet

        telnet  telnet

           use IO::Socket;             # new in 5.004
           $handle = IO::Socket::INET->new('www.perl.com:80')
                   || die "can't connect to port 80 on www.perl.com: $!";
           $handle->autoflush(1);
           if (fork()) {               # XXX: undef means failure
               select($handle);
               print while <STDIN>;    # everything from stdin to socket
           } else {
               print while <$handle>;  # everything from socket to stdout
           }
           close $handle;
           exit;

        Perl Expect

        chat2.pl perl   CPAN  Expect  CPAN  IO::Pty  IO::Stty.

        perl

        $0  perlvar  sendmail (daemons)

           $0 = "orcus [accepting connections]";

        perl script {}

       Unix
            script  shell    shell  shell  eval() script  comp.unix.questions
           FAQ

        kill TERM  KILL

        fork

        tty  Unix Unix  Your_OS::Process

       o    /dev/tty  TIOCNOTTY ioctl tty(4)  POSIX::setsid()

       o    /

       o    STDINSTDOUT  STDERR  tty

       o

               fork && exit;

       The Proc::Daemon module, available from CPAN, provides a function to
       perform these actions for you.

        "-t STDIN"N  "-t STDOUT"

           if (-t STDIN && -t STDOUT) {
               print "Now what? ";
           }

        POSIX

           use POSIX qw/getpgrp tcgetpgrp/;
           open(TTY, "/dev/tty") or die $!;
           $tpgrp = tcgetpgrp(fileno(*TTY));
           $pgrp = getpgrp();
           if ($tpgrp == $pgrp) {
               print "foreground\n";
           } else {
               print "background\n";
           }

        Signals  Camel  alarm()   CPAN  Sys::AlarmCall

       The alarm() function is not implemented on all versions of Windows.
       Check the documentation for your specific version of Perl.

        CPU ?

        CPAN  BSD::Resource

        Unix

        Signals  reaper  SIGCHLD  wait() perlfaq8  "How do I start a process
       in the background?"  fork

        SQL ?

       The DBI module provides an abstract interface to most database servers
       and types, including Oracle, DB2, Sybase, mysql, Postgresql, ODBC, and
       flat files.  The DBI module accesses each database type through a
       database driver, or DBD.  You can see a complete list of available
       drivers on CPAN: http://www.cpan.org/modules/by-module/DBD/ .  You can
       read more about DBI on http://dbi.perl.org .

       Other modules provide more specific access: Win32::ODBC, Alzabo, iodbc,
       and others found on CPAN Search: http://search.cpan.org .

        system()  control-C ?

        system()  perlipc  INT

           $rc = system($cmd);
           if ($rc & 127) { die "signal death" }

        Unix   Fcntl  O_NDELAY  O_NONBLOCK  sysopen()

           use Fcntl;
           sysopen(FH, "/tmp/somefile", O_WRONLY|O_NDELAY|O_CREAT, 0644)
               or die "can't open /tmp/somefile: $!":

       How do I install a module from CPAN?

        CPAN  5.004

           $ perl -MCPAN -e shell

           cpan shell -- CPAN exploration and modules installation (v1.59_54)
           ReadLine support enabled

           cpan> install Some::Module

        CPAN  CPAN

       1

       2
               perl Makefile.PL

       3
               make

       4
               make test

       5
               make install

        perl  (make) make perl  perl

        ExtUtils::MakeMaker require  use

       require  use

       Perl offers several different ways to include code from one file into
       another.  Here are the deltas between the various inclusion constructs:

           1)  do $file is like eval `cat $file`, except the former
               1.1: searches @INC and updates %INC.
               1.2: bequeaths an *unrelated* lexical scope on the eval'ed code.

           2)  require $file is like do $file, except the former
               2.1: checks for redundant loading, skipping already loaded files.
               2.2: raises an exception on failure to find, compile, or execute $file.

           3)  require Module is like require "Module.pm", except the former
               3.1: translates each "::" into your system's directory separator.
               3.2: primes the parser to disambiguate class Module as an indirect object.

           4)  use Module is like require Module, except the former
               4.1: loads the module at compile time, not run-time.
               4.2: imports symbols and semantics from that package to the current one.

       In general, you usually want "use" and a proper Perl module.

       /

        Makefiles  PREFIX

           perl Makefile.PL PREFIX=/mydir/perl LIB=/mydir/perl/lib

          PERL5LIB  perlrun

           use lib '/mydir/perl/lib';

           BEGIN {
               unshift(@INC, '/mydir/perl/lib');
           }

        lib  Perl  lib

       /

           use FindBin;
           use lib "$FindBin::Bin";
           use your_own_modules;

        include  (@INC)

            PERLLIB
            PERL5LIB
           perl -Idir
           use lib
               use lib "$ENV{HOME}/myown_perllib";

       lib.pm  5.002   Perl

        socket.ph

       It's a perl4-style file defining values for system networking
       constants.  Sometimes it is built using h2ph when Perl is installed,
       but other times it is not.  Modern programs "use Socket;" instead.

AUTHOR AND COPYRIGHT

       Copyright (c) 1997-2003 Tom Christiansen and Nathan Torkington.  All
       rights reserved.

       This documentation is free; you can redistribute it and/or modify it
       under the same terms as Perl itself.

       Irrespective of its distribution, all code examples in this file are
       hereby placed into the public domain.  You are permitted and encouraged
       to use this code in your own programs for fun or for profit as you see
       fit.  A simple comment in the code giving credit would be courteous but
       is not required.