]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - bin/csh/hist.c
unfinished sblive driver, playback/mixer only for now - not enabled in
[FreeBSD/FreeBSD.git] / bin / csh / hist.c
1 /*-
2  * Copyright (c) 1980, 1991, 1993
3  *      The Regents of the University of California.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  * 3. All advertising materials mentioning features or use of this software
14  *    must display the following acknowledgement:
15  *      This product includes software developed by the University of
16  *      California, Berkeley and its contributors.
17  * 4. Neither the name of the University nor the names of its contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33
34 #ifndef lint
35 #if 0
36 static char sccsid[] = "@(#)hist.c      8.1 (Berkeley) 5/31/93";
37 #else
38 static const char rcsid[] =
39   "$FreeBSD$";
40 #endif
41 #endif /* not lint */
42
43 #include <sys/types.h>
44 #if __STDC__
45 # include <stdarg.h>
46 #else
47 # include <varargs.h>
48 #endif
49
50 #include "csh.h"
51 #include "extern.h"
52
53 static void     hfree __P((struct Hist *));
54 static void     dohist1 __P((struct Hist *, int *, int, int));
55 static void     phist __P((struct Hist *, int));
56
57 void
58 savehist(sp)
59     struct wordent *sp;
60 {
61     struct Hist *hp, *np;
62     int histlen = 0;
63     Char   *cp;
64
65     /* throw away null lines */
66     if (sp->next->word[0] == '\n')
67         return;
68     cp = value(STRhistory);
69     if (*cp) {
70         Char *p = cp;
71
72         while (*p) {
73             if (!Isdigit(*p)) {
74                 histlen = 0;
75                 break;
76             }
77             histlen = histlen * 10 + *p++ - '0';
78         }
79     }
80     for (hp = &Histlist; (np = hp->Hnext) != NULL;)
81         if (eventno - np->Href >= histlen || histlen == 0)
82             hp->Hnext = np->Hnext, hfree(np);
83         else
84             hp = np;
85     (void) enthist(++eventno, sp, 1);
86 }
87
88 struct Hist *
89 enthist(event, lp, docopy)
90     int     event;
91     struct wordent *lp;
92     bool    docopy;
93 {
94     struct Hist *np;
95
96     np = (struct Hist *) xmalloc((size_t) sizeof(*np));
97     np->Hnum = np->Href = event;
98     if (docopy) {
99         copylex(&np->Hlex, lp);
100     }
101     else {
102         np->Hlex.next = lp->next;
103         lp->next->prev = &np->Hlex;
104         np->Hlex.prev = lp->prev;
105         lp->prev->next = &np->Hlex;
106     }
107     np->Hnext = Histlist.Hnext;
108     Histlist.Hnext = np;
109     return (np);
110 }
111
112 static void
113 hfree(hp)
114     struct Hist *hp;
115 {
116
117     freelex(&hp->Hlex);
118     xfree((ptr_t) hp);
119 }
120
121 void
122 /*ARGSUSED*/
123 dohist(v, t)
124     Char **v;
125     struct command *t;
126 {
127     int     n, rflg = 0, hflg = 0;
128
129     if (getn(value(STRhistory)) == 0)
130         return;
131     if (setintr)
132         (void) sigsetmask(sigblock(0) & ~sigmask(SIGINT));
133     while (*++v && **v == '-') {
134         Char   *vp = *v;
135
136         while (*++vp)
137             switch (*vp) {
138             case 'h':
139                 hflg++;
140                 break;
141             case 'r':
142                 rflg++;
143                 break;
144             case '-':           /* ignore multiple '-'s */
145                 break;
146             default:
147                 stderror(ERR_HISTUS);
148                 break;
149             }
150     }
151     if (*v)
152         n = getn(*v);
153     else {
154         n = getn(value(STRhistory));
155     }
156     dohist1(Histlist.Hnext, &n, rflg, hflg);
157 }
158
159 static void
160 dohist1(hp, np, rflg, hflg)
161     struct Hist *hp;
162     int    *np, rflg, hflg;
163 {
164     bool    print = (*np) > 0;
165
166     for (; hp != 0; hp = hp->Hnext) {
167         (*np)--;
168         hp->Href++;
169         if (rflg == 0) {
170             dohist1(hp->Hnext, np, rflg, hflg);
171             if (print)
172                 phist(hp, hflg);
173             return;
174         }
175         if (*np >= 0)
176             phist(hp, hflg);
177     }
178 }
179
180 static void
181 phist(hp, hflg)
182     struct Hist *hp;
183     int     hflg;
184 {
185     if (hflg == 0)
186         (void) fprintf(cshout, "%6d\t", hp->Hnum);
187     prlex(cshout, &hp->Hlex);
188 }