diff options
author | Larry Wall <lwall@netlabs.com> | 1993-10-07 23:00:00 +0000 |
---|---|---|
committer | Larry Wall <lwall@netlabs.com> | 1993-10-07 23:00:00 +0000 |
commit | 79072805bf63abe5b5978b5928ab00d360ea3e7f (patch) | |
tree | 96688fcd69f9c8d2110e93c350b4d0025eaf240d /faq | |
parent | e334a159a5616cab575044bafaf68f75b7bb3a16 (diff) | |
download | perl-79072805bf63abe5b5978b5928ab00d360ea3e7f.tar.gz |
perl 5.0 alpha 2perl-5a2
[editor's note: from history.perl.org. The sparc executables
originally included in the distribution are not in this commit.]
Diffstat (limited to 'faq')
-rw-r--r-- | faq | 2102 |
1 files changed, 2102 insertions, 0 deletions
@@ -0,0 +1,2102 @@ +Archive-name: perl-faq/part0 +Version: $Id: faq,v 1.1 92/11/30 05:12:22 tchrist Exp Locker: tchrist $ + +This article contains the table of contents to some of the most +frequently asked questions in comp.lang.perl, a newsgroup devoted to +the Perl programming language. There are two pieces following +this, the general information questions in part1 and the largely +technical opnes in part2. + +They're all good questions, but they come up often enough that +substantial net bandwidth can be saved by looking here first before +asking. Before posting a question, you really should consult the Perl +man page; there's a lot of information packed in there. + +Some questions in this group aren't really about Perl, but rather +about system-specific issues. You might also consult the Most +Frequently Asked Questions list in comp.unix.questions for answers +to this type of question. + +The current version of perl is 4.035 (version 4, patchlevel 35). +There haven't actually been 35 updates to perl4; rather, the context +diffs posted to the net have been broken up into 35 news-digestable +chunks. + +This list is maintained by Tom Christiansen, and is archived on +convex.com [130.168.1.1] in the file pub/perl/info/faq. If you +have any suggested additions or corrections to this article, please +send them to Tom at either <tchrist@convex.com> or <convex!tchrist>. +Special thanks to Larry Wall for initially reviewing this list for +accuracy and especially for writing and releasing Perl in the first place. + + +1.1) What is Perl? +1.2) Is Perl hard to learn? +1.3) Should I program everything in Perl? +1.4) Where can I get Perl over the Internet? +1.5) Where can I get Perl via Email? +1.6) How can I get Perl via UUCP? +1.7) Where can I get more information on Perl? +1.8) Can people who aren't on USENET receive comp.lang.perl as a digest? +1.9) Are archives of comp.lang.perl available? +1.10) How do I get Perl to run on machine FOO? +1.11) Where can I get (info|inter|ora|sql|syb)perl? +1.12) There's an a2p and an s2p; why isn't there a p2c (perl-to-C)? +1.13) Where can I get undump for my machine? +1.14) Where can I get a perl-mode for emacs? +1.15) How can I use Perl interactively? +1.16) Is there a Perl shell? +1.17) Is there a Perl profiler? +1.18) Is there a yacc for Perl? +1.19) How can I use curses with perl? +1.20) How can I use X with Perl? +1.21) What is perl4? What is perl5? +1.22) How does Perl compare with languages like REXX or TCL? +1.23) Is it a Perl program or a Perl script? +1.24) What's the difference between "Perl" and "perl"? +1.25) What companies use or ship Perl? +1.26) Is there commercial, 3rd-party support for Perl? +1.27) Where can I get a list of the JAPH signature quotes? +1.28) Where can I get a list of Larry Wall witticisms? + +2.1) What are all these $@*%<> signs and how do I know when to use them? +2.2) Why don't backticks work as they do in shells? +2.3) How come Perl operators have different precedence than C operators? +2.4) How come my converted awk/sed/sh script runs more slowly in Perl? +2.5) How can I call my system's unique C functions from Perl? +2.6) Where do I get the include files to do ioctl() or syscall()? +2.7) Why doesn't "local($foo) = <FILE>;" work right? +2.8) How can I detect keyboard input without reading it? +2.9) How can I make an array of arrays or other recursive data types? +2.10) How can I quote a variable to use in a regexp? +2.11) Why do setuid Perl scripts complain about kernel problems? +2.12) How do I open a pipe both to and from a command? +2.13) How can I change the first N letters of a string? +2.14) How can I manipulate fixed-record-length files? +2.15) How can I make a file handle local to a subroutine? +2.16) How can I extract just the unique elements of an array? +2.17) How can I call alarm() or usleep() from Perl? +2.18) How can I test whether an array contains a certain element? +2.19) How can I do an atexit() or setjmp()/longjmp() in Perl? +2.20) Why doesn't Perl interpret my octal data octally? +2.21) How do I sort an associative array by value instead of by key? +2.22) How can I capture STDERR from an external command? +2.23) Why doesn't open return an error when a pipe open fails? +2.24) How can I compare two date strings? +2.25) What's the fastest way to code up a given task in perl? +2.26) How can I know how many entries are in an associative array? +2.27) Why can't my perl program read from STDIN after I gave it ^D (EOF) ? +2.28) Do I always/never have to quote my strings or use semicolons? +2.29) How can I translate tildes in a filename? +2.30) How can I convert my shell script to Perl? +2.31) What is variable suicide and how can I prevent it? +2.32) Can I use Perl regular expressions to match balanced text? +2.33) Can I use Perl to run a telnet or ftp session? +2.34) What does "Malformed command links" mean? + + + +1.1) What is Perl? + + A programming language, by Larry Wall <lwall@netlabs.com>. + + Here's the beginning of the description from the man page: + + Perl is an interpreted language optimized for scanning arbitrary text + files, extracting information from those text files, and printing reports + based on that information. It's also a good language for many system + management tasks. The language is intended to be practical (easy to use, + efficient, complete) rather than beautiful (tiny, elegant, minimal). It + combines (in the author's opinion, anyway) some of the best features of C, + sed, awk, and sh, so people familiar with those languages should have + little difficulty with it. (Language historians will also note some + vestiges of csh, Pascal, and even BASIC-PLUS.) Expression syntax + corresponds quite closely to C expression syntax. Unlike most Unix + utilities, Perl does not arbitrarily limit the size of your data--if + you've got the memory, Perl can slurp in your whole file as a single + string. Recursion is of unlimited depth. And the hash tables used by + associative arrays grow as necessary to prevent degraded performance. + Perl uses sophisticated pattern matching techniques to scan large amounts + of data very quickly. Although optimized for scanning text, Perl can also + deal with binary data, and can make dbm files look like associative arrays + (where dbm is available). Setuid Perl scripts are safer than C programs + through a dataflow tracing mechanism which prevents many stupid security + holes. If you have a problem that would ordinarily use sed or awk or sh, + but it exceeds their capabilities or must run a little faster, and you + don't want to write the silly thing in C, then Perl may be for you. There + are also translators to turn your sed and awk scripts into Perl scripts. + + +1.2) Is Perl hard to learn? + + No, Perl is easy to learn for two reasons. + + The first reason is that most of Perl is derived from existing tools + and languages, ones that many people who turn to Perl already have + some familiarity with. These include the C programming language, the + UNIX C library, the UNIX shell, sed, and awk. If you already know + these somewhat, Perl should be very easy for you. + + The second reason that Perl is easy to learn is that you don't have to + know every thing there is to know about it in order to get good use + out of it. In fact, just a very small subset, mostly borrowed from C, + the shell, and sed, will be enough for most tasks. As you feel the + need or desire to use more sophisticated features (such as C + structures or networking), you can learn these as you go. The + learning curve for Perl is not a steep one, especially if you have + the headstart of having a background in UNIX. Rather, its learning + curve is gentle and gradual, but it *is* admittedly rather long. + + If you don't know C or UNIX at all, it'll be a steeper learning curve, + but what you then learn from Perl will carry over into other areas, + like using the C library, UNIX system call, regular expressions, and + associative arrays, just to name a few. To know Perl is to know + UNIX, and vice versa. + + +1.3) Should I program everything in Perl? + + Of course not. You should choose the appropriate tool for the task at + hand. While it's true that the answer to the question "Can I do (some + arbitrary task) in Perl?" is almost always "yes", that doesn't mean + this is necessarily a good thing to do. For many people, Perl serves + as a great replacement for shell programming. For a few people, it + also serves as a replacement for most of what they'd do in C. But + for some things, Perl just isn't the optimal choice, such as tasks + requiring very complex data structures. + + +1.4) Where can I get Perl over the Internet? + + From any comp.sources.misc archive. Initial sources were posted to + Volume 18, Issues 19-54 at patchlevel 3. The Patches 4-10 were posted + to Volume 20, Issues 56-62. You can use the archie server + (see the alt.sources FAQ in news.answers) for ways to find these. + + These machines, at the very least, definitely have it available for + anonymous FTP: + + ftp.uu.net 137.39.1.2 + archive.cis.ohio-state.edu 128.146.8.52 + jpl-devvax.jpl.nasa.gov 128.149.1.143 + ftp.netlabs.com 192.94.48.152 + prep.ai.mit.edu 18.71.0.38 + archive.cs.ruu.nl 131.211.80.5 (Europe) + + + + +1.5) Where can I get Perl via Email? + + If you are in Europe, you might using the following site. (I'm still + looking for a domestic site.) This information thanks to "Henk P. + Penning" <henkp@cs.ruu.nl>: One automated fashion is as follows: + + Email: Send a message to 'mail-server@cs.ruu.nl' containing: + begin + path your_email_address + send help + send PERL/INDEX + end + The path-line may be omitted if your message contains a normal From:-line. + You will receive a help-file and an index of the directory that contains + the Perl stuff. + + If all else fails, mail to Larry usually suffices. + + +1.6) How can I get Perl via UUCP? + + You can get it from the site osu-cis; here is the appropriate info, + thanks to J Greely <jgreely@cis.ohio-state.edu> or <osu-cis!jgreely>. + + E-mail contact: + osu-cis!uucp + Get these two files first: + osu-cis!~/GNU.how-to-get. + osu-cis!~/ls-lR.Z + Current Perl distribution: + osu-cis!~/perl/4.0/kits@10/perl.kitXX.Z (XX=01-37) + How to reach osu-cis via uucp(L.sys/Systems file lines): + # + # Direct Trailblazer + # + osu-cis Any ACU 19200 1-614-292-5112 in:--in:--in: Uanon + # + # Direct V.32 (MNP 4) + # dead, dead, dead...sigh. + # + #osu-cis Any ACU 9600 1-614-292-1153 in:--in:--in: Uanon + # + # Micom port selector, at 1200, 2400, or 9600 bps. + # Replace ##'s below with 12, 24, or 96 (both speed and phone number). + # + osu-cis Any ACU ##00 1-614-292-31## "" \r\c Name? osu-cis nected \c GO \d\r\d\r\d\r in:--in:--in: + Uanon + + Modify as appropriate for your site, of course, to deal with your + local telephone system. There are no limitations concerning the hours + of the day you may call. + + Another possibility is to use UUNET, although they charge you + for it. You have been duly warned. Here's the advert: + + Anonymous Access to UUNET's Source Archives + + 1-900-GOT-SRCS + + UUNET now provides access to its extensive collection of UNIX + related sources to non- subscribers. By calling 1-900-468-7727 + and using the login "uucp" with no password, anyone may uucp any + of UUNET's on line source collection. Callers will be charged 40 + cents per minute. The charges will appear on their next tele- + phone bill. + + The file uunet!/info/help contains instructions. The file + uunet!/index//ls-lR.Z contains a complete list of the files available + and is updated daily. Files ending in Z need to be uncompressed + before being used. The file uunet!~/compress.tar is a tar + archive containing the C sources for the uncompress program. + + This service provides a cost effective way of obtaining + current releases of sources without having to maintain accounts + with UUNET or some other service. All modems connected to the + 900 number are Telebit T2500 modems. These modems support all + standard modem speeds including PEP, V.32 (9600), V.22bis (2400), + Bell 212a (1200), and Bell 103 (300). Using PEP or V.32, a 1.5 + megabyte file such as the GNU C compiler would cost $10 in con- + nect charges. The entire 55 megabyte X Window system V11 R4 + would cost only $370 in connect time. These costs are less than + the official tape distribution fees and they are available now + via modem. + + UUNET Communications Services + 3110 Fairview Park Drive, Suite 570 + Falls Church, VA 22042 + +1 703 876 5050 (voice) + +1 703 876 5059 (fax) + info@uunet.uu.net + + + +1.7) Where can I get more information on Perl? + + We'll cover five areas here: USENET (where you're probably reading + this), publications, the reference guide, examples on the Internet, + and Perl instructional courses. + + A. USENET + + You should definitely read the USENET comp.lang.perl newsgrouor + mailing list for all sorts of discussions regarding the language, + bugs, features, history, humor, and trivia. In this respect, it + functions both as a comp.lang.* style newsgroup and also as a user + group for the language; in fact, there's a mailing list called + ``perl-users'' that is bidirectionally gatewayed to the newsgroup; see + question #38 for details. Larry Wall is a very frequent poster here, + as well as many (if not most) of the other seasoned Perl programmers. + It's the best place for the very latest information on Perl. + + B. PUBLICATIONS + + If you've been dismayed by the ~80-page troffed Perl man page (or is + that man treatise?) you should look to ``the Camel Book'', written by + Larry and Randal L. Schwartz <merlyn@ora.com>, published as a Nutshell + Handbook by O'Reilly & Associates and entitled _Programming Perl_. + Besides serving as a reference guide for Perl, it also contains + tutorial material and is a great source of examples and cookbook + procedures, as well as wit and wisdom, tricks and traps, pranks and + pitfalls. The code examples contained therein are available via + anonymous FTP from ftp.uu.net in + /published/oreilly/nutshell/perl/perl.tar.Z for your retrieval. + Corrections and additions to the book can be found in the Perl man + page right before the BUGS section under the heading ERRATA AND + ADDENDA. + + If you can't find the book in your local technical bookstore, the book + may be ordered directly from O'Reilly by calling 1-800-998-9938 if in + North America and 1-707-829-0515. Autographed copies are available + from TECHbooks by calling 1-503-646-8257 or mailing info@techbook.com. + Cost is ~30$US for the regular version, 40$US for the autographed one. + The book's ISBN is 0-937175-64-1. + + Reasonably substantiated rumor has it that there will be another Perl + book out pretty soon, this one aimed more at beginners. Look for it + from ORA towards the beginning of 93. + + Larry Wall has published a 3-part article on perl in Unix World + (August through October of 1991), and Rob Kolstad also had a 3-parter + in Unix Review (May through July of 1990). Tom Christiansen also has + a brief overview article in the trade newsletter Unix Technology + Advisor from November of 1989. You might also investigate "The Wisdom + of Perl" by Gordon Galligher from SunExpert magazine; April 1991 + Volume 2 Number 4. + + The USENIX LISA (Large Installations Systems Adminstration) Conference + have for several years now included many papers of tools written in + Perl. Old proceedings of these conferences are available; look in + your current issue of ";login:" or send mail to office@usenix.org + for futher information. + + C. INTERNET + + For other examples of Perl scripts, look in the Perl source directory in + the eg subdirectory. You can also find a good deal of them on + tut.cis.ohio-state.edu in the pub/perl/scripts/ subdirectory. + + Another source for examples, currently only for anonymous FTP, is on + convex.com [130.168.1.1]. This contains, amongst other things, + a copy of the newsgroup up through Aug 91, a text retrieval database + for the newsgroup, a rather old and short troff version of Tom Christiansen's + perl tutorial (this was the version presented at Washington DC USENIX), + and quite a few of Tom's scripts. You can look at the INDEX file + in /pub/perl/INDEX for a list of what's in that directory. + + The Convex and Ohio State archives are mirrored on uunet + in /languages/perl/scripts-{convex,osu}. + + D. REFERENCE GUIDE + + A nice reference guide by Johan Vromans <jv@mh.nl> is also available; + It is distributed in LaTeX (source) and PostScript (ready to + print) forms. Obsolete versions may still be available in TeX and troff + forms, although these don't print as nicely. The official kit + includes both LaTeX and PostScript forms, and can be FTP'd from + archive.cs.ruu.nl [131.211.80.5], file /pub/DOC/perlref-4.035.tar.Z. + The reference guide comes with the O'Reilly book in a nice, glossy + card format. + + E. PERL COURSES + + Various technical conferences, including USENIX, SUG, WCSAS, AUUG, + FedUnix, and Europen have been sponsoring tutorials of varying lengths + on Perl at their system administration and general conferences. You + might consider attending one of these. These classes are typically + taught by Tom Christiansen <tchrist@usenix.com>, although both Rob + Kolstad <kolstad@usenix.org> and Randal Schwartz <merlyn@ora.com> also + teach Perl on occasion. Special appearances by Tom, Rob, and/or + Randal may also be negotiated. Classes can run from one day up to a + week ranging over a wide range of subject matter (most are two or + three days), and can include lab time if you want; having lab time + with exercises is generally of great benefit. Send us mail if your + organization is interested in having a Perl class taught at your site. + + +1.8) Can people who aren't on USENET receive comp.lang.perl as a digest? + + "Perl-Users" is the mailing list version of the comp.lang.perl + newsgroup. If you're not lucky enough to be on USENET you can post to + comp.lang.perl by sending to one of the following addresses. Which one + will work best for you depends on which nets your site is hooked into. + Ask your local network guru if you're not certain. + + Internet: PERL-USERS@VIRGINIA.EDU + Perl-Users@UVAARPA.VIRGINIA.EDU + + BitNet: Perl@Virginia + + uucp: ...!uunet!virginia!perl-users + + The Perl-Users list is bidirectionally gatewayed with the USENET + newsgroup comp.lang.perl. This means that VIRGINIA functions as a + reflector. All traffic coming in from the non-USENET side is + immediately posted to the newsgroup. Postings from the USENET side are + periodically digested and mailed out to the Perl-Users mailing list. A + digest is created and distributed at least once per day, more often if + traffic warrants. + + All requests to be added to or deleted from this list, problems, + questions, etc., should be sent to: + + Internet: Perl-Users-Request@Virginia.EDU + Perl-Users-Request@uvaarpa.Virginia.EDU + + BitNet: Perl-Req@Virginia + + uucp: ...!uunet!virginia!perl-users-request + + Coordinator: Marc Rouleau <mer6g@VIRGINIA.EDU> + +1.9) Are archives of comp.lang.perl available? + + Yes, although they're poorly organized. You can get them from + the host betwixt.cs.caltech.edu (131.215.128.4) in the directory + /pub/comp.lang.perl. They are also to uunet in + /languages/perl/comp.lang.perl . It contains these things: + + comp.lang.perl.tar.Z -- the 5M tarchive in MH/news format + archives/ -- the unpacked 5M tarchive + unviewed/ -- new comp.lang.perl messages + + These are currently stored in news- or MH-style format; there are + subdirectories named things like "arrays", "programs", "taint", and + "emacs". Unfortunately, only the first ~1600 or so messages have been + so categorized, and we're now up to almost 15000. Furthermore, even + this categorization was haphazardly done and contains errors. + + A more sophisticated query and retrieval mechanism is desirable. + Preferably one that allows you to retrieve article using a fast-access + indices, keyed on at least author, date, subject, thread (as in "trn") + and probably keywords. Right now, the MH pick command works for this, + but it is very slow to select on 15000 articles. + + If you're serious about this, your best bet is probably to retrieve + the compressed tarchive and play with what you get. Any suggestions + how to better sort this all out are extremely welcome. + + Currently the comp.lang.perl archives on convex.com are nearly a year + behind. That's because I no longer have room to store them there. I + do have them all on-line still, but they are not publicly accessible. + If you have a special request for a query on the old newsgroup + postings, and make nice noises in my direction, I can run the query + and send them to you. Algebraic queries are like "find me anything + about this and that and the other thing but not this or whozits". I + hope to put this in the form of a mailserver. Donated software would + be fine. :-) + + The fast text-retrieval query system for this I'm currently using is + Liam Quin's excellent lqtext system, available from ftp.toronto.edu + in /pub/lq-text* . + + Rumor has it that there are WAIS servers out there for comp.lang.perl + these days, but I haven't used them. + + +1.10) How do I get Perl to run on machine FOO? + + Perl comes with an elaborate auto-configuration script that allows Perl + to be painlessly ported to a wide variety of platforms, including many + non-UNIX ones. Amiga and MS-DOS binaries are available on + jpl-devvax.jpl.nasa.gov [128.149.1.143] for anonymous FTP. Try to bring + Perl up on your machine, and if you have problems, examine the README + file carefully, and if all else fails, post to comp.lang.perl; + probably someone out there has run into your problem and will be able + to help you. + + In particular, since they're so often asked about, here's some information + for the MacIntosh from Matthias Ulrich Neeracher <neeri@iis.ethz.ch>: + + A port of Perl to the Apple Macintosh is available by anonymous + ftp to rascal.ics.utexas.edu from the file + ~ftp/mac/programming/Perl_402_MPW_CPT_bin . + + The file is 1.1M and must be transferred in BINARY mode. Please + be considerate of RASCAL's users during CDT working hours. + (And, no, there is no way to get it by email). + + For European users, the file should soon appear on lth.se. + + To make optimal use of all the features of this port, you + should have MPW, ToolServer, and 5M of memory. There is also a + standalone version included, but it's currently of very limited + usefulness. + + This package contains all of the sources for compilation with + MPW C 3.2 + + And here's some VMS information from Rao V. Akella + <rao@moose.cccs.umn.edu>: (this appears to be an old port) + + You can pick up Perl for VMS (version 3.0.1.1 patchlevel 4) via + anonymous ftp from ftp.pitt.edu [130.49.253.1] in the + software/vms/perl subdirectory (there are two files there: + perl-pl18.bck and perl-pl4.bck). + + There is also a v3.018 on info.rz.uni-ulm.de [134.60.1.125] or + vms.huji.ac.il [128.139.4.3] in /pub/VMS/misc (information courtesy + of Anders Rolff <rolff@scotty.eurokom.ie>). + + And here is a recent version for MS-DOS from Budi Rahard + <rahard@ee.UManitoba.CA>, who says: + + I am collecting MS-DOS Perl(s) in ftp.ee.umanitoba.ca directory + /pub/msdos/perl. Currently I received three versions of Perl v4.019 + and one of 4.010. (Tommy Thorn <tthorn@daimi.aau.dk> and Len Reed + <holos0!lbr@gatech.edu>) + + There is now a 4.035 for 386 [DOS], Hitoshi Doi <doi@jrd.december.com> + port, is available ftp.ee.umanitoba.ca as /pub/msdos/perl/perl386.zoo . + + Please contact the porters directly in case of questions about + these ports. + + +1.11) Where can I get (info|inter|ora|sql|syb)perl? + + Numerous database-oriented extensions to Perl have been written. + These amount to using the usub mechanism (see the usub/ subdirectory + in the distribution tree) to link in a database library, allowing + embedded calls to Informix, Interbase, Oracle, Ingres, and Sybase. + There is currently a project underway, organized by Buzz Moschetti + <buzz@toxicavenger.bear.com>, to create a higher level interface + (DBperl) that will allow you to write your queries in a + database-independent fashion. Meanwhile, here are the authors of the + various extensions: + + What Target DB Who + -------- ----------- ---------------------------------------- + Infoperl Informix Kurt Andersen (kurt@hpsdid.sdd.hp.com) + Interperl Interbase Buzz Moschetti (buzz@fsrg.bear.com) + Oraperl Oracle Kevin Stock (kstock@encore.com) + Sqlperl Ingres Ted Lemon (mellon@ncd.com) + Sybperl Sybase Michael Peppler (mpeppler@itf.ch) + + +1.12) There's an a2p and an s2p; why isn't there a p2c (perl-to-C)? + + Because the Pascal people would be upset that we stole their name. :-) + + The dynamic nature of Perl's do and eval operators (and remember that + constructs like s/$mac_donald/$mac_gregor/eieio count as an eval) would + make this very difficult. To fully support them, you would have to put + the whole Perl interpreter into each compiled version for those scripts + using them. This is what undump does right now, if your machine has it. + If what you're doing will be faster in C than in Perl, maybe it should + have been written in C in the first place. For things that ought to be + written in Perl, the interpreter will be just about as fast, because the + pattern matching routines won't work any faster linked into a C program. + Even in the case of simple Perl programs that don't do any fancy evals, the + major gain would be in compiling the control flow tests, with the rest + still being a maze of twisty, turny subroutine calls. Since these are not + usually the major bottleneck in the program, there's not as much to be + gained via compilation as one might think. + + +1.13) Where can I get undump for my machine? + + The undump program comes from the TeX distribution. If you have TeX, then + you may have a working undump. If you don't, and you can't get one, + *AND* you have a GNU emacs working on your machine that can clone itself, + then you might try taking its unexec() function and compiling Perl with + -DUNEXEC, which will make Perl call unexec() instead of abort(). You'll + have to add unexec.o to the objects line in the Makefile. If you succeed, + post to comp.lang.perl about your experience so others can benefit from it. + + +1.14) Where can I get a perl-mode for emacs? + + In the perl4.0 source directory, you'll find a directory called + "emacs", which contains several files that should help you. + + +1.15) How can I use Perl interactively? + + The easiest way to do this is to run Perl under its debugger. + If you have no program to debug, you can invoke the debugger + on an `empty' program like this: + + perl -de 0 + + (The more positive amongst us prefer "perl -de 1". :-) + + Now you can type in any legal Perl code, and it will be immediately + evaluated. You can also examine the symbol table, get stack + backtraces, check variable Values, and if you want to, set + breakpoints and do the other things you can do in a symbolic debugger. + + +1.16) Is there a Perl shell? + + Not really. Perl is a programming language, not a command + interpreter. There is a very simple one called "perlsh" + included in the Perl source distribution. It just does this: + + $/ = ''; # set paragraph mode + $SHlinesep = "\n"; + while ($SHcmd = <>) { + $/ = $SHlinesep; + eval $SHcmd; print $@ || "\n"; + $SHlinesep = $/; $/ = ''; + } + + Not very interesting, eh? + + Daniel Smith <dansmith@autodesk.com> is working on an interactive Perl + shell called SoftList. It's currently at version 3.0beta. SoftList + 3.0 has tcsh-like command line editing, can let you define a file of + aliases so that you can run chunks of perl or UNIX commands, and so + on. You can send mail to him for further information and availability. + + +1.17) Is there a Perl profiler? + + While there isn't one included with the perl source distribution, + various folks have written packages that allow you to do at least some + sort of profiling. The strategy usually includes modifying the perl + debugger to handle profiling. Authors of these packages include + + Wayne Thompson <me@anywhere.EBay.Sun.COM> + Ray Lischner <lisch@sysserver1.mentor.com> + Kresten Krab Thorup <krab@iesd.auc.dk> + + The original articles by these folks containing their + profilers are available on convex.com in + /pub/perl/information/profiling.shar via anon ftp. + + +1.18) Is there a yacc for Perl? + + Yes!! It's a version of Berkeley yacc that outputs Perl code instead + of C code! You can get this from ftp.sterling.com [192.124.9.1] in + /local/perl-byacc1.8.1.tar.Z, or send the author mail for details. + + +1.19) How can I use curses with perl? + + One way is to build a curseperl binary by linking in your C curses + library as described in the usub subdirectory of the perl sources. + This requires a modicum of work, but it will be reasonably fast + since it's all in C (assuming you consider curses reasonably fast. :-) + Programs written using this method require the modified curseperl, + not vanilla perl, to run. While this is something of a disadvantage, + experience indicates that it's better to use curseperl than to + try to roll your own using termcap directly. + + Another possibility is to use Henk Penning's cterm package, a curses + emulation library written in perl. cterm is actually a separate + program with which you communicate via a pipe. It is available from + archive.cs.ruu.nl [131.211.80.5] via anonymous ftp in the directory + pub/PERL. You may also acquire the package via email in compressed, + uuencoded form by sending a message to mail-server@cs.ruu.nl + containing these lines: + + begin + send PERL/cterm.shar.Z + end + + See the question on retrieving perl via mail for more information on + how to get retrieve other items of interest from the mail server + there. + + +1.20) How can I use X with Perl? + + Right now, you have several choices. You can wait for perl5, use + the WAFE or STDWIN packages, or try to make your own usub bindings. + + Perl5 is anticipated to be released with bindings for X, called + guiperl. An exciting prototype for this, written by Jon Biggar + <jon@netlabs.com>, Larry's *other* brother-in-law and officemate, + is already up and running inside of Netlabs. This program addresses + the same dynamic gui-building problem space as does tcl/tk. + + If you can't wait or don't think that guiperl will do what you want, + a stab at Motif bindings was begun by Theodore C. Law + <TEDLAW@TOROLAB6.VNET.IBM.COM> area. His article about this is + on convex.com in /pub/perl/info/motif for anon ftp. + + STDWIN is a library written by Guido van Rossum <guido@cwi.nl> + (author of the Python programming language) that is portable + between Mac, Dos and X11. One could write a Perl agent to + speak to this STDIN server. + + WAFE is a package that implements a symbolic interface to the Athena + widgets (X11R5). A typical Wafe application consists in our framework + of two parts: the front-end (we call it Wafe for Widget[Athena]front + end) and an application program running typically as separate process. + The application program can be implemented in an arbitrary programming + language and talks to the front-end via stdio. Since Wafe (the + front-end) was developed using the extensible TCL shell (cite John + Ousterhout), an application program can dynamically submit requests to + the front-end to build up the graphical user interface; the + application can even down-load application specific procedures into + the front-end. The distribution contains sample application programs + in Perl, GAWK, Prolog, TCL, and C talking to the same Wafe binary. + Many of the demo applications are implemented in Perl. Wafe 0.9 can + be obtained via anonymous ftp from + ftp.wu-wien.ac.at:pub/src/X11/wafe-0.9.tar.Z + (for people without name server: the ip address is 137.208.3.5) + + +1.21) What is perl4? What is perl5? + + The answer to what is perl4 is nearly anything you might otherwise + program in shell or C. The answer to what is perl5 is basically + Perl: the Next Generation. In fact, it's essentially a complete + rewrite of perl from the bottom up, and back again. + + Larry gave a talk on perl5 at a Bay LISA meeting as well as at the + most recent USENIX LISA conference in Long Beach in which he timorously + admitted that perl5 might possibly be beta released in early 1993. + He enumerated some of the following features. Note that not only have + not all these been implemented yet, the ones further down the list + might well not get done at all. + + a faster, tighter, more flexible interpreter + very easy GUI Perl applications using X bindings ("guiperl") + embeddable Perl code in C code: cc prog.c -lperl + multiple coresident perl interpreters: + perhaps threading and/or coroutines + named argument passing: + some_func( OC => $red, TOF => "\f"); + recursive lists: + [a, b, [c, d], e] has 4 elts, the 3rd being itself a list + typed pointers and generalized indirection: + like @{$aptr} or &{$fptr} or &{ $table[$index] . "func" }(). + merging of list operator and function calling syntax: + split /pat/, $string; + subroutines without &'s: myfunc($arg); + generalization of dbm binding for assoc arrays to handle + any generic fetch/store/open/close/flush package. + (thus allowing both dbm and gdbm at once) + object oriented programming: + STDOUT->flush(1); + give dog $bone; + lexical scoping + dynamic loading of C libraries for systems that can + byte-compiled code for speed and maybe security + + It's tempting to want this stuff soon, since the sooner it comes + out the sooner we can all build really cool applications. But the + longer Larry works on it, the more items from this list will actually + get done, and the more robust the release will be. So let's not + ask him about it too often. + + +1.22) How does Perl compare with languages like REXX or TCL? + + REXX is an interpreted programming language first seen on IBM systems, + and TCL is John Ousterhout's embeddable command language. TCL's most + intriguing feature for many people is the tcl/tk toolset that allows + for interpreted X-based tools. + + To avoid any flamage, if you really want to know the answer to this + question, probably the best thing to do is try to write equivalent + code to do a set of tasks. All three have their own newsgroups in + which you can learn about (but hopefully not argue about) these + languages. + + To find out more about these or other languages, you might also check + out David Muir Sharnoff <muir@tfs.com>'s posting on "Catalog of + compilers, interpreters, and other language tools" which he posts to + comp.lang.misc, comp.sources.d, comp.archives.admin, and the + news.answers newsgroups. It's a comprehensive treatment of many + different languages. (Caveat lector: he considers Perl's syntax + "unappealing".) This list is archived on convex.com in + /pub/perl/info/lang-survey.shar . + + +1.23) Is it a Perl program or a Perl script? + + Certainly. :-) + + Current UNIX parlance holds that anything interpreted + is a script, and anything compiled into native machine + code is a program. However, others hold that a program + is a program is a program: after all, one seldom discusses + scripts written in BASIC or LISP. Larry considers it + a program if it's set in stone and you can't change it, + whereas if you go in and hack on it, then it's a script. + + But doesn't really matter. The terms are generally + interchangeable today. + + +1.24) What's the difference between "Perl" and "perl"? + + 32 :-) [ ord('p') - ord('P') ] + + Larry now uses "Perl" to signify the language proper and "perl" the + implementation of it, i.e. the current interpreter. Hence my quip + that "Nothing but perl can parse Perl." + + On the other hand, the aesthetic value of casewise parallelism + in "awk", "sed", and "perl" as much require the lower-case + version as "C", "Pascal", and "Perl" require the + upper-case version. It's also easier to type "Perl" in + typeset print than to be constantly switching in Courier. :-) + + In other words, it doesn't matter much, especially if all + you're doing is hearing someone talk about the language; + case is hard to distingish aurally. + + +1.25) What companies use or ship Perl? + + At this time, the known list includes at least the following: Convex, + Netlabs, BSDI, Integraph, Dell, and Kubota Pacific, although the + latter is in /usr/contrib only. Many other companies use Perl + internally for purposes of tools development, systems administration, + installation scripts, and test suites. Rumor has it that the large + workstation vendors (the TLA set) are seriously looking into shipping + Perl with their standard systems "soon". + + People with support contracts with their vendors are actively + encouraged to submit enhancement requests that Perl be shipped + as part of their standard system. It would, at the very least, + reduce the FTP load on the Internet. :-) + +1.26) Is there commercial, 3rd-party support for Perl? + + No. Although perl is included in the GNU distribution, at last check, + Cygnus does not offer support for it. However, it's unclear whether + they've ever been offered sufficient financial incentive to do so. + + On the other hand, you do have comp.lang.perl as a totally gratis + support mechanism. As long as you ask "interesting" questions, + you'll probably get plenty of help. :-) + +1.27) Where can I get a list of the JAPH signature quotes? + + These are the "just another perl hacker" signatures that + some people sign their postings with. About 100 of the + of the earlier ones are on convex.com in /pib/perl/info/japh. + +1.28) Where can I get a list of Larry Wall witticisms? + + Over a hundred quips by Larry, from postings of his or source code, + can be found on convex.com in /pub/perl/info/lwall-quotes. + + + + +2.1) What are all these $@*%<> signs and how do I know when to use them? + + Those are type specifiers: $ for scalar values, @ for indexed arrays, + and % for hashed arrays. The * means all types of that symbol name + and are sometimes used like pointers; the <> are used for inputting + a record from a filehandle. See the question on arrays of arrays + for more about Perl pointers. + + Always make sure to use a $ for single values and @ for multiple ones. + Thus element 2 of the @foo array is accessed as $foo[2], not @foo[2], + which is a list of length one (not a scalar), and is a fairly common + novice mistake. Sometimes you can get by with @foo[2], but it's + not really doing what you think it's doing for the reason you think + it's doing it, which means one of these days, you'll shoot yourself + in the foot; ponder for a moment what these will really do: + @foo[0] = `cmd args`; + @foo[2] = <FILE>; + Just always say $foo[2] and you'll be happier. + + This may seem confusing, but try to think of it this way: you use the + character of the type which you *want back*. You could use @foo[1..3] for + a slice of three elements of @foo, or even @foo{A,B,C} for a slice of + of %foo. This is the same as using ($foo[1], $foo[2], $foo[3]) and + ($foo{A}, $foo{B}, $foo{C}) respectively. In fact, you can even use + lists to subscript arrays and pull out more lists, like @foo[@bar] or + @foo{@bar}, where @bar is in both cases presumably a list of subscripts. + + While there are a few places where you don't actually need these type + specifiers, except for files, you should always use them. Note that + <FILE> is NOT the type specifier for files; it's the equivalent of awk's + getline function, that is, it reads a line from the handle FILE. When + doing open, close, and other operations besides the getline function on + files, do NOT use the brackets. + + Beware of saying: + $foo = BAR; + Which wil be interpreted as + $foo = 'BAR'; + and not as + $foo = <BAR>; + If you always quote your strings, you'll avoid this trap. + + Normally, files are manipulated something like this (with appropriate + error checking added if it were production code): + + open (FILE, ">/tmp/foo.$$"); + print FILE "string\n"; + close FILE; + + If instead of a filehandle, you use a normal scalar variable with file + manipulation functions, this is considered an indirect reference to a + filehandle. For example, + + $foo = "TEST01"; + open($foo, "file"); + + After the open, these two while loops are equivalent: + + while (<$foo>) {} + while (<TEST01>) {} + + as are these two statements: + + close $foo; + close TEST01; + + but NOT to this: + + while (<$TEST01>) {} # error + ^ + ^ note spurious dollar sign + + This is another common novice mistake; often it's assumed that + + open($foo, "output.$$"); + + will fill in the value of $foo, which was previously undefined. + This just isn't so -- you must set $foo to be the name of a valid + filehandle before you attempt to open it. + + +2.2) Why don't backticks work as they do in shells? + + Several reason. One is because backticks do not interpolate within + double quotes in Perl as they do in shells. + + Let's look at two common mistakes: + + $foo = "$bar is `wc $file`"; # WRONG + + This should have been: + + $foo = "$bar is " . `wc $file`; + + But you'll have an extra newline you might not expect. This + does not work as expected: + + $back = `pwd`; chdir($somewhere); chdir($back); # WRONG + + Because backticks do not automatically eat trailing or embedded + newlines. The chop() function will remove the last character from + a string. This should have been: + + chop($back = `pwd`); chdir($somewhere); chdir($back); + + You should also be aware that while in the shells, embedding + single quotes will protect variables, in Perl, you'll need + to escape the dollar signs. + + Shell: foo=`cmd 'safe $dollar'` + Perl: $foo=`cmd 'safe \$dollar'`; + + +2.3) How come Perl operators have different precedence than C operators? + + Actually, they don't; all C operators have the same precedence in Perl as + they do in C. The problem is with a class of functions called list + operators, e.g. print, chdir, exec, system, and so on. These are somewhat + bizarre in that they have different precedence depending on whether you + look on the left or right of them. Basically, they gobble up all things + on their right. For example, + + unlink $foo, "bar", @names, "others"; + + will unlink all those file names. A common mistake is to write: + + unlink "a_file" || die "snafu"; + + The problem is that this gets interpreted as + + unlink("a_file" || die "snafu"); + + To avoid this problem, you can always make them look like function calls + or use an extra level of parentheses: + + (unlink "a_file") || die "snafu"; + unlink("a_file") || die "snafu"; + + Sometimes you actually do care about the return value: + + unless ($io_ok = print("some", "list")) { } + + Yes, print() return I/O success. That means + + $io_ok = print(2+4) * 5; + + reutrns 5 times whether printing (2+4) succeeded, and + print(2+4) * 5; + returns the same 5*io_success value and tosses it. + + See the Perl man page's section on Precedence for more gory details, + and be sure to use the -w flag to catch things like this. + + +2.4) How come my converted awk/sed/sh script runs more slowly in Perl? + + The natural way to program in those languages may not make for the fastest + Perl code. Notably, the awk-to-perl translator produces sub-optimal code; + see the a2p man page for tweaks you can make. + + Two of Perl's strongest points are its associative arrays and its regular + expressions. They can dramatically speed up your code when applied + properly. Recasting your code to use them can help alot. + + How complex are your regexps? Deeply nested sub-expressions with {n,m} or + * operators can take a very long time to compute. Don't use ()'s unless + you really need them. Anchor your string to the front if you can. + + Something like this: + next unless /^.*%.*$/; + runs more slowly than the equivalent: + next unless /%/; + + Note that this: + next if /Mon/; + next if /Tue/; + next if /Wed/; + next if /Thu/; + next if /Fri/; + runs faster than this: + next if /Mon/ || /Tue/ || /Wed/ || /Thu/ || /Fri/; + which in turn runs faster than this: + next if /Mon|Tue|Wed|Thu|Fri/; + which runs *much* faster than: + next if /(Mon|Tue|Wed|Thu|Fri)/; + + There's no need to use /^.*foo.*$/ when /foo/ will do. + + Remember that a printf costs more than a simple print. + + Don't split() every line if you don't have to. + + Another thing to look at is your loops. Are you iterating through + indexed arrays rather than just putting everything into a hashed + array? For example, + + @list = ('abc', 'def', 'ghi', 'jkl', 'mno', 'pqr', 'stv'); + + for $i ($[ .. $#list) { + if ($pattern eq $list[$i]) { $found++; } + } + + First of all, it would be faster to use Perl's foreach mechanism + instead of using subscripts: + + foreach $elt (@list) { + if ($pattern eq $elt) { $found++; } + } + + Better yet, this could be sped up dramatically by placing the whole + thing in an associative array like this: + + %list = ('abc', 1, 'def', 1, 'ghi', 1, 'jkl', 1, + 'mno', 1, 'pqr', 1, 'stv', 1 ); + $found += $list{$pattern}; + + (but put the %list assignment outside of your input loop.) + + You should also look at variables in regular expressions, which is + expensive. If the variable to be interpolated doesn't change over the + life of the process, use the /o modifier to tell Perl to compile the + regexp only once, like this: + + for $i (1..100) { + if (/$foo/o) { + &some_func($i); + } + } + + Finally, if you have a bunch of patterns in a list that you'd like to + compare against, instead of doing this: + + @pats = ('_get.*', 'bogus', '_read', '.*exit', '_write'); + foreach $pat (@pats) { + if ( $name =~ /^$pat$/ ) { + &some_func(); + last; + } + } + + If you build your code and then eval it, it will be much faster. + For example: + + @pats = ('_get.*', 'bogus', '_read', '.*exit', '_write'); + $code = <<EOS + while () { + study; +EOS + foreach $pat (@pats) { + $code .= <<EOS + if ( /^$pat\$/ ) { + &some_func(); + next; + } +EOS + } + $code .= "}\n"; + print $code if $debugging; + eval $code; + + + +2.5) How can I call my system's unique C functions from Perl? + + If these are system calls and you have the syscall() function, then + you're probably in luck -- see the next question. For arbitrary + library functions, it's not quite so straight-forward. While you + can't have a C main and link in Perl routines, if you're + determined, you can extend Perl by linking in your own C routines. + See the usub/ subdirectory in the Perl distribution kit for an example + of doing this to build a Perl that understands curses functions. It's + neither particularly easy nor overly-documented, but it is feasible. + + +2.6) Where do I get the include files to do ioctl() or syscall()? + + These are generated from your system's C include files using the h2ph + script (once called makelib) from the Perl source directory. This will + make files containing subroutine definitions, like &SYS_getitimer, which + you can use as arguments to your function. + + You might also look at the h2pl subdirectory in the Perl source for how to + convert these to forms like $SYS_getitimer; there are both advantages and + disadvantages to this. Read the notes in that directory for details. + + In both cases, you may well have to fiddle with it to make these work; it + depends how funny-looking your system's C include files happen to be. + + If you're trying to get at C structures, then you should take a look + at using c2ph, which uses debugger "stab" entries generated by your + BSD or GNU C compiler to produce machine-independent perl definitions + for the data structures. This allows to you avoid hardcoding + structure layouts, types, padding, or sizes, greatly enhancing + portability. c2ph comes with the perl distribution. On an SCO + system, GCC only has COFF debugging support by default, so you'll have + to build GCC 2.1 with DBX_DEBUGGING_INFO defined, and use -gstabs to + get c2ph to work there. + + See the file /pub/perl/info/ch2ph on convex.com via anon ftp + for more traps and tips on this process. + + +2.7) Why doesn't "local($foo) = <FILE>;" work right? + + Well, it does. The thing to remember is that local() provides an array + context, an that the <FILE> syntax in an array context will read all the + lines in a file. To work around this, use: + + local($foo); + $foo = <FILE>; + + You can use the scalar() operator to cast the expression into a scalar + context: + + local($foo) = scalar(<FILE>); + + +2.8) How can I detect keyboard input without reading it? + + You should check out the Frequently Asked Questions list in + comp.unix.* for things like this: the answer is essentially the same. + It's very system dependent. Here's one solution that works on BSD + systems: + + sub key_ready { + local($rin, $nfd); + vec($rin, fileno(STDIN), 1) = 1; + return $nfd = select($rin,undef,undef,0); + } + + A closely related question is how to input a single character from the + keyboard. Again, this is a system dependent operation. The following + code that may or may not help you: + + $BSD = -f '/vmunix'; + if ($BSD) { + system "stty cbreak </dev/tty >/dev/tty 2>&1"; + } + else { + system "stty", 'cbreak', + system "stty", 'eol', "\001"; + } + + $key = getc(STDIN); + + if ($BSD) { + system "stty -cbreak </dev/tty >/dev/tty 2>&1"; + } + else { + system "stty", 'icanon'; + system "stty", 'eol', '^@'; # ascii null + } + print "\n"; + + You could also handle the stty operations yourself for speed if you're + going to be doing a lot of them. This code works to toggle cbreak + and echo modes on a BSD system: + + sub set_cbreak { # &set_cbreak(1) or &set_cbreak(0) + local($on) = $_[0]; + local($sgttyb,@ary); + require 'sys/ioctl.ph'; + $sgttyb_t = 'C4 S' unless $sgttyb_t; # c2ph: &sgttyb'typedef() + + ioctl(STDIN,&TIOCGETP,$sgttyb) || die "Can't ioctl TIOCGETP: $!"; + + @ary = unpack($sgttyb_t,$sgttyb); + if ($on) { + $ary[4] |= &CBREAK; + $ary[4] &= ~&ECHO; + } else { + $ary[4] &= ~&CBREAK; + $ary[4] |= &ECHO; + } + $sgttyb = pack($sgttyb_t,@ary); + + ioctl(STDIN,&TIOCSETP,$sgttyb) || die "Can't ioctl TIOCSETP: $!"; + } + + Note that this is one of the few times you actually want to use the + getc() function; it's in general way too expensive to call for normal + I/O. Normally, you just use the <FILE> syntax, or perhaps the read() + or sysread() functions. + + For perspectives on more portable solutions, use anon ftp to retrieve + the file /pub/perl/info/keypress from convex.com. + + +2.9) How can I make an array of arrays or other recursive data types? + + Remember that Perl isn't about nested data structures (actually, + perl0 .. perl4 weren't, but maybe perl5 will be, at least + somewhat). It's about flat ones, so if you're trying to do this, you + may be going about it the wrong way or using the wrong tools. You + might try parallel arrays with common subscripts. + + But if you're bound and determined, you can use the multi-dimensional + array emulation of $a{'x','y','z'}, or you can make an array of names + of arrays and eval it. + + For example, if @name contains a list of names of arrays, you can + get at a the j-th element of the i-th array like so: + + $ary = $name[$i]; + $val = eval "\$$ary[$j]"; + + or in one line + + $val = eval "\$$name[$i][\$j]"; + + You could also use the type-globbing syntax to make an array of *name + values, which will be more efficient than eval. Here @name hold + a list of pointers, which we'll have to dereference through a temporary + variable. + + For example: + + { local(*ary) = $name[$i]; $val = $ary[$j]; } + + In fact, you can use this method to make arbitrarily nested data + structures. You really have to want to do this kind of thing + badly to go this far, however, as it is notationally cumbersome. + + Let's assume you just simply *have* to have an array of arrays of + arrays. What you do is make an array of pointers to arrays of + pointers, where pointers are *name values described above. You + initialize the outermost array normally, and then you build up your + pointers from there. For example: + + @w = ( 'ww' .. 'xx' ); + @x = ( 'xx' .. 'yy' ); + @y = ( 'yy' .. 'zz' ); + @z = ( 'zz' .. 'zzz' ); + + @ww = reverse @w; + @xx = reverse @x; + @yy = reverse @y; + @zz = reverse @z; + + Now make a couple of array of pointers to these: + + @A = ( *w, *x, *y, *z ); + @B = ( *ww, *xx, *yy, *zz ); + + And finally make an array of pointers to these arrays: + + @AAA = ( *A, *B ); + + To access an element, such as AAA[i][j][k], you must do this: + + local(*foo) = $AAA[$i]; + local(*bar) = $foo[$j]; + $answer = $bar[$k]; + + Similar manipulations on associative arrays are also feasible. + + You could take a look at recurse.pl package posted by Felix Lee + <flee@cs.psu.edu>, which lets you simulate vectors and tables (lists and + associative arrays) by using type glob references and some pretty serious + wizardry. + + In C, you're used to creating recursive datatypes for operations + like recursive decent parsing or tree traversal. In Perl, these + algorithms are best implemented using associative arrays. Take an + array called %parent, and build up pointers such that $parent{$person} + is the name of that person's parent. Make sure you remember that + $parent{'adam'} is 'adam'. :-) With a little care, this approach can + be used to implement general graph traversal algorithms as well. + + +2.10) How can I quote a variable to use in a regexp? + + From the manual: + + $pattern =~ s/(\W)/\\$1/g; + + Now you can freely use /$pattern/ without fear of any unexpected + meta-characters in it throwing off the search. If you don't know + whether a pattern is valid or not, enclose it in an eval to avoid + a fatal run-time error. + + +2.11) Why do setuid Perl scripts complain about kernel problems? + + This message: + + YOU HAVEN'T DISABLED SET-ID SCRIPTS IN THE KERNEL YET! + FIX YOUR KERNEL, PUT A C WRAPPER AROUND THIS SCRIPT, OR USE -u AND UNDUMP! + + is triggered because setuid scripts are inherently insecure due to a + kernel bug. If your system has fixed this bug, you can compile Perl + so that it knows this. Otherwise, create a setuid C program that just + execs Perl with the full name of the script. + + +2.12) How do I open a pipe both to and from a command? + + In general, this is a dangerous move because you can find yourself in a + deadlock situation. It's better to put one end of the pipe to a file. + For example: + + # first write some_cmd's input into a_file, then + open(CMD, "some_cmd its_args < a_file |"); + while (<CMD>) { + + # or else the other way; run the cmd + open(CMD, "| some_cmd its_args > a_file"); + while ($condition) { + print CMD "some output\n"; + # other code deleted + } + close CMD || warn "cmd exited $?"; + + # now read the file + open(FILE,"a_file"); + while (<FILE>) { + + If you have ptys, you could arrange to run the command on a pty and + avoid the deadlock problem. See the chat2.pl package in the + distributed library for ways to do this. + + At the risk of deadlock, it is theoretically possible to use a + fork, two pipe calls, and an exec to manually set up the two-way + pipe. (BSD system may use socketpair() in place of the two pipes, + but this is not as portable.) The open2 library function distributed + with the current perl release will do this for you. + + It assumes it's going to talk to something like adb, both writing to + it and reading from it. This is presumably safe because you "know" + that commands like adb will read a line at a time and output a line at + a time. Programs like sort that read their entire input stream first, + however, are quite apt to cause deadlock. + + +2.13) How can I change the first N letters of a string? + + Remember that the substr() function produces an lvalue, that is, it may be + assigned to. Therefore, to change the first character to an S, you could + do this: + + substr($var,0,1) = 'S'; + + This assumes that $[ is 0; for a library routine where you can't know $[, + you should use this instead: + + substr($var,$[,1) = 'S'; + + While it would be slower, you could in this case use a substitute: + + $var =~ s/^./S/; + + But this won't work if the string is empty or its first character is a + newline, which "." will never match. So you could use this instead: + + $var =~ s/^[^\0]?/S/; + + To do things like translation of the first part of a string, use substr, + as in: + + substr($var, $[, 10) =~ tr/a-z/A-Z/; + + If you don't know then length of what to translate, something like + this works: + + /^(\S+)/ && substr($_,$[,length($1)) =~ tr/a-z/A-Z/; + + For some things it's convenient to use the /e switch of the + substitute operator: + + s/^(\S+)/($tmp = $1) =~ tr#a-z#A-Z#, $tmp/e + + although in this case, it runs more slowly than does the previous example. + + +2.14) How can I manipulate fixed-record-length files? + + The most efficient way is using pack and unpack. This is faster than + using substr. Here is a sample chunk of code to break up and put back + together again some fixed-format input lines, in this case, from ps. + + # sample input line: + # 15158 p5 T 0:00 perl /mnt/tchrist/scripts/now-what + $ps_t = 'A6 A4 A7 A5 A*'; + open(PS, "ps|"); + $_ = <PS>; print; + while (<PS>) { + ($pid, $tt, $stat, $time, $command) = unpack($ps_t, $_); + for $var ('pid', 'tt', 'stat', 'time', 'command' ) { + print "$var: <", eval "\$$var", ">\n"; + } + print 'line=', pack($ps_t, $pid, $tt, $stat, $time, $command), "\n"; + } + + +2.15) How can I make a file handle local to a subroutine? + + You must use the type-globbing *VAR notation. Here is some code to + cat an include file, calling itself recursively on nested local + include files (i.e. those with #include "file", not #include <file>): + + sub cat_include { + local($name) = @_; + local(*FILE); + local($_); + + warn "<INCLUDING $name>\n"; + if (!open (FILE, $name)) { + warn "can't open $name: $!\n"; + return; + } + while (<FILE>) { + if (/^#\s*include "([^"]*)"/) { + &cat_include($1); + } else { + print; + } + } + close FILE; + } + + +2.16) How can I extract just the unique elements of an array? + + There are several possible ways, depending on whether the + array is ordered and you wish to preserve the ordering. + + a) If @in is sorted, and you want @out to be sorted: + + $prev = 'nonesuch'; + @out = grep($_ ne $prev && (($prev) = $_), @in); + + This is nice in that it doesn't use much extra memory, + simulating uniq's behavior of removing only adjacent + duplicates. + + b) If you don't know whether @in is sorted: + + undef %saw; + @out = grep(!$saw{$_}++, @in); + + c) Like (b), but @in contains only small integers: + + @out = grep(!$saw[$_]++, @in); + + d) A way to do (b) without any loops or greps: + + undef %saw; + @saw{@in} = (); + @out = sort keys %saw; # remove sort if undesired + + e) Like (d), but @in contains only small positive integers: + + undef @ary; + @ary[@in] = @in; + @out = sort @ary; + + +2.17) How can I call alarm() or usleep() from Perl? + + It's available as a built-in as of version 3.038. If you want finer + granularity than 1 second (as usleep() provides) and have itimers and + syscall() on your system, you can use the following. You could also + use select(). + + It takes a floating-point number representing how long to delay until + you get the SIGALRM, and returns a floating- point number representing + how much time was left in the old timer, if any. Note that the C + function uses integers, but this one doesn't mind fractional numbers. + + # alarm; send me a SIGALRM in this many seconds (fractions ok) + # tom christiansen <tchrist@convex.com> + sub alarm { + require 'syscall.ph'; + require 'sys/time.ph'; + + local($ticks) = @_; + local($in_timer,$out_timer); + local($isecs, $iusecs, $secs, $usecs); + + local($itimer_t) = 'L4'; # should be &itimer'typedef() + + $secs = int($ticks); + $usecs = ($ticks - $secs) * 1e6; + + $out_timer = pack($itimer_t,0,0,0,0); + $in_timer = pack($itimer_t,0,0,$secs,$usecs); + + syscall(&SYS_setitimer, &ITIMER_REAL, $in_timer, $out_timer) + && die "alarm: setitimer syscall failed: $!"; + + ($isecs, $iusecs, $secs, $usecs) = unpack($itimer_t,$out_timer); + return $secs + ($usecs/1e6); + } + + +2.18) How can I test whether an array contains a certain element? + + There are several ways to approach this. If you are going to make + this query many times and the values are arbitrary strings, the + fastest way is probably to invert the original array and keep an + associative array lying about whose keys are the first array's values. + + @blues = ('turquoise', 'teal', 'lapis lazuli'); + undef %is_blue; + for (@blues) { $is_blue{$_} = 1; } + + Now you can check whether $is_blue{$some_color}. It might have been + a good idea to keep the blues all in an assoc array in the first place. + + If the values are all small integers, you could use a simple + indexed array. This kind of an array will take up less space: + + @primes = (2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31); + undef @is_tiny_prime; + for (@primes) { $is_tiny_prime[$_] = 1; } + + Now you check whether $is_tiny_prime[$some_number]. + + If the values in question are integers, but instead of strings, + you can save quite a lot of space by using bit strings instead: + + @articles = ( 1..10, 150..2000, 2017 ); + undef $read; + grep (vec($read,$_,1) = 1, @articles); + + Now check whether vec($read,$n,1) is true for some $n. + + +2.19) How can I do an atexit() or setjmp()/longjmp() in Perl? + + Perl's exception-handling mechanism is its eval operator. You + can use eval as setjmp and die as longjmp. Here's an example + of Larry's for timed-out input, which in C is often implemented + using setjmp and longjmp: + + $SIG{ALRM} = TIMEOUT; + sub TIMEOUT { die "restart input\n" } + + do { eval { &realcode } } while $@ =~ /^restart input/; + + sub realcode { + alarm 15; + $ans = <STDIN>; + alarm 0; + } + + Here's an example of Tom's for doing atexit() handling: + + sub atexit { push(@_exit_subs, @_) } + + sub _cleanup { unlink $tmp } + + &atexit('_cleanup'); + + eval <<'End_Of_Eval'; $here = __LINE__; + # as much code here as you want + End_Of_Eval + + $oops = $@; # save error message + + # now call his stuff + for (@_exit_subs) { &$_() } + + $oops && ($oops =~ s/\(eval\) line (\d+)/$0 . + " line " . ($1+$here)/e, die $oops); + + You can register your own routines via the &atexit function now. You + might also want to use the &realcode method of Larry's rather than + embedding all your code in the here-is document. Make sure to leave + via die rather than exit, or write your own &exit routine and call + that instead. In general, it's better for nested routines to exit + via die rather than exit for just this reason. + + Eval is also quite useful for testing for system dependent features, + like symlinks, or using a user-input regexp that might otherwise + blowup on you. + + +2.20) Why doesn't Perl interpret my octal data octally? + + Perl only understands octal and hex numbers as such when they occur + as constants in your program. If they are read in from somewhere + and assigned, then no automatic conversion takes place. You must + explicitly use oct() or hex() if you want this kind of thing to happen. + Actually, oct() knows to interpret both hex and octal numbers, while + hex only converts hexadecimal ones. For example: + + { + print "What mode would you like? "; + $mode = <STDIN>; + $mode = oct($mode); + unless ($mode) { + print "You can't really want mode 0!\n"; + redo; + } + chmod $mode, $file; + } + + Without the octal conversion, a requested mode of 755 would turn + into 01363, yielding bizarre file permissions of --wxrw--wt. + + If you want something that handles decimal, octal and hex input, + you could follow the suggestion in the man page and use: + + $val = oct($val) if $val =~ /^0/; + +2.21) How do I sort an associative array by value instead of by key? + + You have to declare a sort subroutine to do this. Let's assume + you want an ASCII sort on the values of the associative array %ary. + You could do so this way: + + foreach $key (sort by_value keys %ary) { + print $key, '=', $ary{$key}, "\n"; + } + sub by_value { $ary{$a} cmp $ary{$b}; } + + If you wanted a descending numeric sort, you could do this: + + sub by_value { $ary{$b} <=> $ary{$a}; } + + You can also inline your sort function, like this: + + foreach $key ( sort { $x{$b} <=> $a{$a} } keys %ary ) { + print $key, '=', $ary{$key}, "\n"; + } + + If you wanted a function that didn't have the array name hard-wired + into it, you could so this: + + foreach $key (&sort_by_value(*ary)) { + print $key, '=', $ary{$key}, "\n"; + } + sub sort_by_value { + local(*x) = @_; + sub _by_value { $x{$a} cmp $x{$b}; } + sort _by_value keys %x; + } + + If you want neither an alphabetic nor a numeric sort, then you'll + have to code in your own logic instead of relying on the built-in + signed comparison operators "cmp" and "<=>". + + Note that if you're sorting on just a part of the value, such as a + piece you might extract via split, unpack, pattern-matching, or + substr, then rather than performing that operation inside your sort + routine on each call to it, it is significantly more efficient to + build a parallel array of just those portions you're sorting on, sort + the indices of this parallel array, and then to subscript your original + array using the newly sorted indices. This method works on both + regular and associative arrays, since both @ary[@idx] and @ary{@idx} + make sense. See page 245 in the Camel Book on "Sorting an Array by a + Computable Field" for a simple example of this. + + +2.22) How can I capture STDERR from an external command? + + There are three basic ways of running external commands: + + system $cmd; + $output = `$cmd`; + open (PIPE, "cmd |"); + + In the first case, both STDOUT and STDERR will go the same place as + the script's versions of these, unless redirected. You can always put + them where you want them and then read them back when the system + returns. In the second and third cases, you are reading the STDOUT + *only* of your command. If you would like to have merged STDOUT and + STDERR, you can use shell file-descriptor redirection to dup STDERR to + STDOUT: + + $output = `$cmd 2>&1`; + open (PIPE, "cmd 2>&1 |"); + + Another possibility is to run STDERR into a file and read the file + later, as in + + $output = `$cmd 2>some_file`; + open (PIPE, "cmd 2>some_file |"); + + Here's a way to read from both of them and know which descriptor + you got each line from. The trick is to pipe only STDERR through + sed, which then marks each of its lines, and then sends that + back into a merged STDOUT/STDERR stream, from which your Perl program + then reads a line at a time: + + open (CMD, + "3>&1 (cmd args 2>&1 1>&3 3>&- | sed 's/^/STDERR:/' 3>&-) 3>&- |"); + + while (<CMD>) { + if (s/^STDERR://) { + print "line from stderr: ", $_; + } else { + print "line from stdout: ", $_; + } + } + + Be apprised that you *must* use Bourne shell redirection syntax + here, not csh! In fact, you can't even do these things with csh. + For details on how lucky you are that perl's system() and backtick + and pipe opens all use Bourne shell, fetch the file from convex.com + called /pub/csh.whynot -- and you'll be glad that perl's shell + interface is the Bourne shell. + + +2.23) Why doesn't open return an error when a pipe open fails? + + These statements: + + open(TOPIPE, "|bogus_command") || die ... + open(FROMPIPE, "bogus_command|") || die ... + + will not fail just for lack of the bogus_command. They'll only + fail if the fork to run them fails, which is seldom the problem. + + If you're writing to the TOPIPE, you'll get a SIGPIPE if the child + exits prematurely or doesn't run. If you are reading from the + FROMPIPE, you need to check the close() to see what happened. + + If you want an answer sooner than pipe buffering might otherwise + afford you, you can do something like this: + + $kid = open (PIPE, "bogus_command |"); # XXX: check defined($kid) + (kill 0, $kid) || die "bogus_command failed"; + + This works fine if bogus_command doesn't have shell metas in it, but + if it does, the shell may well not have exited before the kill 0. You + could always introduce a delay: + + $kid = open (PIPE, "bogus_command </dev/null |"); + sleep 1; + (kill 0, $kid) || die "bogus_command failed"; + + but this is sometimes undesirable, and in any event does not guarantee + correct behavior. But it seems slightly better than nothing. + + Similar tricks can be played with writable pipes if you don't wish to + catch the SIGPIPE. + + +2.24) How can I compare two date strings? + + If the dates are in an easily parsed, predetermined format, then you + can break them up into their component parts and call &timelocal from + the distributed perl library. If the date strings are in arbitrary + formats, however, it's probably easier to use the getdate program + from the Cnews distribution, since it accepts a wide variety of dates. + Note that in either case the return values you will really be + comparing will be the total time in seconds as return by time(). + + Here's a getdate function for perl that's not very efficient; you + can do better this by sending it many dates at once or modifying + getdate to behave better on a pipe. Beware the hardcoded pathname. + + sub getdate { + local($_) = shift; + + s/-(\d{4})$/+$1/ || s/\+(\d{4})$/-$1/; + # getdate has broken timezone sign reversal! + + $_ = `/usr/local/lib/news/newsbin/getdate '$_'`; + chop; + $_; + } + + Richard Ohnemus <rick@IMD.Sterling.COM> actually has a getdate.y + for use with the Perl yacc. You can get this from ftp.sterling.com + [192.124.9.1] in /local/perl-byacc1.8.1.tar.Z, or send the author + mail for details. + + +2.25) What's the fastest way to code up a given task in perl? + + Because Perl so lends itself to a variety of different approaches + for any given task, a common question is which is the fastest way + to code a given task. Since some approaches can be dramatically + more efficient that others, it's sometimes worth knowing which is + best. Unfortunately, the implementation that first comes to mind, + perhaps as a direct translation from C or the shell, often yields + suboptimal performance. Not all approaches have the same results + across different hardware and software platforms. Furthermore, + legibility must sometimes be sacrificed for speed. + + While an experienced perl programmer can sometimes eye-ball the code + and make an educated guess regarding which way would be fastest, + surprises can still occur. So, in the spirit of perl programming + being an empirical science, the best way to find out which of several + different methods runs the fastest is simply to code them all up and + time them. For example: + + $COUNT = 10_000; $| = 1; + + print "method 1: "; + + ($u, $s) = times; + for ($i = 0; $i < $COUNT; $i++) { + # code for method 1 + } + ($nu, $ns) = times; + printf "%8.4fu %8.4fs\n", ($nu - $u), ($ns - $s); + + print "method 2: "; + + ($u, $s) = times; + for ($i = 0; $i < $COUNT; $i++) { + # code for method 2 + } + ($nu, $ns) = times; + printf "%8.4fu %8.4fs\n", ($nu - $u), ($ns - $s); + + For more specific tips, see the section on Efficiency in the + ``Other Oddments'' chapter at the end of the Camel Book. + + +2.26) How can I know how many entries are in an associative array? + + While the number of elements in a @foobar array is simply @foobar when + used in a scalar, you can't figure out how many elements are in an + associative array in an analagous fashion. That's because %foobar in + a scalar context returns the ratio (as a string) of number of buckets + filled versus the number allocated. For example, scalar(%ENV) might + return "20/32". While perl could in theory keep a count, this would + break down on associative arrays that have been bound to dbm files. + + However, while you can't get a count this way, one thing you *can* use + it for is to determine whether there are any elements whatsoever in + the array, since "if (%table)" is guaranteed to be false if nothing + has ever been stored in it. + + So you either have to keep your own count around and increments + it every time you store a new key in the array, or else do it + on the fly when you really care, perhaps like this: + + $count++ while each %ENV; + + This preceding method will be faster than extracting the + keys into a temporary array to count them. + + As of a very recent patch, you can say + + $count = keys %ENV; + + + +2.27) Why can't my perl program read from STDIN after I gave it ^D (EOF) ? + + Because some stdio's set error and eof flags that need clearing. + + Try keeping around the seekpointer and go there, like this: + $where = tell(LOG); + seek(LOG, $where, 0); + + If that doesn't work, try seeking to a different part of the file and + then back. If that doesn't work, try seeking to a different part of + the file, reading something, and then seeking back. If that doesn't + work, give up on your stdio package and use sysread. You can't call + stdio's clearerr() from Perl, so if you get EINTR from a signal + handler, you're out of luck. Best to just use sysread() from the + start for the tty. + + +2.28) Do I always/never have to quote my strings or use semicolons? + + You don't have to quote strings that can't mean anything else + in the language, like identifiers with any upper-case letters + in them. Therefore, it's fine to do this: + + $SIG{INT} = Timeout_Routine; + or + + @Days = (Sun, Mon, Tue, Wed, Thu, Fri, Sat, Sun); + + but you can't get away with this: + + $foo{while} = until; + + in place of + + $foo{'while'} = 'until'; + + The requirements on semicolons have been increasingly relaxed. You no + longer need one at the end of a block, but stylistically, you're + better to use them if you don't put the curly brace on the same line: + + for (1..10) { print } + + is ok, as is + + @nlist = sort { $a <=> $b } @olist; + + but you probably shouldn't do this: + + for ($i = 0; $i < @a; $i++) { + print "i is $i\n" # <-- oops! + } + + because you might want to add lines later, and anyway, + it looks funny. :-) + + +2.29) How can I translate tildes in a filename? + + Perl doesn't expand tildes -- the shell (ok, some shells) do. + The classic request is to be able to do something like: + + open(FILE, "~/dir1/file1"); + open(FILE, "~tchrist/dir1/file1"); + + which doesn't work. (And you don't know it, because you + did a system call without an "|| die" clause! :-) + + If you *know* you're on a system with the csh, and you *know* + that Larry hasn't internalized file globbing, then you could + get away with + + $filename = <~tchrist/dir1/file1>; + + but that's pretty iffy. + + A better way is to do the translation yourself, as in: + + $filename =~ s#^~(\w+)(/.*)?$#(getpwnam($1))[7].$2#e; + + More robust and efficient versions that checked for error conditions, + handed simple ~/blah notation, and cached lookups are all reasonable + enhancements. + + +2.30) How can I convert my shell script to Perl? + + Larry's standard answer for this is to send your script to me (Tom + Christiansen) with appropriate supplications and offerings. :-( + That's because there's no automatic machine translator. Even if you + were, you wouldn't gain a lot, as most of the external programs would + still get called. It's the same problem as blind translation into C: + you're still apt to be bogged down by exec()s. You have to analize + the dataflow and algorithm and rethink it for optimal speedup. It's + not uncommon to see one, two, or even three orders of magnitude of + speed difference between the brute-force and the recoded approaches. + + +2.31) What is variable suicide and how can I prevent it? + + Variable suicide is a nasty sideeffect of dynamic scoping and + the way variables are passed by reference. If you say + + $x = 17; + &munge($x); + sub munge { + local($x); + local($myvar) = $_[0]; + ... + } + + Then you have just clubbered $_[0]! Why this is occurring + is pretty heavy wizardry: the reference to $x stored in + $_[0] was temporarily occluded by the previous local($x) + statement (which, you're recall, occurs at run-time, not + compile-time). The work around is simple, however: declare + your formal parameters first: + + sub munge { + local($myvar) = $_[0]; + local($x); + ... + } + + That doesn't help you if you're going to be trying to access + @_ directly after the local()s. In this case, careful use + of the package facility is your only recourse. + + Another manifestation of this problem occurs due to the + magical nature of the index variable in a foreach() loop. + + @num = 0 .. 4; + print "num begin @num\n"; + foreach $m (@num) { &ug } + print "num finish @num\n"; + sub ug { + local($m) = 42; + print "m=$m $num[0],$num[1],$num[2],$num[3]\n"; + } + + Which prints out the mysterious: + + num begin 0 1 2 3 4 + m=42 42,1,2,3 + m=42 0,42,2,3 + m=42 0,1,42,3 + m=42 0,1,2,42 + m=42 0,1,2,3 + num finish 0 1 2 3 4 + + What's happening here is that $m is an alias for each + element of @num. Inside &ug, you temporarily change + $m. Well, that means that you've also temporarily + changed whatever $m is an alias to!! The only workaround + is to be careful with global variables, using packages, + and/or just be aware of this potential in foreach() loops. + + +2.32) Can I use Perl regular expressions to match balanced text? + + No, or at least, not by the themselves. + + Regexps just aren't powerful enough. Although Perl's patterns aren't + strictly regular because they do backtracking (the \1 notation), you + still can't do it. You need to employ auxiliary logic. A simple + approach would involve keeping a bit of state around, something + vaguely like this (although we don't handle patterns on the same line): + + while(<>) { + if (/pat1/) { + if ($inpat++ > 0) { warn "already saw pat1" } + redo; + } + if (/pat2/) { + if (--$inpat < 0) { warn "never saw pat1" } + redo; + } + } + + A rather more elaborate subroutine to pull out balanced and possibly + nested single chars, like ` and ', { and }, or ( and ) can be found + on convex.com in /pub/perl/scripts/pull_quotes. + + +2.33) Can I use Perl to run a telnet or ftp session? + + Sure, you can connect directly to them using sockets, or you can run a + session on a pty. In either case, Randal's chat2 package, which is + distributed with the perl source, will come in handly. It address + much the same problem space as Don Libes's expect package does. Two + examples of using managing an ftp session using chat2 can be found on + convex.com in /pub/perl/scripts/ftp-chat2.shar . + + Caveat lector: chat2 is documented only by example, may not run on + System V systems, and is subtly machine dependent both in its ideas + of networking and in pseudottys. + + +2.34) What does "Malformed command links" mean? + + This is a bug in 4.035. While in general it's merely a cosmetic + problem, it often comanifests with a highly undesirable coredumping + problem. Programs known to be affected by the fatal coredump include + plum and pcops. Since perl5 is prety much a total rewrite, we can + count on it being fixed then, but if anyone tracks down the coredump + problem before then, a signifcant portion of the perl world would + rejoice. [Fixed in 4.036--lwall] |