home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / misc / volume1 / 8709 / 15 < prev    next >
Encoding:
Internet Message Format  |  1990-07-13  |  6.9 KB

  1. Path: uunet!husc6!necntc!ncoast!allbery
  2. From: rickers@RUTGERS.EDU@drexel.UUCP (Rick Wargo)
  3. Newsgroups: comp.sources.misc
  4. Subject: directory stack manipulation routines for bourne shell
  5. Keywords: pushd, popd, dirs ...
  6. Message-ID: <4563@ncoast.UUCP>
  7. Date: 24 Sep 87 02:39:22 GMT
  8. Sender: allbery@ncoast.UUCP
  9. Organization: Drexel University, Phila., Pa.
  10. Lines: 194
  11. Approved: allbery@ncoast.UUCP
  12. X-Archive: comp.sources.misc/8709/15
  13.  
  14.  
  15.  
  16. Hello ( is there a better greeting that does not sound so boring? ) -
  17.  
  18.         Having been  working  for  a  long  time  under  csh  and  being
  19. accustomed  to  the commands pushd and popd, I was saddened to find that
  20. these commands were not avaiable under  my  version  of  Microport  Unix
  21. System  V (version 2.2).  I had just come across ksh routines to do this
  22. and thought, hey, what a wonderful way to spend a few hours  instead  of
  23. doing  something that I should be doing (like real work 8-).  The result
  24. is my first csh program (all other shell programs  where  written  using
  25. the  bourne shell).  It is used with a few (four) alias-es and manages a
  26. directory stack.  Hope you find it useful.
  27.  
  28.         If you decide to give this a try, wait  until  using  it  before
  29. reading  the next sentence.  You shouldn't be reading this unless you've
  30. tried it already - okay - experienced it? -  well  ...  it  may  not  be
  31. incredibly fast, but the object was to learn a bit of the c shell.
  32.  
  33.  
  34.                                                   Rickers
  35.                                                   ..!drexel!rickers
  36.  
  37. ==========c=u=t====h=e=r=e=====================c=u=t====h=e=r=e=========
  38. #!/bin/csh
  39. #
  40. #    (-8 tab stops should be at every four for easy readibility 8-)
  41. #
  42. #    dirstack  --  c shell script to manipulate a directory stack
  43. #                    written by rickers, august 29, 1987
  44. #
  45. #    Permission is granted to do what you wish with this code.  Happily
  46. #    placed in the public domain.  No copyrights - no nutin'.
  47. #
  48. #    Description of routines:
  49. #        init  --  initializes the environment so that the routines can work.
  50. #        dirs  --  prints out directory stack.
  51. #        pushd --  push the current directory and change to that specified
  52. #        popd  --  pop a directory and change to it
  53. #
  54. #    These routines pattern themselves after the same functions of the
  55. #    C shell, with a few exceptions.  Idea to write this script taken from
  56. #    ksh script originally written by David C. Stewart, and modified to
  57. #    work under MKS tookkit ksh by Keith Ericson, both of Tektronix Inc.
  58. #
  59. #    To use, some aliases are needed.  These follow.
  60. #        set dirstack=/usr/local/lib/dirstack
  61. #        alias    initds        "set argv=(init \!*);  source $dirstack; set argv"
  62. #        alias    dirs        "set argv=(dirs \!*);  source $dirstack; set argv"
  63. #        alias    pushd        "set argv=(pushd \!*); source $dirstack; set argv"
  64. #        alias    popd        "set argv=(popd \!*);  source $dirstack; set argv"
  65. #        unset dirstack
  66. #
  67. #    This file should be placed in a known directory.  The dirstack variable
  68. #    is just to make the alias look a bit neater.
  69. #
  70. #    You may be pondering with the question "why did he do it this way?"  when
  71. #    i figure it out, i will let you know (maybe).  it just seemed the thing to
  72. #    do.  note these need routines need to be executed using source.  it is 
  73. #    faster    (it does not invoke another shell) and it makes the variable
  74. #    available to the shell.
  75. #    
  76. #    Oh, btw, the other reason this was written, was to make up for a lacking
  77. #    csh under Microport Unix System V 2.2.
  78. #
  79.  
  80. #
  81. #    Depending on argv[1], goto a certain spot in the script and execute 
  82. #    
  83. goto $argv[1]
  84.  
  85. init:
  86. #    the current directory stack depth
  87.     set ddepth=1
  88.  
  89. #    dstack is the directory stack, set to a max depth of 20
  90.     set dstack=(`pwd` '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '')
  91.     goto finish
  92.  
  93. #
  94. #    dirs is equivalent (almost) to the csh command `dirs'.  It prints out
  95. #    the stack, current directory first, followed by top of stack, and the
  96. #    rest of the stack.  it fmt-s the output so it looks nice and does not
  97. #    get fold-ed at 80 chars.  It is a bit slow - oh well, so are the rest
  98. #    of the routines.
  99. #
  100. dirs:
  101.     set i=$ddepth
  102.     if ( $i == 1 ) set dstack[1]=`pwd`
  103.     cp /dev/null /tmp/$$
  104.     while ($i > 0)
  105.         echo $dstack[$i] >> /tmp/$$
  106.         @ i = $i - 1
  107.     end
  108.     sed "s,$home,\~,g" /tmp/$$ | fmt ; rm /tmp/$$
  109.     goto finish
  110.  
  111. #
  112. #    pushd is stretching from the csh definition of pushd.  given one arg,
  113. #    it pushes the current directory on the stack, and changes to the
  114. #    specified directory.  now comes the kludge.  to specify a buried
  115. #    directory, use the syntax: pushd + n.  note the space between the
  116. #    plus sign and the number.  It is there to make life easier and faster.
  117. #    you wouldn't want it any other way now, would you?  also, the way it
  118. #    works is different from the way my pushd works (under 4.2BSD).  It 
  119. #    exchanges the current directory and the specified directory, making
  120. #    the specified directory current.  note that the number is offset to
  121. #    the current directory on the dirs print-out ( + 1 is top of stack ).
  122. #    also note that the current directory is not on the top of the stack.
  123. #    pushd given with no arguments is the exact same as pushd + 1, and 
  124. #    exchanges the current directory with the top to the stack.
  125. #
  126. pushd:
  127.     switch ($#argv)
  128.     case 1:
  129.         if ( $ddepth < 2 ) then
  130.             echo pushd: No other directory.
  131.             goto finish
  132.         else
  133.             @ i = $ddepth - 1
  134.             set temp=$dstack[$i]
  135.             set dstack[$i]=$dstack[$ddepth]
  136.             set dstack[$ddepth]=$temp
  137.             cd $dstack[$ddepth]
  138.         endif
  139.         breaksw
  140.     case 2:
  141.         if ( $ddepth == 1 ) set dstack[1]=`pwd`
  142.         @ ddepth++
  143.         cd $argv[2]
  144.         set dstack[$ddepth]=`pwd`
  145.         breaksw
  146.     case 3:
  147.         @ i = $argv[3]
  148.         @ i = $ddepth - $i
  149.         set temp=$dstack[$i]
  150.         set dstack[$i]=$dstack[$ddepth]
  151.         set dstack[$ddepth]=$temp
  152.         cd $dstack[$ddepth]
  153.         breaksw
  154.     default:
  155.         echo usage: pushd \| pushd name \| pushd +n
  156.         goto finish
  157.     endsw
  158.     goto dirs
  159.  
  160. #
  161. #    popd is stretching from the csh definition of popd.  given no args,
  162. #    it pops one directory from the stack and makes it current, assuming
  163. #    that one exists.  again a kludge (same one).  to specify a buried
  164. #    directory, use the syntax: popd + n.  note the space between the
  165. #    plus sign and the number.  same old argument as above.  but, ha, this
  166. #    one actually works like the csh popd.  oh well, there goes the large
  167. #    deviation.  what this action does is removes the specifed directory
  168. #    from the directory stack.  again, note that the number is offset to
  169. #    the current directory on the dirs print-out ( + 1 is top of stack ).
  170. #    also note that the current directory is not on the top of the stack,
  171. #    although it is the first printed in the dirs output.
  172. #
  173. popd:
  174.     if ( $ddepth == 1 ) then
  175.         echo popd: Directory stack empty.
  176.         goto finish
  177.     else switch ($#argv)
  178.     case 1:
  179.         breaksw
  180.     case 2:
  181.         echo usage: popd \[ + n \]
  182.         goto finish
  183.         breaksw
  184.     case 3:
  185.         if ( ($argv[3] < 1) || ($argv[3] >= $ddepth) ) then
  186.             echo popd: Illegal value.
  187.             goto finish
  188.         endif
  189.         @ i = $ddepth - $argv[3]
  190.         while ( $i < $ddepth )
  191.             @ temp = $i + 1
  192.             set dstack[$i]=$dstack[$temp]
  193.             @ i = $i + 1
  194.         end
  195.         breaksw
  196.     endsw
  197.     endif
  198.     @ ddepth--
  199.     cd $dstack[$ddepth]
  200.     goto dirs
  201.  
  202. #
  203. #    finishup is the generic get outta here routine.
  204. #    
  205. finish:
  206.     unset i
  207.     unset temp
  208.