ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/cv/trans.c
Revision: 1.2
Committed: Mon Jul 8 10:17:37 1991 UTC (32 years, 8 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 1.1: +2 -2 lines
Log Message:
minor optimization

File Contents

# Content
1 /* Copyright (c) 1990 Regents of the University of California */
2
3 #ifndef lint
4 static char SCCSid[] = "$SunId$ LBL";
5 #endif
6
7 /*
8 * Translator utilities
9 *
10 * Greg Ward
11 */
12
13 #include <stdio.h>
14
15 #include "trans.h"
16
17
18 fgetid(idp, dls, fp) /* read an id up to char in dls from fp */
19 ID *idp;
20 char *dls;
21 register FILE *fp;
22 {
23 char dset[256/8];
24 char buf[MAXSTR];
25 register int c;
26 register char *cp;
27 /* create delimiter set */
28 for (cp = dset+sizeof(dset); cp-- > dset; )
29 *cp = 0;
30 for (cp = dls; *cp; cp++)
31 dset[*cp>>3] |= 1<<(*cp&7);
32 /* get characters up to delimiter */
33 cp = buf;
34 while ((c = getc(fp)) != EOF && !(dset[c>>3] & 1<<(c&7)))
35 *cp++ = c;
36 /* check for empty */
37 if (cp == buf) {
38 if (c == EOF)
39 return(EOF);
40 idp->number = 0;
41 idp->name = NULL;
42 return(0);
43 }
44 /* truncate space at end */
45 while (cp[-1] == ' ' || cp[-1] == '\t')
46 cp--;
47 *cp = '\0';
48 /* skip white space at beginning */
49 for (cp = buf; *cp && (*cp == ' ' || *cp == '\t'); cp++)
50 ;
51 /* assign value */
52 idp->number = atoi(cp);
53 idp->name = NULL;
54 /* check for ghost string */
55 if (!*cp)
56 return(0);
57 /* check for name */
58 if (idp->number == 0 && *cp != '0')
59 idp->name = savestr(cp);
60 return(0);
61 }
62
63
64 int
65 findid(idl, idp, insert) /* find (or insert) id in list */
66 register IDLIST *idl;
67 ID *idp;
68 int insert;
69 {
70 int upper, lower;
71 register int cm, i;
72 /* binary search */
73 lower = 0;
74 upper = cm = idl->nids;
75 while ((i = (lower + upper) >> 1) != cm) {
76 cm = idcmp(idp, &idl->id[i]);
77 if (cm > 0)
78 lower = i;
79 else if (cm < 0)
80 upper = i;
81 else
82 return(i);
83 cm = i;
84 }
85 if (!insert)
86 return(-1);
87 if (idl->nids == 0) { /* create new list */
88 idl->id = (ID *)malloc(sizeof(ID));
89 if (idl->id == NULL)
90 goto memerr;
91 } else { /* grow old list */
92 idl->id = (ID *)realloc((char *)idl->id,(idl->nids+1)*sizeof(ID));
93 if (idl->id == NULL)
94 goto memerr;
95 for (i = idl->nids; i > upper; i--) {
96 idl->id[i].number = idl->id[i-1].number;
97 idl->id[i].name = idl->id[i-1].name;
98 }
99 }
100 idl->nids++; /* insert new element */
101 idl->id[i].number = idp->number;
102 if (idp->name == NULL)
103 idl->id[i].name = NULL;
104 else
105 idl->id[i].name = savestr(idp->name);
106 return(i);
107 memerr:
108 eputs("Out of memory in findid\n");
109 quit(1);
110 }
111
112
113 int
114 idcmp(id1, id2) /* compare two identifiers */
115 register ID *id1, *id2;
116 {
117 /* names are greater than numbers */
118 if (id1->name == NULL)
119 if (id2->name == NULL)
120 return(id1->number - id2->number);
121 else
122 return(-1);
123 else
124 if (id2->name == NULL)
125 return(1);
126 else
127 return(strcmp(id1->name, id2->name));
128 }
129
130
131 write_quals(qlp, idl, fp) /* write out qualifier lists */
132 QLIST *qlp;
133 IDLIST idl[];
134 FILE *fp;
135 {
136 int i;
137
138 for (i = 0; i < qlp->nquals; i++)
139 if (idl[i].nids > 0) {
140 fprintf(fp, "qualifier %s begin\n", qlp->qual[i]);
141 fputidlist(&idl[i], fp);
142 fprintf(fp, "end\n");
143 }
144 }
145
146
147 fputidlist(qp, fp) /* put id list out to fp */
148 IDLIST *qp;
149 FILE *fp;
150 {
151 int fi;
152 register int i;
153 /* print numbers/ranges */
154 fi = 0;
155 for (i = 0; i < qp->nids && qp->id[i].name == NULL; i++)
156 if (i > 0 && qp->id[i].number > qp->id[i-1].number+1) {
157 if (i > fi+1)
158 fprintf(fp, "[%d:%d]\n", qp->id[fi].number,
159 qp->id[i-1].number);
160 else
161 fprintf(fp, "%d\n", qp->id[fi].number);
162 fi = i;
163 }
164 if (i-1 > fi)
165 fprintf(fp, "[%d:%d]\n", qp->id[fi].number,
166 qp->id[i-1].number);
167 else if (i > 0)
168 fprintf(fp, "%d\n", qp->id[fi].number);
169 for ( ; i < qp->nids; i++)
170 fprintf(fp, "\"%s\"\n", qp->id[i].name);
171 }
172
173
174 RULEHD *
175 getmapping(file, qlp) /* read in mapping file */
176 char *file;
177 QLIST *qlp;
178 {
179 char *err;
180 register int c;
181 RULEHD *mp = NULL;
182 int nrules = 0;
183 register RULEHD *rp;
184 register int qt;
185 char buf[MAXSTR];
186 FILE *fp;
187
188 if ((fp = fopen(file, "r")) == NULL) {
189 eputs(file);
190 eputs(": cannot open\n");
191 quit(1);
192 }
193 /* get each rule */
194 while (fscanf(fp, " %[^ ;\n]", buf) == 1) {
195 if (buf[0] == '#') { /* comment */
196 while ((c = getc(fp)) != EOF && c != '\n')
197 ;
198 continue;
199 }
200 rp = (RULEHD *)calloc(1, rulsiz(qlp->nquals));
201 if (rp == NULL)
202 goto memerr;
203 rp->mnam = savestr(buf);
204 for ( ; ; ) { /* get conditions */
205 while ((c = getc(fp)) != '(')
206 if (c == ';' || c == EOF)
207 goto endloop;
208 if (fscanf(fp, " %s ", buf) != 1) {
209 err = "missing variable";
210 goto fmterr;
211 }
212 if ((qt = qtype(buf, qlp)) == -1) {
213 err = "unknown variable";
214 goto fmterr;
215 }
216 if (rp->qflg & FL(qt)) {
217 err = "variable repeated";
218 goto fmterr;
219 }
220 rp->qflg |= FL(qt);
221 c = getc(fp);
222 switch (c) {
223 case '"': /* id name */
224 if (fscanf(fp, "%[^\"]\" )", buf) != 1) {
225 err = "bad string value";
226 goto fmterr;
227 }
228 idm(rp)[qt].nam = savestr(buf);
229 break;
230 case '[': /* id range */
231 if (fscanf(fp, "%d : %d ] )", &idm(rp)[qt].min,
232 &idm(rp)[qt].max) != 2) {
233 err = "bad range value";
234 goto fmterr;
235 }
236 if (idm(rp)[qt].min > idm(rp)[qt].max) {
237 err = "reverse range value";
238 goto fmterr;
239 }
240 break;
241 default: /* id number? */
242 if ((c < '0' || c > '9') && c != '-') {
243 err = "unrecognizable value";
244 goto fmterr;
245 }
246 ungetc(c, fp);
247 if (fscanf(fp, "%d )", &idm(rp)[qt].min) != 1) {
248 err = "bad number id";
249 goto fmterr;
250 }
251 idm(rp)[qt].max = idm(rp)[qt].min;
252 break;
253 }
254 }
255 endloop:
256 rp->next = mp;
257 mp = rp;
258 nrules++;
259 }
260 fclose(fp);
261 return(mp);
262 fmterr:
263 sprintf(buf, "%s: %s for rule %d\n", file, err, nrules+1);
264 eputs(buf);
265 quit(1);
266 memerr:
267 eputs("Out of memory in getmapping\n");
268 quit(1);
269 }
270
271
272 int
273 qtype(qnm, qlp) /* return number for qualifier name */
274 char *qnm;
275 register QLIST *qlp;
276 {
277 register int i;
278
279 for (i = 0; i < qlp->nquals; i++)
280 if (!strcmp(qnm, qlp->qual[i]))
281 return(i);
282 return(-1);
283 }
284
285
286 matchid(it, im) /* see if we match an id */
287 register ID *it;
288 register IDMATCH *im;
289 {
290 if (it->name == NULL) {
291 if (im->nam != NULL)
292 return(0);
293 return(it->number >= im->min && it->number <= im->max);
294 }
295 if (im->nam == NULL)
296 return(0);
297 return(!strcmp(it->name, im->nam));
298 }