|
|
1.1 root 1: #include "hdr.h"
2:
3: #define LARGE 100000
4:
5: static int delta0[256];
6: static char cmap[256];
7: static char *bmpat;
8:
9: bmprep(pattern)
10: char *pattern;
11: {
12: register int j, patlen;
13:
14: patlen = strlen(bmpat = pattern);
15: for(j = 0; j < 256; j++){
16: delta0[j] = patlen;
17: cmap[j] = j;
18: }
19: for(j = 0; j < patlen-1; j++)
20: delta0[pattern[j]] = patlen-j-1;
21: delta0[pattern[patlen-1]] = LARGE;
22: if(iflag){
23: for(j = 0; j < patlen-1; j++)
24: if(islower(pattern[j]))
25: delta0[toupper(pattern[j])] = patlen-j-1;
26: if(islower(pattern[patlen-1]))
27: delta0[toupper(pattern[patlen-1])] = LARGE;
28: for(j = 'A'; j <= 'Z'; j++)
29: cmap[j] = tolower(j);
30: }
31: }
32:
33: bmexecute(file)
34: char *file;
35: {
36: register char *p;
37: register char *endpt;
38: register char *s;
39: register int j;
40: int len, patlen = strlen(bmpat);
41: char *rdpt;
42: int fd, eof, n;
43: long seek;
44: char *nlp, *proc, *np, *op;
45: char buf[8*8192];
46:
47: if(file){
48: if((fd = open(file, 0)) < 0){
49: fprint(2, "egrep: can't open %s\n", file);
50: badbotch=1;
51: return;
52: }
53: } else
54: fd = 0;
55: lnum = 1;
56: tln = 0;
57: rdpt = buf;
58: seek = 0;
59: for(eof = 0; eof == 0;){
60: Fflush(1);
61: if((n = read(fd, rdpt, &buf[sizeof buf]-rdpt)) <= 0){
62: if(rdpt == buf)
63: break; /* eof, nothing left to process */
64: *rdpt = '\n'; /* terminate */
65: endpt = rdpt+1;
66: eof = 1;
67: } else {
68: for(p = &rdpt[n]; p >= rdpt;)
69: if(*--p == '\n')
70: break;
71: if(p < rdpt){ /* line bigger than buf!! */
72: rdpt = &buf[sizeof buf/2]; /* chop in half */
73: continue; /* reading */
74: }
75: endpt = p+1;
76: }
77: /*
78: invariants:
79: no newline between buf and rdpt[-1]
80: lnum = nlines before buf
81: seek = char offset of buf[0]
82: last char read is rdpt[n-1]
83: first char after last \n is endpt
84:
85: following is exited to three places:
86: succeed: match
87: refresh: !match (readjust ptrs and loop)
88:
89: */
90: p = buf+patlen-1;
91: proc = buf-1;
92: scan:
93: for(;;){
94: while((p += delta0[*(unsigned char *)p]) < endpt)
95: ;
96: if(p < (buf+LARGE)){ /* no match */
97: goto refresh;
98: }
99: p -= LARGE;
100: for(j = patlen-2, s = p-1; j >= 0; j--)
101: if(cmap[*s--] != bmpat[j])
102: break;
103: if(j < 0) /* match!! */
104: goto succeed;
105: fail:
106: p++;
107: }
108: succeed:
109: if(bmegrep || !cflag || !sflag){ /* lflag doesn't matter */
110: nlp = memchr(p, '\n', (endpt+1)-p);
111: op = p;
112: p -= patlen-1;
113: while(*p != '\n')
114: if(--p < buf) break;
115: p++;
116: if(bmegrep)
117: if(legrep(p) == 0){
118: p = op;
119: goto fail;
120: }
121: }
122: nsucc = 1;
123: if (cflag){
124: tln++;
125: p = nlp+1;
126: goto scan;
127: } else if(sflag)
128: ; /* ugh */
129: else if(lflag){
130: Fprint(1, "%s\n", file);
131: close(fd);
132: return;
133: } else {
134: if (nfile > 1 && hflag)
135: Fprint(1, "%s:", file);
136: if (bflag)
137: Fprint(1, "%ld:", (seek+(p-buf))/BLKSIZE);
138: if (nflag){
139: while(np = memchr(proc+1, '\n', p-proc)){
140: lnum++;
141: proc = np;
142: }
143: Fprint(1, "%ld:", lnum);
144: }
145: Fwrite(1, p, nlp-p+1);
146: p = nlp+1;
147: if(p < endpt)
148: goto scan;
149: }
150: refresh:
151: if(nflag){ /* count newlines that we haven't proc */
152: while(proc = memchr(proc+1, '\n', endpt-proc))
153: lnum++;
154: }
155: memcpy(buf, endpt, j = &rdpt[n]-endpt);
156: rdpt = &buf[j];
157: seek += n;
158: }
159: done: close(fd);
160: if (cflag) {
161: if (nfile > 1)
162: Fprint("%s:", file);
163: Fprint(1, "%ld\n", tln);
164: }
165: }
166:
167: /*
168: isn't egrep pretty when it just has to mtach or not?
169: */
170:
171: legrep(p)
172: register char *p;
173: {
174: register State *cstat, *t;
175:
176: if(reinit == 1)
177: clearg();
178: cstat = istat;
179: if(cstat->out)
180: return(1);
181: for(;;){
182: if((t = cstat->gotofn[*(unsigned char *)p]) == 0)
183: cstat = nxtst(cstat, *(unsigned char *)p);
184: else
185: cstat = t;
186: if(cstat->out){
187: return(1);
188: }
189: if(*p++ == RIGHT){
190: return(0);
191: }
192: }
193: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.