Team LiB   Previous Section   Next Section

Program and Subroutine Parameters

The main part of any Perl script is sometimes known as package main, and just like any Perl package it can have subroutines. Calling these routines is straightforward. An example, displayed in Figure A-3, is broken down as follows:

  1. You can deliver any number of parameters directly into a Perl script via the special built-in @ARGV array. The script's own file name is stored in another special scalar variable, $0. For instance, in Figure A-3, if the script was called doctor_yes.pl and had three parameters, we could run it like this:

    $ perl doctor_yes.pl '007' 'James' 'Bond'

    In the background, Perl would set the following values for us before the rest of the script was executed:

    $0 = 'doctor_yes.pl';
    @ARGV = ('007', 'James', 'Bond');

    We're then free to use these values throughout the rest of the program, as if we're accessing ordinary variables.

  2. There is a kind of mini-@ARGV for subroutines, and each subroutine gets its own one. This is the @_ array, which dynamically expands depending on how many parameters we decide to send in. When we call funcOneTakesTwoParams( ) in Figure A-3, with two parameters Laurel and Hardy, this fills the @_ array, dedicated to funcOneTakesTwoParams( ), with the two appropriate strings.

  3. In funcTwoTakesSixParams( ) the six parameters are sent in here to fill another totally separate @_ array. This has absolutely nothing to do with the totally separate @_ array owned by funcOneTakesTwoParams( ).

Figure A-3. @ARGV and @_
figs/pdba_aa03.gif

Environmental Variable Access

A Perl script can also make use of environmental variables. These are stored within the built-in %ENV hash:

$old_oracle_home = $ENV{ORACLE_HOME};  # Store latest ORACLE_HOME
$ENV{ORACLE_HOME} = "C:\ORANT";        # Now set new ORACLE_HOME

Variable Types

Production Perl code generally starts off with the following line:

use strict;

This pragma disciplines the naming of Perl's two main types of variable:

Package variables

These are your typical global variables. We've seen how the main Perl script is known as package main. When we use other packages, we'll see that each one has an entirely different namespace; in this way, different package variables avoid naming clashes. What use strict does is to ensure that we fully qualify these variable names, so $friendly_variable in a small script must be used as $main::friendly_variable in a script employing the use strict pragma. You can localize package variables, within a code block, by the local operator, but only temporarily until the code block ends.

Lexical variables

Prefixed by my, these variables only exist within an appropriate code block, unless referred to from the outside. They disappear when the code block ends. In the following code the $timeString only exists within the while loop:

while($flag == 1){
   my $timeString = some_time_function(  );           # $timeString my'ed
   $flag = some_validation_function($timeString);
}

Think of package variables as being the major chess pieces, one set for the black package and one set for the white, with $black::king being entirely different from $white::king. Think of the lexical my variables as being more like pawns, useful to a particular package but generally disposable. However, as we'll see later in our discussion of object orientation, even humble my variables can be vital for object orientation - in the same way that a lowly pawn can decide chess games by reaching the opposite package's back line and becoming a knight or a queen.

The our prefix, introduced in Perl 5.6, mimics the my syntax, but defines globals rather than lexically scoped variables. It's a way of disguising package variables from the discipline of the use strict pragma, often to make your code look cleaner by avoiding full package name qualification. Aside from instances like this, where it is assumed that you know what you're doing, the use strict pragma will insist that you employ either fully qualified package variable names or lexically declared variables. Think of our as being like a bishop disguised as a pawn. Because it takes other pieces diagonally, a bishop is sometimes used to hold up pawn defenses, but is still a major piece possessing lethal power.[2]

[2] At least one of your authors has forgotten this more than once, and has suffered the consequences when the big pawn thing has turned the game, with an unexpected backwards corner-to-corner diagonal move, to take a queen.

Taint Mode

As well as use strict, you can also run your program with extra warnings to detect syntax ambiguities, unused variables, and that sort of thing. You can turn these warnings on via either the -w flag, or (in Perl Version 5.6 onwards) the use warnings pragma. For instance, the following code at the top of a program will turn on extra warnings:

#!/usr/local/bin/perl -w
use strict;

Alternatively, use the more modern form:

#!/usr/local/bin/perl
use warnings;
use strict;

To go beyond warnings in certain classes of programs, you must use taint mode. This mode works on the simple principle that nothing derived from outside your program should be allowed to change anything else held outside your program. All data is checked in taint mode, and the tainted variety usually includes @ARGV program parameters, %ENV environmental variables, and any file input. Anything else that uses tainted data also becomes tainted. You turn taint mode on with the following -T switch:

#!/usr/local/bin/perl -T

There are many mechanisms within Perl for laundering tainted data, but they all work on the basic assumption that you know what you're doing before you untaint such data. All CGI scripts should use taint mode, as should any other program being accessed remotely, especially via the Internet. You should also consider taint mode for any kind of daemon, or indeed any other kind of program that deals with external users or sensitive data.

    Team LiB   Previous Section   Next Section