SlideShare ist ein Scribd-Unternehmen logo
1 von 12
Downloaden Sie, um offline zu lesen
30/11/12                                                Bash Shell Programming in Linux

     Home | Linux |     Bash Shell Programming in Linux                          Share This Page


                                       Bash Shell Programming in Linux
                                                               Copyright © 2006, P. Lutus

                                                       Bash what? | Introduction | Preliminaries
                                                     Simple Stuff | Where are you? | Listing Files
                                           Examining Files | Pipelines and Redirection | Shell Script Basics
                                           First Shell Script | Tests and Branching | Loops and Repetition
                       Using Numbers in Scripts | Coping with user input | An advanced example with numbers and user input
                       Creating and using arrays | Strings and substrings | Searching and Replacing Substrings within Strings
                                     More obscure but useful string operations | Bash Version 3 | Useful Links

                                                       (double-click any word to see its definition)


           Revised 3/2006

           Bash what?

               Okay, I grant that this page might represent a leap from the familiar to the alien without much warning. Here are some
               explananatory notes:

                    Under Linux, there are some powerful tools that for all practical purposes are unavailable under Windows (I can imagine
                    all the old Linux hands saying "Duh!").
                    One of these tools is something called "shell programming". This means writing code that a command shell executes.
                    There is something like this under Windows, but as usual, the Windows version is a weak imitation.
                    The most common Linux shell is named "Bash". The name comes from "Bourne Again SHell," which, in turn ... (imagine a
                    lengthy recursion terminating in a caveman's grunt).
                    There are many other shells available. Unless there is a compelling reason not to, I recommend that people stick to the
                    Bash shell, because this increases the chance that your scripts will be portable between machines, distributions, even
                    operating systems.
                    I'll be showing some very basic examples of Bash shell programming on this page, and I want to say at the outset that
                    shell programming is an art, not a science. That means there is always some other way to do the same thing.
                    Because shell programming is an art, please don't write to say, "Wow, that was a really inefficient way to do such-and-
                    such." Please do write (message page) to report actual errors.
                    If this page seems too sketchy and elementary for your taste, you can choose from among the more advanced
                    resources in .


           Introduction


                    Early computers had a teletype machine with a keyboard for I/O. Later, glass terminals became the norm, but the
                    behavior was much the same — a keyboard, a screen, a text display. A program was responsible for mediating the
                    transaction between the operator and the machine, and as the years passed this program (the command interpreter or
                    shell) became more sophisticated.

                    At this stage the command shell has become rather too sophisticated, typically having a dozen ways to do any particular
                    thing. In this page I will try to limit myself to describing a handful of useful operations, based not on listing everything
                    that can be done, but on solving specific problems. There are some at the bottom of this page for those wanting more
                    depth.


           Preliminaries


                    There are two primary ways to use the shell: interactively and by writing shell scripts.

                            In the interactive mode, the user types a single command (or a short string of commands) and the result is
                            printed out.
                            In shell scripting, the user types anything from a few lines to an entire program into a text editor, then executes
                            the resulting text file as a shell script.
                            It is often the case that an interactive session becomes a shell scripting session, once things get too complicated
                            for simple interactive line entries, or because a specific sequence of commands appears to be generally useful and
                            worth preserving.

                    In a modern Linux environment the user can have more than one shell open at a time, either by moving between a
                    sequence of independent "virtual terminals" in a text-only environment, or by opening any number of shell windows in
                    the X Windows environment.
                    The advantage of having more than one shell available is that one shell can be used for testing one command at a time,
                    while another might provide a text editor for assembling single commands into a shell program.
                    I don't want to get too distribution-specific, but if you are not hosting X Windows and want more than one
                    simultaneous shell session, with many current distributions you can switch between "virtual terminals" by pressing
                    Ctrl+Alt+F(n), n typically between 1 and 6.

arachnoid.com/linux/shell_programming.html                                                                                                         1/12
In an environment that supports X Windows, simply open any desired number of command shell windows and move
        between them.


Simple Stuff


        First, a convention. I'll list things for you to type in this format:

        $dt
          ae

        I will list the computer's reply like this:

        TeDc2 1:25 PT20
        u e 3 05:1 S 03

        Notice the "$" symbol in the user entry above. This is a generic shell prompt, and yours will almost certainly look
        different (but it will include a similar symbol). I'll be using one of two prompts (this is a common convention, worth
        remembering): I'll use "$" to refer to a normal user session, and "#" to refer to a root session.
        NOTE: Avoid using root sessions and permissions unless it is required. Misused root authority can cause very serious
        harm to your system. Since this is a tutorial in which you will want to experiment with different commands, limit the
        chance for harm by doing so as an ordinary user.

        To put this another way, enter this example:

        #wom
          hai
        ro
        ot

        If your session produced the result shown above, please — log out and become an ordinary user.

        In shell programming, spaces matter. If you see spaces between words and characters in these examples, be sure to
        include the spaces.

        In shell programming, case matters also. If you don't get the results shown on this page, look at the case of your
        entries.


Where are you?


        As you may be aware, a Linux filesystem is in the form of a large tree with many branches called "subdirectories". When
        you issue a shell command, it is often necessary to know where you are in the "tree". Type this example:

        $pd
          w
        /ahpt/ah
        pt/ahpt

        When you try this example ("pwd" means "print working directory"), your current working directory will be printed.

        You can decide where you are in the tree. Type this example:

        $c ~
          d
        $pd
          w
        /oeuenm
        hm/srae

        The symbol "~" is a special shortcut character that can be used to refer to your home directory. You could have typed
        this —

        $c /oeuenm
          d hm/srae

        — and accomplished the same result, but if you think about it, the "~" character is more portable. Later, when you are
        writing shell scripts, you might want a command that moves to any user's home directory.


Listing Files


        Directories contain files, and you can list them in a simple, compact format:

        $ls
        flnm flnm flnm ..
        ieae ieae ieae .

        Or you can list them in more detail:

        $l -a
          s l
        (ealdls,oefl prln)
        dtie it n ie e ie

        And, very important, to find out what a command's options are, use the "man" (manual) command:

        $mnl
          a s
        (aulpg fr"s)
        mna ae o l"
30/11/12                                             Bash Shell Programming in Linux
                   NOTE: The "man" command allows you to learn a command's options. You still have to remember the command's
                   name.

                   To find files by name:

                   $fn .-ae'.p'
                     id  nm *jg
                   (ito flswt .p sfi i cretadalciddrcois
                   ls f ie ih jg ufx n urn n l hl ietre)

                   To create a text diagram of the directory tree:

                   $te - .
                     re d
                   (iga o tedrcoyte fo tecretdrcoy
                   darm f h ietr re rm h urn ietr)

                   The "tree" command is less useful now that directory trees have become so complicated, and now that most
                   distributions support X Windows and sophisticated filesystem browsers.

           Examining Files


                   There are a number of things you can do to find out more about the files in the list. Here are just a few:

                   The "file" command tries to identify files by examining their contents:

                   $fl txsalpg
                     ie u_ml.n
                   txsalpg PGiaedt,18x11 8btclrRB nnitrae
                   u_ml.n: N mg aa 2   5, -i/oo G, o-nelcd

                   The next example uses the obscurely named "cat" command. It prints the contents of a file. Unfortunately if the file's
                   contents are not readable, they get printed anyway.

                   $ctzpoe.x
                     a icdstt
                   (rnsteetr cnet o afl nmd"icdstt)
                   pit h nie otns f   ie ae zpoe.x"

                   If a file is too long to be viewed on one page, you can say:

                   $mr zpoe.x
                     oe icdstt
                   (rnsfl oesrefla atm)
                   pit ie n cenu t  ie

                   You can also use "grep" to print only those parts of a file you are interested in:

                   $ge 101zpoe.x
                     rp 00 icdstt
                   (rnsol toelnsta hv tecaatrsrn "00"i te)
                   pit ny hs ie ht ae h hrce tig 101 n hm

                   The "grep" command is very useful, unfortunately it has a difficult-to-remember name. Be sure to:

                   $mnge
                     a rp

              There are many, many more shell commands to learn and to use. You may want to browse the list of for more detail.


           Pipelines and Redirection


                   You can use a pipeline (symbolized by "|") to make the output of one command serve as the input to another
                   command. This idea can be used to create a combination of commands to accomplish something no single command
                   can do.

                   Enter this command:

                   $eh "hryapepah
                     co cer pl ec"
                   cer apepah
                   hry pl ec

                   Okay, let's say we want to sort these words alphabetically. There is a command "sort", but it sorts entire lines, not
                   words, so we need to break this single line into individual lines, one line per word.

                   Step one: pipe the output of "echo" into a translation (tr) command that will replace spaces with linefeeds (represented
                   by "n"):

                   $eh "hryapepah |t """n
                     co cer pl ec"  r   "
                   cer
                   hry
                   ape
                   pl
                   pah
                   ec

                   Success: each word appears on a separate line. Now we are ready to sort.

                   Step two: add the sort command:

                   $eh "hryapepah |t """n |sr
                     co cer pl ec"  r   "  ot
                   ape
                   pl
                   cer
                   hry
                   pah
                   ec
arachnoid.com/linux/shell_programming.html                                                                                                    3/12
30/11/12                                              Bash Shell Programming in Linux
                   Let's try reversing the order of the sort:

                   $eh "hryapepah |t """n |sr -
                     co cer pl ec"  r   "  ot r
                   pah
                   ec
                   cer
                   hry
                   ape
                   pl

                   Remember: A pipeline ("|") takes the output of one command and makes it the input to another command.

                   Normally the output from commands is printed on the screen. But using the symbol ">", you can redirect the output to
                   a file:

                   $dt >Rgto.x
                     ae  ihNwtt
                   $ctRgto.x
                     a ihNwtt
                   TeDc2 1:33 PT20
                   u e 3 44:3 S 03

                   The above example used ">" to replace the content of any existing file having the name "RightNow.txt". To append new
                   data to an existing file, use ">>" instead:

                   $dt > Rgto.x
                     ae > ihNwtt
                   $ctRgto.x
                     a ihNwtt
                   TeDc2 1:33 PT20
                   u e 3 44:3 S 03
                   TeDc2 1:61 PT20
                   u e 3 44:0 S 03

                   Remember: Use ">" to overwrite any existing file, use ">>" to append to any existing file. In both cases, if no file
                   exists, one is created.

                   Many commands have inputs as well as outputs. The input defaults to the keyboard, the output defaults to the screen.
                   To redirect the output to a file, use ">" or ">>" as shown above.
                   To make the output of a command serve as the input of another command, use "|".
                   To make the contents of a file serve as the input to a command, use "<":

                   $w <Rgto.x
                     c   ihNwtt
                   21 5
                     2 8

                   As is so often the case in shell programming, there is at least one other way to produce the above result:

                   $ctRgto.x |w
                     a ihNwtt  c
                   21 5
                     2 8


           Shell Script Basics


                   A shell script is a plain-text file that contains shell commands. It can be executed by typing its name into a shell, or by
                   placing its name in another shell script.

                   To be executable, a shell script file must meet some conditions:

                         The file must have a special first line that names an appropriate command processor. For this tutorial, the following
                         will work in most cases:

                         #/i/ah
                          !bnbs

                         If this example doesn't work, you will need to find out where your Bash shell executable is located and substitute
                         that location in the above example. Here is one way to find out:

                         $weesbs
                           hri ah

                         The file must be made executable by changing its permission bits. An example:

                         $cmd+ (hl srp flnm)
                           ho x sel cit ieae

                   A shell script file may optionally have an identifying suffix, like ".sh". This only helps the user remember which files are
                   which. The command processor responsible for executing the file uses the executable bit, plus the file's first line, to
                   decide how to handle a shell script file.

                   One normally executes a shell script this way:

                   $.srpnm.h
                     /citaes

                   This special entry is a way to tell the command processor that the desired script is located in the current directory.
                   Always remember: if you cannot get your shell script to run, remember this trick to provide its location as well as its
                   name.


           First Shell Script


                   This will get you past the details of writing and launching a simple script.

arachnoid.com/linux/shell_programming.html                                                                                                        4/12
30/11/12                                             Bash Shell Programming in Linux
                      1. Choose a text editor you want to use. It can be a command-line editor like emacs, pico or vi, or an X Windows
                         editor if you have this option.

                      2. Run your choice of editor and type the following lines:


                         #/i/ah
                          !bnbs
                         eh "el,wrd"
                          co Hlo ol.



                         NOTE: Be sure to place a linefeed at the end of your script. Forgetting a terminating linefeed is a common
                         beginner's error.
                      3. Save the file in the current working directory as "myscript.sh".

                      4. Move from the text editor to a command shell.

                      5. From the command shell, type this:

                         $cmd+ msrp.h
                           ho x ycits

                      6. To execute the script, type this:

                         $.msrp.h
                           /ycits
                         Hlo wrd
                          el, ol.

                   These steps will become second nature soon enough.


           Tests and Branching


                   Bash shell scripts can perform, and act on, various kinds of tests. This will be just the most basic introduction — see
                   the reference material at for more on this rather baroque topic.

                   To follow these and other examples that involve multiline shell scripts, please set up to edit and run a test script file
                   (let's call it "myscript.sh") that you can use to enter and test various options. And remember that the examples won't
                   include the all-important first line of the script (see script examples above) — it will be assumed to exist in each case.

                   Also, to save time, you may want to copy some of the shell code examples from this page directly into your editor.

                   Here is an example of a test and branch:


                   i [- .]
                    f  e
                   te
                    hn
                         eh "e.
                         co Ys"
                   es
                    le
                         eh "o"
                         co N.
                   fi



                   Run the test script:

                   $.msrp.h
                     /ycits
                   Ys
                   e.

                   We created a test (the part of the script between "[" and "]") which tested whether a particular element existed ("-e").
                   Because the symbol "." in this context means the current directory, the test succeeded. Try replacing the "." with
                   something that is not present in the current directory, example "xyz". See how the outcome changes.

                   It is important to realize that "[" is an alias for the command "test". The script could have been written as:


                   i ts - .
                    f et e
                   te
                    hn
                        eh "e.
                         co Ys"
                   es
                    le
                        eh "o"
                         co N.
                   fi



                   NOTE: Be sure to read the "test" man page to find out all the different tests that are available:

                   $mnts
                     a et

                   Before we move on, there is a perversity about tests in Bash shells that I want to discuss. It turns out, because of a
                   historical accident that now might as well be cast in concrete, when a test is conducted or a command returns a result

arachnoid.com/linux/shell_programming.html                                                                                                      5/12
30/11/12                                              Bash Shell Programming in Linux
                   value, the numerical value for "true" is 0, and "false" is 1. Those of you who have some programming experience will
                   likely find this reversal of intuition as annoying as I do.

                   Here is a way to get the result of the most recent logical test (and to show the weird reversal described above):

                   $ts - .
                     et e
                   $eh $
                     co ?
                   0

                   $ts - xz
                     et e y
                   $eh $
                     co ?
                   1

                   Please remember this reversal, because it confounds the process of thinking through, and constructing, logical tests.
                   For example, you may want to write a shortcut form for a test that only acts on one kind of result:

                   $ts - .& eh "e.
                     et e  & co Ys"
                   Ys
                   e.

                   This sort of shorthand relies on some knowledge of logical processing — if the left-hand part of an AND test yields
                   "true", then the right-hand part must also be evaluated, and so it is. But the numerical "true" value for the left-hand
                   test is 0, which would argue for the opposite logic.

                   Just to show how perverse this all is, here is an example of Bash logical testing that comes out the opposite way:

                   $eh $(0& 0)
                     co (  &  )
                   0

                   $eh $(1& 0)
                     co (  &  )
                   0

                   $eh $(0& 1)
                     co (  &  )
                   0

                   $eh $(1& 1)
                     co (  &  )
                   1

                   Yes, just as you would expect. So do be on guard against this shell "gotcha", which only affects the outcome of tests
                   and command result values. It probably will not surprise you to learn that no one mentions this strange anomaly in the
                   official Bash documentation.

                   A couple of rules about logical operators used as branches:
                        If you write "test && command", the command will only be executed if the test succeeds.
                        If you write "test || command", the command will only be executed if the test fails.

                   Run these tests:

                   $tu & eh "e.
                     re & co Ys"
                   Ys
                   e.

                   $fle| eh "e.
                     as | co Ys"
                   Ys
                   e.

                   Notice that the outcomes are entirely in keeping with one's intuition about such logical comparisons, and all is well as
                   long as you don't think about the fact that true equals 0. :)

                   Here's another scheme commonly seen in shell script programming and interactive sessions:

                   $cmad & cmad & cmad & cmad
                     omn1 & omn2 & omn3 & omn4

                   This line of code will not run the next command in the sequence unless the prior command has returned "true", meaning
                   no errors. It is a way to avoid running a command if a required prior outcome is not present.


           Loops and Repetition


                   Here are some examples of loop operators:


                   frf i * d
                   o n n ; o
                        eh "f"
                        co $n
                   dn
                   oe



                   In this example, the "*" is expanded by the shell to a list of all the files in the current directory, then each filename is
                   applied to the loop control area. In such a construct, any whitespace-delimited list will do:



arachnoid.com/linux/shell_programming.html                                                                                                        6/12
30/11/12                                              Bash Shell Programming in Linux
                   frf i tmdc hry d
                   o n n o ik ar; o
                        eh "f"
                        co $n
                   dn
                   oe



                   $.msrp.h
                     /ycits
                   tm
                   o
                   dc
                   ik
                   hry
                   ar

                   This method will work for any list that uses spaces as delimiters. But what happens if you must parse a list that must be
                   delimited by linefeeds instead of spaces, such as the case of a list of filenames or paths that contain spaces as part of
                   their names?

                   You can solve such a problem this way (there are other solutions):


                   l - |wiera f;d
                    s 1 hl ed n o
                        eh "f"
                        co $n
                   dn
                    oe



                   This example uses an option to "ls" (note: the option is "-" followed by the numerical digit "1", not a lowercase "L") that
                   formats file listings with one name per line, then this list is pipelined to a routine that reads lines until there are no more
                   to read. This meets the requirement that linefeeds become the delimiters between list elements, not spaces.

                   There is plenty more to this topic. Please refer to the list of for more.

           Using Numbers in Scripts


                   Contrary to a sometimes-expressed view, numbers can easily be accommodated in scripts. Example:


                   n1
                   =
                   wie[$ -e6] d
                   hl   n l  ; o
                       eh $
                        co n
                       ltn+
                        e +
                   dn
                   oe



                   $.msrp.h
                     /ycits
                   1
                   2
                   3
                   4
                   5
                   6

                   Notice the "let" command, which treats its argument in a way meant to accommodate numbers.

                   Here is a somewhat more complex example:


                   y1
                   =
                   wie[$ -e1 ] d
                   hl   y l 2 ; o
                       x1
                        =
                       wie[$ -e1 ] d
                        hl    x l 2 ; o
                             pit " 4"$($ *$ )
                              rnf % d ( x  y )
                             ltx+
                              e +
                       dn
                        oe
                       eh "
                        co "
                       lty+
                        e +
                   dn
                   oe



                   $.msrp.h
                     /ycits



                       1    2 3 4 5 6 7 8 9                     10   11   12
                       2    4 6 8 1 1 1 1 1
                                   0 2 4 6 8                    20   22   24
                       3    6 9 1 1 1 2 2 2
                                 2 5 8 1 4 7                    30   33   36
                       4    8 1 1 2 2 2 3 3
                               2 6 0 4 8 2 6                    40   44   48
arachnoid.com/linux/shell_programming.html                                                                                                           7/12
30/11/12                                                 Bash Shell Programming in Linux
                       5   10   15   20   25   30   35   4 4 5 5 6
                                                          0 5 0 5 0
                       6   12   18   24   30   36   42   4 5 6 6 7
                                                          8 4 0 6 2
                       7   14   21   28   35   42   49   5 6 7 7 8
                                                          6 3 0 7 4
                       8   16   24   32   40   48   56   6 7 8 8 9
                                                          4 2 0 8 6
                       9   18   27   36   45   54   63   7 8 9 9 18
                                                          2 1 0 9 0
                      10   20   30   40   50   60   70   8 9 101010
                                                          0 0 0 1 2
                      11   22   33   44   55   66   77   8 9 101112
                                                          8 9 1 2 3
                      12   24   36   48   60   72   84   9 18101214
                                                          6 0 2 3 4




           Coping with user input


                   Here is an example that relies on user input to decide what to do. It exploits a shell feature as an easy way to create a
                   menu of choices:


                   P3"hoe(-)"
                    S=Cos 15:
                   eh "hoefo tels blw"
                    co Cos rm h it eo.
                   slc nm i rdgenbu ylo mgna
                    eet ae n e re le elw aet
                   do
                        bek
                         ra
                   dn
                    oe
                   eh "o coe$ae"
                    co Yu hs nm.



                   When run, it looks like this:

                   $.msrp.h
                     /ycits


                   Cos fo tels blw
                    hoe rm h it eo.
                   1 rd
                    ) e
                   2 gen
                    ) re
                   3 bu
                    ) le
                   4 ylo
                    ) elw
                   5 mgna
                    ) aet
                   Cos (-)4
                    hoe 15:
                   Yucoeylo.
                    o hs elw




                   As written, this menu code won't catch some kinds of errors (like a number that is out of range). In any application
                   where the user choice must fall into defined bounds, be sure to perform a test on the result before using it. Example:


                   i ["nm"=" ] te
                    f  $ae   " ; hn
                        eh "ro i ety"
                        co Err n nr.
                        ei 1
                        xt
                   fi




           An advanced example with numbers and user input


                   Here is an example guessing game that ties together some of the elements we've covered so far:


                   sceNme=( (`ae+N /10)%10 + )
                   ertubr$( (dt %`      00    0) 1 )
                   ges-
                   us=1
                   wie["ges ! "sceNme"] d
                   hl    $us" = $ertubr ; o
                        eh - " a tikn o anme bten1ad10 Etryu ges"
                         co n I m hnig f   ubr ewe   n 0. ne or us:
                        ra ges
                         ed us
                        i ["ges =" ] te
                         f  $us"   " ; hn
                             eh "laeetranme.
                              co Pes ne     ubr"
                        ei ["ges ="sceNme"] te
                         lf  $us"   $ertubr ; hn
                             eh - "ae!$us i tecretase!
                              co e Ys ges s h orc nwr"
                        ei ["sceNme"-t"ges ] te
                         lf  $ertubr g $us" ; hn
                             eh "h sce nme i lre ta yu ges Tyaan"
                              co Te ert ubr s agr hn or us. r gi.
                        es
                         le
                             eh "h sce nme i salrta yu ges Tyaan"
                              co Te ert ubr s mle hn or us. r gi.
arachnoid.com/linux/shell_programming.html                                                                                                     8/12
fi
       dn
       oe



       Please study this example carefully, and refer to the reference materials in to understand some of the methods.

Creating and using arrays


       Shell arrays are relatively easy to construct. Example:


       ary(e genbu ylo mgna
       ra=rd re le elw aet)
       ln$#ra[]
       e={ary*}
       eh "h aryhs$e mmes Te ae"
       co Te ra a ln ebr. hy r:
       i0
       =
       wie[$ -t$e ] d
       hl   i l ln ; o
            eh "i $ary$]"
            co $: {ra[i}
            lti+
            e +
       dn
       oe



       Run this example:

       $.msrp.h
         /ycits



       Tearyhs5mmes Te ae
        h ra a  ebr. hy r:
       0 rd
        : e
       1 gen
        : re
       2 bu
        : le
       3 ylo
        : elw
       4 mgna
        : aet




       Now, before you decide this is a silly, rather useless example, replace one line of the script and run it again:


       ary(l`
       ra=`s)



       See what difference this makes (and think of all the kinds of lists you might create for this line).


Strings and substrings


       It's useful to be able to take strings apart and put them together in different ways. Here is how to select a substring
       from a string:


       srn=ti i asbtigts"
       tig"hs s   usrn et
       sbtig$srn:09
       usrn={tig1:}



       In this example, the variable "substring" contains the word "substring". Remember this rule:


       sbtig$srn_aibenm:trigpsto:egh
       usrn={tigvral_aesatn_oiinlnt}



       The string starting position is zero-based.


Searching and Replacing Substrings within Strings


       In this method you can replace one or more instances of a string with another string. Here is the basic syntax:
30/11/12                                             Bash Shell Programming in Linux
                   apa"hsi ats srn i wihtewr ts i rpae.
                   lh=Ti s  et tig n hc h od "et" s elcd"
                   bt=$apats/elc}
                   ea"{lh/etrpae"



                   The string "beta" now contains an edited version of the original string in which the first case of the word "test" has been
                   replaced by "replace". To replace all cases, not just the first, use this syntax:


                   bt=$apa/etrpae"
                   ea"{lh/ts/elc}



                   Note the double "//" symbol.

                   Here is an example in which we replace one string with another in a multi-line block of text:


                   ls=ciktfo ctdg
                    it"rce rg a o"
                   pe=Iwnab axn
                    om" an e    
                   Axi wa Idlv t b
                       s ht ' oe o en
                   I Ibcm axn
                    f   eae  
                   HwhpyIwudb.n
                    o ap    ol e"
                   frcitri $it d
                    o rte n ls; o
                         eh - $pe/x$rte}
                         co e {om//citr
                   dn
                    oe



                   Run this example:

                   $.msrp.h
                     /ycits



                   Iwnab acikt
                      an e   rce
                   Acikti wa Idlv t b
                      rce s ht ' oe o e
                   I Ibcm acikt
                    f   eae   rce
                   HwhpyIwudb.
                    o ap    ol e
                   Iwnab afo
                      an e   rg
                   Afo i wa Idlv t b
                      rg s ht ' oe o e
                   I Ibcm afo
                    f   eae   rg
                   HwhpyIwudb.
                    o ap    ol e
                   Iwnab act
                      an e   a
                   Acti wa Idlv t b
                      a s ht ' oe o e
                   I Ibcm act
                    f   eae   a
                   HwhpyIwudb.
                    o ap    ol e
                   Iwnab adg
                      an e   o
                   Adgi wa Idlv t b
                      o s ht ' oe o e
                   I Ibcm adg
                    f   eae   o
                   HwhpyIwudb.
                    o ap    ol e




                   Silly example, huh? It should be obvious that this search & replace capability could have many more useful purposes.


           More obscure but useful string operations


                   Here is a way to isolate something useful from a large, even multi-line, string. As above, this method relies on enclosing
                   a variable name in curly braces, then aplying a special operator to achieve a particular result.

                   Here is a list of four such operators:

                         Operator "#" means "delete from the left, to the first case of what follows."


                               $x"hsi m ts srn.
                                =Ti s y et tig"
                               $eh $x*}
                                co {#

                               i m ts srn.
                                s y et tig




                         Operator "##" means "delete from the left, to the last case of what follows."

arachnoid.com/linux/shell_programming.html                                                                                                  10/12
$x"hsi m ts srn.
             =Ti s y et tig"
            $eh $x# }
             co {#*

            srn.
            tig




      Operator "%" means "delete from the right, to the first case of what follows."


            $x"hsi m ts srn.
             =Ti s y et tig"
            $eh $x *
             co {% }

            Ti i m ts
            hs s y et




      Operator "%%" means "delete from the right, to the last case of what follows."


            $x"hsi m ts srn.
             =Ti s y et tig"
            $eh $x%*
             co {% }

            Ti
            hs




I find these operators particularly useful in parsing multi-line strings. Let's say I want to isolate a particular IP address
from the output of the "ifconfig" command. Here's how I would proceed:


      $x`si/fofg
        =/bnicni`
      $eh $
        co x

      eh
       t0         Ln ecpEhre Had 0:D5:C8:0
                   ik na:tent Wdr 00:60:D1
                  ie ad:9.6.. Bat1218025 Ms:5.5.5.
                   nt dr121801 cs:9.6..5   ak2525250
                  ie6ad:f8:2d5f:ec81/4SoeLn
                   nt dr e0:0:6ff0:d06 cp:ik
                  U BODATRNIGMLIAT MU10 Mti:
                   P RACS UNN UTCS   T:50 erc1
                  R pces233 err: dopd0oern: fae0
                   X akt:539 ros0 rpe: vrus0 rm:
                  T pces432 err: dopd0oern: crir0
                   X akt:279 ros0 rpe: vrus0 are:
                  cliin: tqeee:00
                   olsos0 xuuln10
                  R bts3108 (44MB T bts46649(7. MB
                   X ye:6505 3. i) X ye:9789 437 i)
                  Bs ades0ec Mmr:ee00f500
                   ae drs:xc0 eoyf400-e000
      lo          Ln ecpLclLobc
                   ik na:oa opak
                  ie ad:2... Ms:5...
                   nt dr17001 ak25000
                  ie6ad::118SoeHs
                   nt dr :/2 cp:ot
                  U LOBC RNIG MU146 Mti:
                   P OPAK UNN  T:63  erc1
                  R pces199 err: dopd0oern: fae0
                   X akt:034 ros0 rpe: vrus0 rm:
                  T pces199 err: dopd0oern: crir0
                   X akt:034 ros0 rpe: vrus0 are:
                  cliin: tqeee:
                   olsos0 xuuln0
                  R bts1328 (17MB T bts1328 (17MB
                   X ye:2730 1. i) X ye:2730 1. i)




There's lots of information, more than we need. Let's say for the sake of argument that I want the IP of "lo", the
loopback interface. I could specify this:


      $y$x*ntad:
        ={#ie dr}




But, while gobbling text from the left, this search would stop at the IP address of eth0, not the desired interface. So I
can specify it this way:


      $y$x*o*ntad:
        ={#l ie dr}




As a last step I'll trim off all remaining text to the right:
30/11/12                                              Bash Shell Programming in Linux

                         $y$y%*
                           ={% }




                   Leaving only the desired address.

                   It seems the "#" and "%" operators, and their variants, are able to accept a rather complex argument and sort through
                   the content of large strings, including strings with line breaks. This means I can use the shell to directly filter content in
                   some simple cases where I might have considered using sed or Perl.

           Bash Version 3


              I have always thought the inability to test for the presence of a string or pattern (without using grep, sed or something
              similar) was a conspicuous weakness in shell programming. Bash version 3, present on must current Linux distributions,
              addresses this lack by allowing regular expression matching.

              Let's say we need to establish whether variable $x appears to be a social security number:


                   i [ $ = [-]3-09{}[-]4 ]
                    f [ x ~ 09{}[-]2-09{} ]
                   te
                    hn
                         #poesSN
                           rcs S
                   es
                    le
                         #piterrmsae
                           rn ro esg
                   fi




              Notice the Perlish "=~" syntax and that the regular expression appears within double brackets. A substantial number of
              regular expression metacharacters are supported, but not some of the Perl-specific extensions like w, d and s.

              Another Bash 3 feature is an improved brace expansion operator:


                   $eh {.z
                     co a.}


                   abcdefghijklmnopqrstuvwxyz




                   frni {.5
                    o  n 0.}
                   do
                        eh $
                        co n
                   dn
                    oe


                   0
                   1
                   2
                   3
                   4
                   5




           Useful Links

              Well, as long-winded as it turned out to be, this page is supposed to be an introduction to shell programming, one that just
              touches the highlights. The linked references below will provide a deeper understanding of the covered topics.

                   A quick guide to writing scripts using the bash shell (Rutgers)
                   Advanced Bash Scripting Guide (Linux Documentation Project)
                   Bash Reference Manual (GNU Project, downloadable versions)




     Home | Linux |    Bash Shell Programming in Linux                         Share This Page



arachnoid.com/linux/shell_programming.html                                                                                                     12/12

Weitere ähnliche Inhalte

Was ist angesagt?

OpenGurukul : Language : Shell Scripting
OpenGurukul : Language : Shell ScriptingOpenGurukul : Language : Shell Scripting
OpenGurukul : Language : Shell ScriptingOpen Gurukul
 
Unix Shell Scripting
Unix Shell ScriptingUnix Shell Scripting
Unix Shell ScriptingMustafa Qasim
 
InstallingRoRinLinux
InstallingRoRinLinuxInstallingRoRinLinux
InstallingRoRinLinuxtutorialsruby
 
Bash shell scripting
Bash shell scriptingBash shell scripting
Bash shell scriptingVIKAS TIWARI
 
Complete Guide for Linux shell programming
Complete Guide for Linux shell programmingComplete Guide for Linux shell programming
Complete Guide for Linux shell programmingsudhir singh yadav
 
Introduction to Shell script
Introduction to Shell scriptIntroduction to Shell script
Introduction to Shell scriptBhavesh Padharia
 
Linux shell env
Linux shell envLinux shell env
Linux shell envRahul Pola
 

Was ist angesagt? (13)

OpenGurukul : Language : Shell Scripting
OpenGurukul : Language : Shell ScriptingOpenGurukul : Language : Shell Scripting
OpenGurukul : Language : Shell Scripting
 
Unix Shell Scripting
Unix Shell ScriptingUnix Shell Scripting
Unix Shell Scripting
 
InstallingRoRinLinux
InstallingRoRinLinuxInstallingRoRinLinux
InstallingRoRinLinux
 
SHELL PROGRAMMING
SHELL PROGRAMMINGSHELL PROGRAMMING
SHELL PROGRAMMING
 
Unix quicksheet
Unix quicksheetUnix quicksheet
Unix quicksheet
 
Shell scripting
Shell scriptingShell scripting
Shell scripting
 
Bash shell scripting
Bash shell scriptingBash shell scripting
Bash shell scripting
 
21bUc8YeDzZpE
21bUc8YeDzZpE21bUc8YeDzZpE
21bUc8YeDzZpE
 
Complete Guide for Linux shell programming
Complete Guide for Linux shell programmingComplete Guide for Linux shell programming
Complete Guide for Linux shell programming
 
Shell programming
Shell programmingShell programming
Shell programming
 
Introduction to Shell script
Introduction to Shell scriptIntroduction to Shell script
Introduction to Shell script
 
Basics of shell programming
Basics of shell programmingBasics of shell programming
Basics of shell programming
 
Linux shell env
Linux shell envLinux shell env
Linux shell env
 

Andere mochten auch

Sintesis informativa 18 de mayo 2016
Sintesis informativa 18 de mayo 2016Sintesis informativa 18 de mayo 2016
Sintesis informativa 18 de mayo 2016megaradioexpress
 
Colorado Coach Connection September 20, 2011
Colorado Coach Connection September 20, 2011Colorado Coach Connection September 20, 2011
Colorado Coach Connection September 20, 2011ICF Colorado
 
Technical Info 15 wrestplank replacement
Technical Info  15  wrestplank replacementTechnical Info  15  wrestplank replacement
Technical Info 15 wrestplank replacementDavid Boyce
 
Introduction to Web Server Security
Introduction to Web Server SecurityIntroduction to Web Server Security
Introduction to Web Server SecurityJITENDRA KUMAR PATEL
 
Sevilla misterios y leyendas - fotos antiguas semana santa
Sevilla misterios y leyendas - fotos antiguas semana santaSevilla misterios y leyendas - fotos antiguas semana santa
Sevilla misterios y leyendas - fotos antiguas semana santaAntonio Camel
 
Juguetes por edades
Juguetes por edadesJuguetes por edades
Juguetes por edadesGregorio5
 
Day 2: Trends in citizen input to the work of parliament, Ms. María Luisa So...
Day 2: Trends in citizen input to the work of parliament,  Ms. María Luisa So...Day 2: Trends in citizen input to the work of parliament,  Ms. María Luisa So...
Day 2: Trends in citizen input to the work of parliament, Ms. María Luisa So...wepc2016
 
Tratamientos aptos para el paciente complejo
Tratamientos aptos para el paciente complejoTratamientos aptos para el paciente complejo
Tratamientos aptos para el paciente complejoVictor Montori
 
Gestion Del Talento Ie 12 De Nov
Gestion Del Talento Ie 12 De NovGestion Del Talento Ie 12 De Nov
Gestion Del Talento Ie 12 De Novjcsanteserna
 
Seguridad en Infraestructura VoIp
Seguridad en Infraestructura VoIpSeguridad en Infraestructura VoIp
Seguridad en Infraestructura VoIpDaniela Calva
 
Mkt Buscadores Avanzado 2009 5 4
Mkt Buscadores Avanzado 2009 5 4Mkt Buscadores Avanzado 2009 5 4
Mkt Buscadores Avanzado 2009 5 4Iñaki Lakarra
 
State of the Art Communication - Does your Internal Communication Measure Up?
State of the Art Communication - Does your Internal Communication Measure Up?State of the Art Communication - Does your Internal Communication Measure Up?
State of the Art Communication - Does your Internal Communication Measure Up?SocialChorus
 
Manejo de excepciones en Java
Manejo de excepciones en JavaManejo de excepciones en Java
Manejo de excepciones en JavaJohn Ortiz
 
Mobile Development Platforms
Mobile Development PlatformsMobile Development Platforms
Mobile Development PlatformsAndri Yadi
 
Subluxacion de codo
Subluxacion de codoSubluxacion de codo
Subluxacion de codoBlanca Lobo
 

Andere mochten auch (20)

2015 c3 online learning part 1 & 2
2015 c3 online learning part 1 & 22015 c3 online learning part 1 & 2
2015 c3 online learning part 1 & 2
 
Resume_All
Resume_AllResume_All
Resume_All
 
Seabee eCourier Jan 7 2016
Seabee eCourier Jan 7 2016Seabee eCourier Jan 7 2016
Seabee eCourier Jan 7 2016
 
Sintesis informativa 18 de mayo 2016
Sintesis informativa 18 de mayo 2016Sintesis informativa 18 de mayo 2016
Sintesis informativa 18 de mayo 2016
 
Colorado Coach Connection September 20, 2011
Colorado Coach Connection September 20, 2011Colorado Coach Connection September 20, 2011
Colorado Coach Connection September 20, 2011
 
ACHA. ADVANCED CHANGE AGENT
ACHA. ADVANCED CHANGE AGENTACHA. ADVANCED CHANGE AGENT
ACHA. ADVANCED CHANGE AGENT
 
Technical Info 15 wrestplank replacement
Technical Info  15  wrestplank replacementTechnical Info  15  wrestplank replacement
Technical Info 15 wrestplank replacement
 
Masnuriyah
Masnuriyah Masnuriyah
Masnuriyah
 
Introduction to Web Server Security
Introduction to Web Server SecurityIntroduction to Web Server Security
Introduction to Web Server Security
 
Sevilla misterios y leyendas - fotos antiguas semana santa
Sevilla misterios y leyendas - fotos antiguas semana santaSevilla misterios y leyendas - fotos antiguas semana santa
Sevilla misterios y leyendas - fotos antiguas semana santa
 
Juguetes por edades
Juguetes por edadesJuguetes por edades
Juguetes por edades
 
Day 2: Trends in citizen input to the work of parliament, Ms. María Luisa So...
Day 2: Trends in citizen input to the work of parliament,  Ms. María Luisa So...Day 2: Trends in citizen input to the work of parliament,  Ms. María Luisa So...
Day 2: Trends in citizen input to the work of parliament, Ms. María Luisa So...
 
Tratamientos aptos para el paciente complejo
Tratamientos aptos para el paciente complejoTratamientos aptos para el paciente complejo
Tratamientos aptos para el paciente complejo
 
Gestion Del Talento Ie 12 De Nov
Gestion Del Talento Ie 12 De NovGestion Del Talento Ie 12 De Nov
Gestion Del Talento Ie 12 De Nov
 
Seguridad en Infraestructura VoIp
Seguridad en Infraestructura VoIpSeguridad en Infraestructura VoIp
Seguridad en Infraestructura VoIp
 
Mkt Buscadores Avanzado 2009 5 4
Mkt Buscadores Avanzado 2009 5 4Mkt Buscadores Avanzado 2009 5 4
Mkt Buscadores Avanzado 2009 5 4
 
State of the Art Communication - Does your Internal Communication Measure Up?
State of the Art Communication - Does your Internal Communication Measure Up?State of the Art Communication - Does your Internal Communication Measure Up?
State of the Art Communication - Does your Internal Communication Measure Up?
 
Manejo de excepciones en Java
Manejo de excepciones en JavaManejo de excepciones en Java
Manejo de excepciones en Java
 
Mobile Development Platforms
Mobile Development PlatformsMobile Development Platforms
Mobile Development Platforms
 
Subluxacion de codo
Subluxacion de codoSubluxacion de codo
Subluxacion de codo
 

Ähnlich wie Bash shell programming in linux

Shell & Shell Script
Shell & Shell ScriptShell & Shell Script
Shell & Shell ScriptAmit Ghosh
 
(Ebook) linux shell scripting tutorial
(Ebook) linux shell scripting tutorial(Ebook) linux shell scripting tutorial
(Ebook) linux shell scripting tutorialjayaramprabhu
 
Introduction to-linux
Introduction to-linuxIntroduction to-linux
Introduction to-linuxkishore1986
 
Shell tutorial
Shell tutorialShell tutorial
Shell tutorialVu Duy Tu
 
Introduction to-linux
Introduction to-linuxIntroduction to-linux
Introduction to-linuxrowiebornia
 
Introduction-to-Linux.pptx
Introduction-to-Linux.pptxIntroduction-to-Linux.pptx
Introduction-to-Linux.pptxDavidMaina47
 
Introduction khgjkhygkjiyhgikjyhgikygkii
Introduction khgjkhygkjiyhgikjyhgikygkiiIntroduction khgjkhygkjiyhgikjyhgikygkii
Introduction khgjkhygkjiyhgikjyhgikygkiicmdept1
 
Raspberry pi Part 4
Raspberry pi Part 4Raspberry pi Part 4
Raspberry pi Part 4Techvilla
 
Using Unix
Using UnixUsing Unix
Using UnixDr.Ravi
 
Unix tutorial-08
Unix tutorial-08Unix tutorial-08
Unix tutorial-08Tushar Jain
 

Ähnlich wie Bash shell programming in linux (20)

Shell intro
Shell introShell intro
Shell intro
 
Shell & Shell Script
Shell & Shell ScriptShell & Shell Script
Shell & Shell Script
 
Shell intro
Shell introShell intro
Shell intro
 
Shell intro
Shell introShell intro
Shell intro
 
Unixshellscript 100406085942-phpapp02
Unixshellscript 100406085942-phpapp02Unixshellscript 100406085942-phpapp02
Unixshellscript 100406085942-phpapp02
 
Linux Basics
Linux BasicsLinux Basics
Linux Basics
 
60761 linux
60761 linux60761 linux
60761 linux
 
21bUc8YeDzZpE
21bUc8YeDzZpE21bUc8YeDzZpE
21bUc8YeDzZpE
 
21bUc8YeDzZpE
21bUc8YeDzZpE21bUc8YeDzZpE
21bUc8YeDzZpE
 
(Ebook) linux shell scripting tutorial
(Ebook) linux shell scripting tutorial(Ebook) linux shell scripting tutorial
(Ebook) linux shell scripting tutorial
 
Introduction to-linux
Introduction to-linuxIntroduction to-linux
Introduction to-linux
 
Shell tutorial
Shell tutorialShell tutorial
Shell tutorial
 
Unix practical file
Unix practical fileUnix practical file
Unix practical file
 
Introduction-to-Linux.pptx
Introduction-to-Linux.pptxIntroduction-to-Linux.pptx
Introduction-to-Linux.pptx
 
Introduction to-linux
Introduction to-linuxIntroduction to-linux
Introduction to-linux
 
Introduction-to-Linux.pptx
Introduction-to-Linux.pptxIntroduction-to-Linux.pptx
Introduction-to-Linux.pptx
 
Introduction khgjkhygkjiyhgikjyhgikygkii
Introduction khgjkhygkjiyhgikjyhgikygkiiIntroduction khgjkhygkjiyhgikjyhgikygkii
Introduction khgjkhygkjiyhgikjyhgikygkii
 
Raspberry pi Part 4
Raspberry pi Part 4Raspberry pi Part 4
Raspberry pi Part 4
 
Using Unix
Using UnixUsing Unix
Using Unix
 
Unix tutorial-08
Unix tutorial-08Unix tutorial-08
Unix tutorial-08
 

Mehr von Norberto Angulo

Mehr von Norberto Angulo (16)

Curso hacking en video nuevos links
Curso hacking en video nuevos linksCurso hacking en video nuevos links
Curso hacking en video nuevos links
 
Configurar el cliente de no ip en linux, dns dinamico
Configurar el cliente de no ip en linux, dns dinamicoConfigurar el cliente de no ip en linux, dns dinamico
Configurar el cliente de no ip en linux, dns dinamico
 
Aircrack windows web
Aircrack windows webAircrack windows web
Aircrack windows web
 
Enlaces a libros digitales
Enlaces a libros digitalesEnlaces a libros digitales
Enlaces a libros digitales
 
Clase002
Clase002Clase002
Clase002
 
sistemas distribuidos
sistemas distribuidossistemas distribuidos
sistemas distribuidos
 
Derecho informatico
Derecho informaticoDerecho informatico
Derecho informatico
 
Taller propiedad intelectual
Taller propiedad intelectualTaller propiedad intelectual
Taller propiedad intelectual
 
Propiedad intelectual
Propiedad intelectual Propiedad intelectual
Propiedad intelectual
 
Propiedad intelectualcbe
Propiedad intelectualcbePropiedad intelectualcbe
Propiedad intelectualcbe
 
WirelessKeyloggerEs
WirelessKeyloggerEsWirelessKeyloggerEs
WirelessKeyloggerEs
 
keylogger casero
keylogger caserokeylogger casero
keylogger casero
 
Wireless keyloggeres
Wireless keyloggeresWireless keyloggeres
Wireless keyloggeres
 
Keylogger casero
Keylogger caseroKeylogger casero
Keylogger casero
 
P padrino todo
P padrino todoP padrino todo
P padrino todo
 
Todo es posible
Todo es posibleTodo es posible
Todo es posible
 

Bash shell programming in linux

  • 1. 30/11/12 Bash Shell Programming in Linux Home | Linux | Bash Shell Programming in Linux Share This Page Bash Shell Programming in Linux Copyright © 2006, P. Lutus Bash what? | Introduction | Preliminaries Simple Stuff | Where are you? | Listing Files Examining Files | Pipelines and Redirection | Shell Script Basics First Shell Script | Tests and Branching | Loops and Repetition Using Numbers in Scripts | Coping with user input | An advanced example with numbers and user input Creating and using arrays | Strings and substrings | Searching and Replacing Substrings within Strings More obscure but useful string operations | Bash Version 3 | Useful Links (double-click any word to see its definition) Revised 3/2006 Bash what? Okay, I grant that this page might represent a leap from the familiar to the alien without much warning. Here are some explananatory notes: Under Linux, there are some powerful tools that for all practical purposes are unavailable under Windows (I can imagine all the old Linux hands saying "Duh!"). One of these tools is something called "shell programming". This means writing code that a command shell executes. There is something like this under Windows, but as usual, the Windows version is a weak imitation. The most common Linux shell is named "Bash". The name comes from "Bourne Again SHell," which, in turn ... (imagine a lengthy recursion terminating in a caveman's grunt). There are many other shells available. Unless there is a compelling reason not to, I recommend that people stick to the Bash shell, because this increases the chance that your scripts will be portable between machines, distributions, even operating systems. I'll be showing some very basic examples of Bash shell programming on this page, and I want to say at the outset that shell programming is an art, not a science. That means there is always some other way to do the same thing. Because shell programming is an art, please don't write to say, "Wow, that was a really inefficient way to do such-and- such." Please do write (message page) to report actual errors. If this page seems too sketchy and elementary for your taste, you can choose from among the more advanced resources in . Introduction Early computers had a teletype machine with a keyboard for I/O. Later, glass terminals became the norm, but the behavior was much the same — a keyboard, a screen, a text display. A program was responsible for mediating the transaction between the operator and the machine, and as the years passed this program (the command interpreter or shell) became more sophisticated. At this stage the command shell has become rather too sophisticated, typically having a dozen ways to do any particular thing. In this page I will try to limit myself to describing a handful of useful operations, based not on listing everything that can be done, but on solving specific problems. There are some at the bottom of this page for those wanting more depth. Preliminaries There are two primary ways to use the shell: interactively and by writing shell scripts. In the interactive mode, the user types a single command (or a short string of commands) and the result is printed out. In shell scripting, the user types anything from a few lines to an entire program into a text editor, then executes the resulting text file as a shell script. It is often the case that an interactive session becomes a shell scripting session, once things get too complicated for simple interactive line entries, or because a specific sequence of commands appears to be generally useful and worth preserving. In a modern Linux environment the user can have more than one shell open at a time, either by moving between a sequence of independent "virtual terminals" in a text-only environment, or by opening any number of shell windows in the X Windows environment. The advantage of having more than one shell available is that one shell can be used for testing one command at a time, while another might provide a text editor for assembling single commands into a shell program. I don't want to get too distribution-specific, but if you are not hosting X Windows and want more than one simultaneous shell session, with many current distributions you can switch between "virtual terminals" by pressing Ctrl+Alt+F(n), n typically between 1 and 6. arachnoid.com/linux/shell_programming.html 1/12
  • 2. In an environment that supports X Windows, simply open any desired number of command shell windows and move between them. Simple Stuff First, a convention. I'll list things for you to type in this format: $dt ae I will list the computer's reply like this: TeDc2 1:25 PT20 u e 3 05:1 S 03 Notice the "$" symbol in the user entry above. This is a generic shell prompt, and yours will almost certainly look different (but it will include a similar symbol). I'll be using one of two prompts (this is a common convention, worth remembering): I'll use "$" to refer to a normal user session, and "#" to refer to a root session. NOTE: Avoid using root sessions and permissions unless it is required. Misused root authority can cause very serious harm to your system. Since this is a tutorial in which you will want to experiment with different commands, limit the chance for harm by doing so as an ordinary user. To put this another way, enter this example: #wom hai ro ot If your session produced the result shown above, please — log out and become an ordinary user. In shell programming, spaces matter. If you see spaces between words and characters in these examples, be sure to include the spaces. In shell programming, case matters also. If you don't get the results shown on this page, look at the case of your entries. Where are you? As you may be aware, a Linux filesystem is in the form of a large tree with many branches called "subdirectories". When you issue a shell command, it is often necessary to know where you are in the "tree". Type this example: $pd w /ahpt/ah pt/ahpt When you try this example ("pwd" means "print working directory"), your current working directory will be printed. You can decide where you are in the tree. Type this example: $c ~ d $pd w /oeuenm hm/srae The symbol "~" is a special shortcut character that can be used to refer to your home directory. You could have typed this — $c /oeuenm d hm/srae — and accomplished the same result, but if you think about it, the "~" character is more portable. Later, when you are writing shell scripts, you might want a command that moves to any user's home directory. Listing Files Directories contain files, and you can list them in a simple, compact format: $ls flnm flnm flnm .. ieae ieae ieae . Or you can list them in more detail: $l -a s l (ealdls,oefl prln) dtie it n ie e ie And, very important, to find out what a command's options are, use the "man" (manual) command: $mnl a s (aulpg fr"s) mna ae o l"
  • 3. 30/11/12 Bash Shell Programming in Linux NOTE: The "man" command allows you to learn a command's options. You still have to remember the command's name. To find files by name: $fn .-ae'.p' id nm *jg (ito flswt .p sfi i cretadalciddrcois ls f ie ih jg ufx n urn n l hl ietre) To create a text diagram of the directory tree: $te - . re d (iga o tedrcoyte fo tecretdrcoy darm f h ietr re rm h urn ietr) The "tree" command is less useful now that directory trees have become so complicated, and now that most distributions support X Windows and sophisticated filesystem browsers. Examining Files There are a number of things you can do to find out more about the files in the list. Here are just a few: The "file" command tries to identify files by examining their contents: $fl txsalpg ie u_ml.n txsalpg PGiaedt,18x11 8btclrRB nnitrae u_ml.n: N mg aa 2 5, -i/oo G, o-nelcd The next example uses the obscurely named "cat" command. It prints the contents of a file. Unfortunately if the file's contents are not readable, they get printed anyway. $ctzpoe.x a icdstt (rnsteetr cnet o afl nmd"icdstt) pit h nie otns f ie ae zpoe.x" If a file is too long to be viewed on one page, you can say: $mr zpoe.x oe icdstt (rnsfl oesrefla atm) pit ie n cenu t ie You can also use "grep" to print only those parts of a file you are interested in: $ge 101zpoe.x rp 00 icdstt (rnsol toelnsta hv tecaatrsrn "00"i te) pit ny hs ie ht ae h hrce tig 101 n hm The "grep" command is very useful, unfortunately it has a difficult-to-remember name. Be sure to: $mnge a rp There are many, many more shell commands to learn and to use. You may want to browse the list of for more detail. Pipelines and Redirection You can use a pipeline (symbolized by "|") to make the output of one command serve as the input to another command. This idea can be used to create a combination of commands to accomplish something no single command can do. Enter this command: $eh "hryapepah co cer pl ec" cer apepah hry pl ec Okay, let's say we want to sort these words alphabetically. There is a command "sort", but it sorts entire lines, not words, so we need to break this single line into individual lines, one line per word. Step one: pipe the output of "echo" into a translation (tr) command that will replace spaces with linefeeds (represented by "n"): $eh "hryapepah |t """n co cer pl ec" r " cer hry ape pl pah ec Success: each word appears on a separate line. Now we are ready to sort. Step two: add the sort command: $eh "hryapepah |t """n |sr co cer pl ec" r " ot ape pl cer hry pah ec arachnoid.com/linux/shell_programming.html 3/12
  • 4. 30/11/12 Bash Shell Programming in Linux Let's try reversing the order of the sort: $eh "hryapepah |t """n |sr - co cer pl ec" r " ot r pah ec cer hry ape pl Remember: A pipeline ("|") takes the output of one command and makes it the input to another command. Normally the output from commands is printed on the screen. But using the symbol ">", you can redirect the output to a file: $dt >Rgto.x ae ihNwtt $ctRgto.x a ihNwtt TeDc2 1:33 PT20 u e 3 44:3 S 03 The above example used ">" to replace the content of any existing file having the name "RightNow.txt". To append new data to an existing file, use ">>" instead: $dt > Rgto.x ae > ihNwtt $ctRgto.x a ihNwtt TeDc2 1:33 PT20 u e 3 44:3 S 03 TeDc2 1:61 PT20 u e 3 44:0 S 03 Remember: Use ">" to overwrite any existing file, use ">>" to append to any existing file. In both cases, if no file exists, one is created. Many commands have inputs as well as outputs. The input defaults to the keyboard, the output defaults to the screen. To redirect the output to a file, use ">" or ">>" as shown above. To make the output of a command serve as the input of another command, use "|". To make the contents of a file serve as the input to a command, use "<": $w <Rgto.x c ihNwtt 21 5 2 8 As is so often the case in shell programming, there is at least one other way to produce the above result: $ctRgto.x |w a ihNwtt c 21 5 2 8 Shell Script Basics A shell script is a plain-text file that contains shell commands. It can be executed by typing its name into a shell, or by placing its name in another shell script. To be executable, a shell script file must meet some conditions: The file must have a special first line that names an appropriate command processor. For this tutorial, the following will work in most cases: #/i/ah !bnbs If this example doesn't work, you will need to find out where your Bash shell executable is located and substitute that location in the above example. Here is one way to find out: $weesbs hri ah The file must be made executable by changing its permission bits. An example: $cmd+ (hl srp flnm) ho x sel cit ieae A shell script file may optionally have an identifying suffix, like ".sh". This only helps the user remember which files are which. The command processor responsible for executing the file uses the executable bit, plus the file's first line, to decide how to handle a shell script file. One normally executes a shell script this way: $.srpnm.h /citaes This special entry is a way to tell the command processor that the desired script is located in the current directory. Always remember: if you cannot get your shell script to run, remember this trick to provide its location as well as its name. First Shell Script This will get you past the details of writing and launching a simple script. arachnoid.com/linux/shell_programming.html 4/12
  • 5. 30/11/12 Bash Shell Programming in Linux 1. Choose a text editor you want to use. It can be a command-line editor like emacs, pico or vi, or an X Windows editor if you have this option. 2. Run your choice of editor and type the following lines: #/i/ah !bnbs eh "el,wrd" co Hlo ol. NOTE: Be sure to place a linefeed at the end of your script. Forgetting a terminating linefeed is a common beginner's error. 3. Save the file in the current working directory as "myscript.sh". 4. Move from the text editor to a command shell. 5. From the command shell, type this: $cmd+ msrp.h ho x ycits 6. To execute the script, type this: $.msrp.h /ycits Hlo wrd el, ol. These steps will become second nature soon enough. Tests and Branching Bash shell scripts can perform, and act on, various kinds of tests. This will be just the most basic introduction — see the reference material at for more on this rather baroque topic. To follow these and other examples that involve multiline shell scripts, please set up to edit and run a test script file (let's call it "myscript.sh") that you can use to enter and test various options. And remember that the examples won't include the all-important first line of the script (see script examples above) — it will be assumed to exist in each case. Also, to save time, you may want to copy some of the shell code examples from this page directly into your editor. Here is an example of a test and branch: i [- .] f e te hn eh "e. co Ys" es le eh "o" co N. fi Run the test script: $.msrp.h /ycits Ys e. We created a test (the part of the script between "[" and "]") which tested whether a particular element existed ("-e"). Because the symbol "." in this context means the current directory, the test succeeded. Try replacing the "." with something that is not present in the current directory, example "xyz". See how the outcome changes. It is important to realize that "[" is an alias for the command "test". The script could have been written as: i ts - . f et e te hn eh "e. co Ys" es le eh "o" co N. fi NOTE: Be sure to read the "test" man page to find out all the different tests that are available: $mnts a et Before we move on, there is a perversity about tests in Bash shells that I want to discuss. It turns out, because of a historical accident that now might as well be cast in concrete, when a test is conducted or a command returns a result arachnoid.com/linux/shell_programming.html 5/12
  • 6. 30/11/12 Bash Shell Programming in Linux value, the numerical value for "true" is 0, and "false" is 1. Those of you who have some programming experience will likely find this reversal of intuition as annoying as I do. Here is a way to get the result of the most recent logical test (and to show the weird reversal described above): $ts - . et e $eh $ co ? 0 $ts - xz et e y $eh $ co ? 1 Please remember this reversal, because it confounds the process of thinking through, and constructing, logical tests. For example, you may want to write a shortcut form for a test that only acts on one kind of result: $ts - .& eh "e. et e & co Ys" Ys e. This sort of shorthand relies on some knowledge of logical processing — if the left-hand part of an AND test yields "true", then the right-hand part must also be evaluated, and so it is. But the numerical "true" value for the left-hand test is 0, which would argue for the opposite logic. Just to show how perverse this all is, here is an example of Bash logical testing that comes out the opposite way: $eh $(0& 0) co ( & ) 0 $eh $(1& 0) co ( & ) 0 $eh $(0& 1) co ( & ) 0 $eh $(1& 1) co ( & ) 1 Yes, just as you would expect. So do be on guard against this shell "gotcha", which only affects the outcome of tests and command result values. It probably will not surprise you to learn that no one mentions this strange anomaly in the official Bash documentation. A couple of rules about logical operators used as branches: If you write "test && command", the command will only be executed if the test succeeds. If you write "test || command", the command will only be executed if the test fails. Run these tests: $tu & eh "e. re & co Ys" Ys e. $fle| eh "e. as | co Ys" Ys e. Notice that the outcomes are entirely in keeping with one's intuition about such logical comparisons, and all is well as long as you don't think about the fact that true equals 0. :) Here's another scheme commonly seen in shell script programming and interactive sessions: $cmad & cmad & cmad & cmad omn1 & omn2 & omn3 & omn4 This line of code will not run the next command in the sequence unless the prior command has returned "true", meaning no errors. It is a way to avoid running a command if a required prior outcome is not present. Loops and Repetition Here are some examples of loop operators: frf i * d o n n ; o eh "f" co $n dn oe In this example, the "*" is expanded by the shell to a list of all the files in the current directory, then each filename is applied to the loop control area. In such a construct, any whitespace-delimited list will do: arachnoid.com/linux/shell_programming.html 6/12
  • 7. 30/11/12 Bash Shell Programming in Linux frf i tmdc hry d o n n o ik ar; o eh "f" co $n dn oe $.msrp.h /ycits tm o dc ik hry ar This method will work for any list that uses spaces as delimiters. But what happens if you must parse a list that must be delimited by linefeeds instead of spaces, such as the case of a list of filenames or paths that contain spaces as part of their names? You can solve such a problem this way (there are other solutions): l - |wiera f;d s 1 hl ed n o eh "f" co $n dn oe This example uses an option to "ls" (note: the option is "-" followed by the numerical digit "1", not a lowercase "L") that formats file listings with one name per line, then this list is pipelined to a routine that reads lines until there are no more to read. This meets the requirement that linefeeds become the delimiters between list elements, not spaces. There is plenty more to this topic. Please refer to the list of for more. Using Numbers in Scripts Contrary to a sometimes-expressed view, numbers can easily be accommodated in scripts. Example: n1 = wie[$ -e6] d hl n l ; o eh $ co n ltn+ e + dn oe $.msrp.h /ycits 1 2 3 4 5 6 Notice the "let" command, which treats its argument in a way meant to accommodate numbers. Here is a somewhat more complex example: y1 = wie[$ -e1 ] d hl y l 2 ; o x1 = wie[$ -e1 ] d hl x l 2 ; o pit " 4"$($ *$ ) rnf % d ( x y ) ltx+ e + dn oe eh " co " lty+ e + dn oe $.msrp.h /ycits 1 2 3 4 5 6 7 8 9 10 11 12 2 4 6 8 1 1 1 1 1 0 2 4 6 8 20 22 24 3 6 9 1 1 1 2 2 2 2 5 8 1 4 7 30 33 36 4 8 1 1 2 2 2 3 3 2 6 0 4 8 2 6 40 44 48 arachnoid.com/linux/shell_programming.html 7/12
  • 8. 30/11/12 Bash Shell Programming in Linux 5 10 15 20 25 30 35 4 4 5 5 6 0 5 0 5 0 6 12 18 24 30 36 42 4 5 6 6 7 8 4 0 6 2 7 14 21 28 35 42 49 5 6 7 7 8 6 3 0 7 4 8 16 24 32 40 48 56 6 7 8 8 9 4 2 0 8 6 9 18 27 36 45 54 63 7 8 9 9 18 2 1 0 9 0 10 20 30 40 50 60 70 8 9 101010 0 0 0 1 2 11 22 33 44 55 66 77 8 9 101112 8 9 1 2 3 12 24 36 48 60 72 84 9 18101214 6 0 2 3 4 Coping with user input Here is an example that relies on user input to decide what to do. It exploits a shell feature as an easy way to create a menu of choices: P3"hoe(-)" S=Cos 15: eh "hoefo tels blw" co Cos rm h it eo. slc nm i rdgenbu ylo mgna eet ae n e re le elw aet do bek ra dn oe eh "o coe$ae" co Yu hs nm. When run, it looks like this: $.msrp.h /ycits Cos fo tels blw hoe rm h it eo. 1 rd ) e 2 gen ) re 3 bu ) le 4 ylo ) elw 5 mgna ) aet Cos (-)4 hoe 15: Yucoeylo. o hs elw As written, this menu code won't catch some kinds of errors (like a number that is out of range). In any application where the user choice must fall into defined bounds, be sure to perform a test on the result before using it. Example: i ["nm"=" ] te f $ae " ; hn eh "ro i ety" co Err n nr. ei 1 xt fi An advanced example with numbers and user input Here is an example guessing game that ties together some of the elements we've covered so far: sceNme=( (`ae+N /10)%10 + ) ertubr$( (dt %` 00 0) 1 ) ges- us=1 wie["ges ! "sceNme"] d hl $us" = $ertubr ; o eh - " a tikn o anme bten1ad10 Etryu ges" co n I m hnig f ubr ewe n 0. ne or us: ra ges ed us i ["ges =" ] te f $us" " ; hn eh "laeetranme. co Pes ne ubr" ei ["ges ="sceNme"] te lf $us" $ertubr ; hn eh - "ae!$us i tecretase! co e Ys ges s h orc nwr" ei ["sceNme"-t"ges ] te lf $ertubr g $us" ; hn eh "h sce nme i lre ta yu ges Tyaan" co Te ert ubr s agr hn or us. r gi. es le eh "h sce nme i salrta yu ges Tyaan" co Te ert ubr s mle hn or us. r gi. arachnoid.com/linux/shell_programming.html 8/12
  • 9. fi dn oe Please study this example carefully, and refer to the reference materials in to understand some of the methods. Creating and using arrays Shell arrays are relatively easy to construct. Example: ary(e genbu ylo mgna ra=rd re le elw aet) ln$#ra[] e={ary*} eh "h aryhs$e mmes Te ae" co Te ra a ln ebr. hy r: i0 = wie[$ -t$e ] d hl i l ln ; o eh "i $ary$]" co $: {ra[i} lti+ e + dn oe Run this example: $.msrp.h /ycits Tearyhs5mmes Te ae h ra a ebr. hy r: 0 rd : e 1 gen : re 2 bu : le 3 ylo : elw 4 mgna : aet Now, before you decide this is a silly, rather useless example, replace one line of the script and run it again: ary(l` ra=`s) See what difference this makes (and think of all the kinds of lists you might create for this line). Strings and substrings It's useful to be able to take strings apart and put them together in different ways. Here is how to select a substring from a string: srn=ti i asbtigts" tig"hs s usrn et sbtig$srn:09 usrn={tig1:} In this example, the variable "substring" contains the word "substring". Remember this rule: sbtig$srn_aibenm:trigpsto:egh usrn={tigvral_aesatn_oiinlnt} The string starting position is zero-based. Searching and Replacing Substrings within Strings In this method you can replace one or more instances of a string with another string. Here is the basic syntax:
  • 10. 30/11/12 Bash Shell Programming in Linux apa"hsi ats srn i wihtewr ts i rpae. lh=Ti s et tig n hc h od "et" s elcd" bt=$apats/elc} ea"{lh/etrpae" The string "beta" now contains an edited version of the original string in which the first case of the word "test" has been replaced by "replace". To replace all cases, not just the first, use this syntax: bt=$apa/etrpae" ea"{lh/ts/elc} Note the double "//" symbol. Here is an example in which we replace one string with another in a multi-line block of text: ls=ciktfo ctdg it"rce rg a o" pe=Iwnab axn om" an e Axi wa Idlv t b s ht ' oe o en I Ibcm axn f eae HwhpyIwudb.n o ap ol e" frcitri $it d o rte n ls; o eh - $pe/x$rte} co e {om//citr dn oe Run this example: $.msrp.h /ycits Iwnab acikt an e rce Acikti wa Idlv t b rce s ht ' oe o e I Ibcm acikt f eae rce HwhpyIwudb. o ap ol e Iwnab afo an e rg Afo i wa Idlv t b rg s ht ' oe o e I Ibcm afo f eae rg HwhpyIwudb. o ap ol e Iwnab act an e a Acti wa Idlv t b a s ht ' oe o e I Ibcm act f eae a HwhpyIwudb. o ap ol e Iwnab adg an e o Adgi wa Idlv t b o s ht ' oe o e I Ibcm adg f eae o HwhpyIwudb. o ap ol e Silly example, huh? It should be obvious that this search & replace capability could have many more useful purposes. More obscure but useful string operations Here is a way to isolate something useful from a large, even multi-line, string. As above, this method relies on enclosing a variable name in curly braces, then aplying a special operator to achieve a particular result. Here is a list of four such operators: Operator "#" means "delete from the left, to the first case of what follows." $x"hsi m ts srn. =Ti s y et tig" $eh $x*} co {# i m ts srn. s y et tig Operator "##" means "delete from the left, to the last case of what follows." arachnoid.com/linux/shell_programming.html 10/12
  • 11. $x"hsi m ts srn. =Ti s y et tig" $eh $x# } co {#* srn. tig Operator "%" means "delete from the right, to the first case of what follows." $x"hsi m ts srn. =Ti s y et tig" $eh $x * co {% } Ti i m ts hs s y et Operator "%%" means "delete from the right, to the last case of what follows." $x"hsi m ts srn. =Ti s y et tig" $eh $x%* co {% } Ti hs I find these operators particularly useful in parsing multi-line strings. Let's say I want to isolate a particular IP address from the output of the "ifconfig" command. Here's how I would proceed: $x`si/fofg =/bnicni` $eh $ co x eh t0 Ln ecpEhre Had 0:D5:C8:0 ik na:tent Wdr 00:60:D1 ie ad:9.6.. Bat1218025 Ms:5.5.5. nt dr121801 cs:9.6..5 ak2525250 ie6ad:f8:2d5f:ec81/4SoeLn nt dr e0:0:6ff0:d06 cp:ik U BODATRNIGMLIAT MU10 Mti: P RACS UNN UTCS T:50 erc1 R pces233 err: dopd0oern: fae0 X akt:539 ros0 rpe: vrus0 rm: T pces432 err: dopd0oern: crir0 X akt:279 ros0 rpe: vrus0 are: cliin: tqeee:00 olsos0 xuuln10 R bts3108 (44MB T bts46649(7. MB X ye:6505 3. i) X ye:9789 437 i) Bs ades0ec Mmr:ee00f500 ae drs:xc0 eoyf400-e000 lo Ln ecpLclLobc ik na:oa opak ie ad:2... Ms:5... nt dr17001 ak25000 ie6ad::118SoeHs nt dr :/2 cp:ot U LOBC RNIG MU146 Mti: P OPAK UNN T:63 erc1 R pces199 err: dopd0oern: fae0 X akt:034 ros0 rpe: vrus0 rm: T pces199 err: dopd0oern: crir0 X akt:034 ros0 rpe: vrus0 are: cliin: tqeee: olsos0 xuuln0 R bts1328 (17MB T bts1328 (17MB X ye:2730 1. i) X ye:2730 1. i) There's lots of information, more than we need. Let's say for the sake of argument that I want the IP of "lo", the loopback interface. I could specify this: $y$x*ntad: ={#ie dr} But, while gobbling text from the left, this search would stop at the IP address of eth0, not the desired interface. So I can specify it this way: $y$x*o*ntad: ={#l ie dr} As a last step I'll trim off all remaining text to the right:
  • 12. 30/11/12 Bash Shell Programming in Linux $y$y%* ={% } Leaving only the desired address. It seems the "#" and "%" operators, and their variants, are able to accept a rather complex argument and sort through the content of large strings, including strings with line breaks. This means I can use the shell to directly filter content in some simple cases where I might have considered using sed or Perl. Bash Version 3 I have always thought the inability to test for the presence of a string or pattern (without using grep, sed or something similar) was a conspicuous weakness in shell programming. Bash version 3, present on must current Linux distributions, addresses this lack by allowing regular expression matching. Let's say we need to establish whether variable $x appears to be a social security number: i [ $ = [-]3-09{}[-]4 ] f [ x ~ 09{}[-]2-09{} ] te hn #poesSN rcs S es le #piterrmsae rn ro esg fi Notice the Perlish "=~" syntax and that the regular expression appears within double brackets. A substantial number of regular expression metacharacters are supported, but not some of the Perl-specific extensions like w, d and s. Another Bash 3 feature is an improved brace expansion operator: $eh {.z co a.} abcdefghijklmnopqrstuvwxyz frni {.5 o n 0.} do eh $ co n dn oe 0 1 2 3 4 5 Useful Links Well, as long-winded as it turned out to be, this page is supposed to be an introduction to shell programming, one that just touches the highlights. The linked references below will provide a deeper understanding of the covered topics. A quick guide to writing scripts using the bash shell (Rutgers) Advanced Bash Scripting Guide (Linux Documentation Project) Bash Reference Manual (GNU Project, downloadable versions) Home | Linux | Bash Shell Programming in Linux Share This Page arachnoid.com/linux/shell_programming.html 12/12