1 /*- 2 * Copyright (c) 1980, 1991 The Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 */ 7 8 #ifndef lint 9 static char sccsid[] = "@(#)hist.c 5.9 (Berkeley) 06/08/91"; 10 #endif /* not lint */ 11 12 #include <sys/types.h> 13 #include <stdlib.h> 14 #if __STDC__ 15 # include <stdarg.h> 16 #else 17 # include <varargs.h> 18 #endif 19 20 #include "csh.h" 21 #include "extern.h" 22 23 static void hfree __P((struct Hist *)); 24 static void dohist1 __P((struct Hist *, int *, int, int, int)); 25 static void phist __P((struct Hist *, int, int)); 26 27 void 28 savehist(sp) 29 struct wordent *sp; 30 { 31 register struct Hist *hp, *np; 32 register int histlen = 0; 33 Char *cp; 34 35 /* throw away null lines */ 36 if (sp->next->word[0] == '\n') 37 return; 38 cp = value(STRhistory); 39 if (*cp) { 40 register Char *p = cp; 41 42 while (*p) { 43 if (!Isdigit(*p)) { 44 histlen = 0; 45 break; 46 } 47 histlen = histlen * 10 + *p++ - '0'; 48 } 49 } 50 for (hp = &Histlist; np = hp->Hnext;) 51 if (eventno - np->Href >= histlen || histlen == 0) 52 hp->Hnext = np->Hnext, hfree(np); 53 else 54 hp = np; 55 (void) enthist(++eventno, sp, 1); 56 } 57 58 struct Hist * 59 enthist(event, lp, docopy) 60 int event; 61 register struct wordent *lp; 62 bool docopy; 63 { 64 register struct Hist *np; 65 66 np = (struct Hist *) xmalloc((size_t) sizeof(*np)); 67 (void) time(&(np->Htime)); 68 np->Hnum = np->Href = event; 69 if (docopy) { 70 copylex(&np->Hlex, lp); 71 } 72 else { 73 np->Hlex.next = lp->next; 74 lp->next->prev = &np->Hlex; 75 np->Hlex.prev = lp->prev; 76 lp->prev->next = &np->Hlex; 77 } 78 np->Hnext = Histlist.Hnext; 79 Histlist.Hnext = np; 80 return (np); 81 } 82 83 static void 84 hfree(hp) 85 register struct Hist *hp; 86 { 87 88 freelex(&hp->Hlex); 89 xfree((ptr_t) hp); 90 } 91 92 void 93 dohist(vp) 94 Char **vp; 95 { 96 int n, rflg = 0, hflg = 0, tflg = 0; 97 98 if (getn(value(STRhistory)) == 0) 99 return; 100 if (setintr) 101 (void) sigsetmask(sigblock((sigset_t) 0) & ~sigmask(SIGINT)); 102 while (*++vp && **vp == '-') { 103 Char *vp2 = *vp; 104 105 while (*++vp2) 106 switch (*vp2) { 107 case 'h': 108 hflg++; 109 break; 110 case 'r': 111 rflg++; 112 break; 113 case 't': 114 tflg++; 115 break; 116 case '-': /* ignore multiple '-'s */ 117 break; 118 default: 119 stderror(ERR_HISTUS); 120 break; 121 } 122 } 123 if (*vp) 124 n = getn(*vp); 125 else { 126 n = getn(value(STRhistory)); 127 } 128 dohist1(Histlist.Hnext, &n, rflg, hflg, tflg); 129 } 130 131 static void 132 dohist1(hp, np, rflg, hflg, tflg) 133 struct Hist *hp; 134 int *np, rflg, hflg, tflg; 135 { 136 bool print = (*np) > 0; 137 138 for (; hp != 0; hp = hp->Hnext) { 139 (*np)--; 140 hp->Href++; 141 if (rflg == 0) { 142 dohist1(hp->Hnext, np, rflg, hflg, tflg); 143 if (print) 144 phist(hp, hflg, tflg); 145 return; 146 } 147 if (*np >= 0) 148 phist(hp, hflg, tflg); 149 } 150 } 151 152 static void 153 phist(hp, hflg, tflg) 154 register struct Hist *hp; 155 int hflg, tflg; 156 { 157 struct tm *t; 158 char ampm = 'a'; 159 160 if (hflg == 0) { 161 xprintf("%6d\t", hp->Hnum); 162 if (tflg == 0) { 163 t = localtime(&hp->Htime); 164 if (adrof(STRampm)) { /* addition by Hans J. Albertsson */ 165 if (t->tm_hour >= 12) { 166 if (t->tm_hour > 12) 167 t->tm_hour -= 12; 168 ampm = 'p'; 169 } 170 else if (t->tm_hour == 0) 171 t->tm_hour = 12; 172 xprintf("%2d:%02d%cm\t", t->tm_hour, t->tm_min, ampm); 173 } 174 else { 175 xprintf("%2d:%02d\t", t->tm_hour, t->tm_min); 176 } 177 } 178 } 179 prlex(&hp->Hlex); 180 } 181