added "more" command
[unix-history] / usr / src / usr.bin / error / filter.c
CommitLineData
442fe3bf
DF
1/*
2 * Copyright (c) 1980 Regents of the University of California.
3 * All rights reserved. The Berkeley software License Agreement
4 * specifies the terms and conditions for redistribution.
5 */
6
7#ifndef lint
8static char sccsid[] = "@(#)filter.c 5.1 (Berkeley) %G%";
9#endif not lint
10
3a5a3cc6
BJ
11#include <stdio.h>
12#include <ctype.h>
13#include <pwd.h>
14#include "error.h"
15
16char *lint_libs[] = {
17 IG_FILE1,
18 IG_FILE2,
19 IG_FILE3,
20 IG_FILE4,
21 0
22};
23extern char* processname;
24int lexsort();
25/*
26 * Read the file ERRORNAME of the names of functions in lint
27 * to ignore complaints about.
28 */
29getignored(auxname)
30 char *auxname;
31{
58195f21
RH
32 reg int i;
33 FILE *fyle;
34 char inbuffer[256];
35 int uid;
36 char filename[128];
37 char *username;
38 struct passwd *passwdentry;
3a5a3cc6
BJ
39
40 nignored = 0;
41 if (auxname == 0){ /* use the default */
42 if ( (username = (char *)getlogin()) == NULL){
43 username = "Unknown";
44 uid = getuid();
45 if ( (passwdentry = (struct passwd *)getpwuid(uid)) == NULL){
46 return;
47 }
48 } else {
49 if ( (passwdentry = (struct passwd *)getpwnam(username)) == NULL)
50 return;
51 }
52 strcpy(filename, passwdentry->pw_dir);
58195f21 53 (void)strcat(filename, ERRORNAME);
3a5a3cc6 54 } else
58195f21 55 (void)strcpy(filename, auxname);
3a5a3cc6
BJ
56#ifdef FULLDEBUG
57 printf("Opening file \"%s\" to read names to ignore.\n",
58 filename);
59#endif
60 if ( (fyle = fopen(filename, "r")) == NULL){
61#ifdef FULLDEBUG
62 fprintf(stderr, "%s: Can't open file \"%s\"\n",
63 processname, filename);
64#endif
65 return;
66 }
67 /*
68 * Make the first pass through the file, counting lines
69 */
70 for (nignored = 0; fgets(inbuffer, 255, fyle) != NULL; nignored++)
71 continue;
72 names_ignored = (char **)Calloc(nignored+1, sizeof (char *));
73 fclose(fyle);
74 if (freopen(filename, "r", fyle) == NULL){
75#ifdef FULLDEBUG
76 fprintf(stderr, "%s: Failure to open \"%s\" for second read.\n",
77 processname, filename);
78#endif
79 nignored = 0;
80 return;
81 }
82 for (i=0; i < nignored && (fgets (inbuffer, 255, fyle) != NULL); i++){
83 names_ignored[i] = strsave(inbuffer);
58195f21 84 (void)substitute(names_ignored[i], '\n', '\0');
3a5a3cc6
BJ
85 }
86 qsort(names_ignored, nignored, sizeof *names_ignored, lexsort);
87#ifdef FULLDEBUG
88 printf("Names to ignore follow.\n");
89 for (i=0; i < nignored; i++){
90 printf("\tIgnore: %s\n", names_ignored[i]);
91 }
92#endif
93}
94
95int lexsort(cpp1, cpp2)
96 char **cpp1, **cpp2;
97{
98 return(strcmp(*cpp1, *cpp2));
99}
100
101int search_ignore(key)
102 char *key;
103{
58195f21
RH
104 reg int ub, lb;
105 reg int halfway;
106 int order;
3a5a3cc6
BJ
107
108 if (nignored == 0)
109 return(-1);
110 for(lb = 0, ub = nignored - 1; ub >= lb; ){
111 halfway = (ub + lb)/2;
112 if ( (order = strcmp(key, names_ignored[halfway])) == 0)
113 return(halfway);
114 if (order < 0) /*key is less than probe, throw away above*/
115 ub = halfway - 1;
116 else
117 lb = halfway + 1;
118 }
119 return(-1);
120}
121
122/*
123 * Tell if the error text is to be ignored.
124 * The error must have been canonicalized, with
125 * the file name the zeroth entry in the errorv,
126 * and the linenumber the second.
127 * Return the new categorization of the error class.
128 */
129Errorclass discardit(errorp)
58195f21 130 reg Eptr errorp;
3a5a3cc6 131{
58195f21
RH
132 int language;
133 reg int i;
3a5a3cc6
BJ
134 Errorclass errorclass = errorp->error_e_class;
135
136 switch(errorclass){
137 case C_SYNC:
138 case C_NONSPEC:
139 case C_UNKNOWN: return(errorclass);
140 default: ;
141 }
142 if(errorp->error_lgtext < 2){
143 return(C_NONSPEC);
144 }
145 language = errorp->error_language;
146 if(language == INLINT){
147 if (errorclass != C_NONSPEC){ /* no file */
148 for(i=0; lint_libs[i] != 0; i++){
149 if (strcmp(errorp->error_text[0], lint_libs[i]) == 0){
150 return(C_DISCARD);
151 }
152 }
153 }
154 /* check if the argument to the error message is to be ignored*/
155 if (ispunct(lastchar(errorp->error_text[2])))
156 clob_last(errorp->error_text[2], '\0');
157 if (search_ignore(errorp->error_text[errorclass == C_NONSPEC ? 0 : 2]) >= 0){
158 return(C_NULLED);
159 }
160 }
161 return(errorclass);
162}