gpaul@opus.cdc.com (Gerry Paul ) (03/18/89)
... while trying to learn more about csh and shell scripts...
What I would like to do is to edit a previous entry on the history list
and execute it, much as I can on a Symbolics machine.
The closest I am able to do is to make one change to a prior command.
Eg history ...4 echo 'fred'
5 ....
I can do a !4:s/fred/wanda which executes echo 'wanda'
To "simplify" this, I would like to create a shell command which would
do the same thing so I could enter (the admittedly not much simpler)
h 4 /fred/wanda instead of !4:s/fred/wanda
My unsuccessful attempts look like this
alias h '!\!^:s\!$'
While I don't think I have the quotes, backquotes, etc right yet, a bigger
problem seems to loom in the evaluation sequence. First I need the
history entry number from the prior command, ie, !^ or 4 in this
example. Then I need to prepend the ! to get the !4 command...
Can I do this within csh? Can I use EVAL in this?
Also, is there a more general way to re-edit a prior entry?
Gerry Paul INTERNET: gpaul@shamash.cdc.com
UUCP: {rosevax,umn-cs,bungia,ems}!shamash!gpaul
Gerry Paul INTERNET: gpaul@shamash.cdc.com
UUCP: {rosevax,umn-cs,bungia,ems}!shamash!gpaulmaart@cs.vu.nl (Maarten Litmaath) (03/21/89)
: This is a shar archive. Extract with sh, not csh.
: This archive ends with exit, so do not worry about trailing junk.
: --------------------------- cut here --------------------------
PATH=/bin:/usr/bin:/usr/ucb
echo Extracting 'cmde.c'
sed 's/^X//' > 'cmde.c' << '+ END-OF-FILE ''cmde.c'
X/*
X * To use this history command line editing facility, set the following alias:
X *
X * alias ! 'cmde ~/.cmde ! && source ~/.cmde'
X *
X * (Put 'cmde' in your path.)
X * If your history character is some other character than '!', just change
X * EVERY occurrence of '!' into your char.
X * When you want to invoke 'cmde', just type '!' and hit return.
X * Now you can type the remaining characters to complete the history
X * reference, just as if you typed them adjacent to the '!', e.g.:
X *
X * % !
X * d
X * or
X * % !
X * ?foo
X * or
X * % !
X * -3
X * or
X * % !
X * 56
X *
X * Type '!' or just return to obtain the previous command, or ^D to quit the
X * editor. If you didn't quit, you'll end up in a 1 line vi editor; type 'ZZ'
X * or ':x' to end the editing.
X * Author: Maarten Litmaath @ VU Informatika Amsterdam (maart@cs.vu.nl)
X */
X
X#include <stdio.h>
X
X
Xmain(argc, argv)
Xint argc;
Xchar **argv;
X{
X FILE *fp, *fopen();
X char h, *gets(), buf[512], *adjust(), *check();
X int c;
X
X
X if (argc != 3 && argc != 4) {
X fprintf(stderr, "Argc error.\n");
X exit(1);
X }
X
X if (!(fp = fopen(argv[1], "w"))) {
X perror(argv[1]);
X exit(1);
X }
X
X h = *argv[2];
X
X if (argc == 3) { /* first pass */
X if (!gets(buf))
X exit(1);
X
X fprintf(fp,
X "echo \"%c%s:q\" | %s %s %c 2; ex +open %s; source %s\n",
X h, !*buf || *buf == h ? "-2" :
X *buf == '-' ? adjust(buf) :
X *buf == '?' ? check(buf) : buf,
X argv[0], argv[1], h, argv[1], argv[1]);
X
X exit(0);
X }
X
X /* second pass */
X
X while ((c = getchar()) != EOF) {
X if (c == h) {
X switch (c = getchar()) {
X case ' ':
X case '\t':
X case '\n':
X case '=':
X case '(':
X break;
X default:
X putc('\\', fp);
X }
X putc(h, fp);
X }
X putc(c, fp);
X }
X
X exit(0);
X}
X
X
Xchar *adjust(s)
Xchar *s;
X{
X static char buf[8] = "-";
X char *sprintf();
X
X
X if (*++s < '0' || *s > '9')
X return --s;
X
X (void) sprintf(buf + 1, "%d", atoi(s) + 1);
X
X return buf;
X}
X
X
Xchar *check(s)
Xregister char *s;
X{
X static char buf[32] = "?";
X register char *p = buf + 1;
X char *save = s++;
X
X
X while (*p = *s++)
X if (*p++ == '?')
X return save;
X *p++ = '?';
X *p = '\0';
X return buf;
X}
+ END-OF-FILE cmde.c
chmod 'u=rw,g=r,o=r' 'cmde.c'
set `wc -c 'cmde.c'`
count=$1
case $count in
2097) :;;
*) echo 'Bad character count in ''cmde.c' >&2
echo 'Count should be 2097' >&2
esac
exit 0
--
Modeless editors and strong typing: |Maarten Litmaath @ VU Amsterdam:
both for people with weak memories. |maart@cs.vu.nl, mcvax!botter!maart