Beefy Boxes and Bandwidth Generously Provided by pair Networks
We don't bite newbies here... much
 
PerlMonks  

Command line question

by igotlongestname (Acolyte)
on Jun 17, 2008 at 21:27 UTC ( [id://692590]=perlquestion: print w/replies, xml ) Need Help??

igotlongestname has asked for the wisdom of the Perl Monks concerning the following question:

I have a program written a while ago, with a Perl command line call, which I am having trouble deciphering. I think it may be using some older Perl syntax that I'm not familiar with (or possibly I am just not reading the line right). Here is the command:
perl -ni -e's+${SOURCE}/${SAMS}/++g;s+${SOURCE}/${SAMLIB}/++g;s+${SOUR +CE}/${SMCLIB}/+${SOURCE}/${KENO}/+g;if ( not m+^${SOURCE}/+ ) {s+${SO +URCE}/+\$$\{OBJECT\}/+g;print}' .depend ;\ ${SCALE}/cmds/Sort .depend )
I have an understanding of the -n putting the code in a loop, the -i allowing to write to the same file, and the -e letting the command line act like code. I'm having trouble seeing what each Perl code "line" (the stuff between the ;'s) does, as well as if s+ was syntax for substitute or something else. If anyone can give a quick synopsis of what's going on I'd be quite grateful. Thanks!

~Jack

Replies are listed 'Best First'.
Re: Command line question
by kyle (Abbot) on Jun 17, 2008 at 21:51 UTC

    Here it is spread out:

    while (<>) { s+${SOURCE}/${SAMS}/++g; s+${SOURCE}/${SAMLIB}/++g; s+${SOURCE}/${SMCLIB}/+${SOURCE}/${KENO}/+g; if ( not m+^${SOURCE}/+ ) { s+${SOURCE}/+\$$\{OBJECT\}/+g; print } }

    This is run on a file named ".depend", and then something else runs after that.

    I'm guessing that ${SOURCE} and friends are being interpolated somehow (even though they're in single quotes) because there's nothing in the Perl to give those variables values.

    Anyway, this is using "+" instead of "/" for the delimiters on s///, probably so that it can put a literal slash in there without having to backslash it. What it does (for each line) is something like:

    1. Remove "${SOURCE}/${SAMS}/" and "${SOURCE}/${SAMLIB}/" anywhere in the line.
    2. Replace every "${SOURCE}/${SMCLIB}/" with "${SOURCE}/${KENO}/"
    3. If the line starts with "${SOURCE}/", replace every "${SOURCE}" with a literal "${OBJECT}" (I think), and print the line.
    4. (Lines that don't start with "${SOURCE}/" are not printed and so removed.)

      I'm guessing that ${SOURCE} and friends are being interpolated somehow (even though they're in single quotes)

      Those quotes are processed by the shell. In the bourne shell or a derivative like bash, single quote don't perform any interpolation.

      $ echo "${PATH}" .:/home/ikegami/bin:/usr/local/bin:/usr/bin:/bin:/usr/bin/X11:/usr/gam +es $ echo '${PATH}' ${PATH}

      ( Here on end, assuming the bourne shell or a derivative like bash )

      So Perl sees

      BEGIN { $^I = ''; } while (<>) { s+${SOURCE}/${SAMS}/++g; s+${SOURCE}/${SAMLIB}/++g; s+${SOURCE}/${SMCLIB}/+${SOURCE}/${KENO}/+g; if ( not m+^${SOURCE}/+ ) { s+${SOURCE}/+\$$\{OBJECT\}/+g; print } }

      On the other hand, Perl regexp and replace expressions *do* interpolate. So the above is equivalent to

      BEGIN { $^I = ''; } while (<>) { s+//++g; s+//++g; s+//+//+g; if ( not m+^/+ ) { s+/+\${OBJECT}/+g; print } }

      Depending on what the OP wants to do, he needs to use -e"" instead of -e'', to escape the dollar signs, or to define those variables in Perl.

        My guess is that the code snippet is from a make file (while we are guessing).

        Ordinarily, I'd agree with you, but I get the impression that the OP's code works as-is, and he's just trying to figure out what it does and how. My guess is that the whole thing is in double quotes, and what perl actually sees is:

        BEGIN { $^I = ""; } LINE: while (defined($_ = <ARGV>)) { s[value-of-SOURCE/value-of-SAMS/][]g; s[value-of-SOURCE/value-of-SAMLIB/][]g; s[value-of-SOURCE/value-of-SMCLIB/][value-of-SOURCE/value-of-KENO/ +]g; if (not m[^value-of-SOURCE/]) { s[value-of-SOURCE/][$${OBJECT}/]g; print $_; } }

        That $${OBJECT} in there still seems wrong, though, and the OP is ambiguous about whether this is working code or not, so I'm pretty far from sure about this.

Re: Command line question
by FunkyMonk (Chancellor) on Jun 17, 2008 at 21:43 UTC
    After removing some backslashes that shouldn't(?) be there, and running what's left through Deparse (perl -MO=Deparse -c -e ...), I got:
    s[$SOURCE/$SAMS/][]g; s[$SOURCE/$SAMLIB/][]g; s[$SOURCE/$SMCLIB/][$SOURCE/$KENO/]g; if (not m[^$SOURCE/]) { s[$SOURCE/][$$OBJECT/]g; print $_; }

    Does that help?


    Unless I state otherwise, all my code runs with strict and warnings

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://692590]
Approved by kyle
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others perusing the Monastery: (2)
As of 2024-04-20 13:23 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found