ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/hd/rhoptimize.c
Revision: 3.7
Committed: Mon Feb 1 09:56:18 1999 UTC (25 years, 2 months ago) by gwlarson
Content type: text/plain
Branch: MAIN
Changes since 3.6: +1 -1 lines
Log Message:
made caching code slightly more efficient

File Contents

# Content
1 /* Copyright (c) 1999 Silicon Graphics, Inc. */
2
3 #ifndef lint
4 static char SCCSid[] = "$SunId$ SGI";
5 #endif
6
7 /*
8 * Optimize holodeck for quick access.
9 *
10 * 11/4/98 Greg Ward Larson
11 */
12
13 #include "holo.h"
14
15 #include <signal.h>
16
17 #ifndef BKBSIZE
18 #define BKBSIZE 256 /* beam clump size (kilobytes) */
19 #endif
20
21 char *progname;
22 char tempfile[128];
23 int dupchecking = 0;
24
25 extern char *rindex();
26 extern int quit();
27 extern long rhinitcopy();
28
29
30 main(argc, argv)
31 int argc;
32 char *argv[];
33 {
34 char *inpname, *outname;
35 int hdfd[2];
36 long nextipos, lastopos, thisopos;
37
38 progname = argv[0];
39 argv++; argc--; /* duplicate checking flag? */
40 if (argc > 1 && !strcmp(argv[0], "-u")) {
41 dupchecking++;
42 argv++; argc--;
43 }
44 if (argc < 1 | argc > 2) {
45 fprintf(stderr, "Usage: %s [-u] input.hdk [output.hdk]\n",
46 progname);
47 exit(1);
48 }
49 inpname = argv[0]; /* get input file */
50 argv++; argc--;
51 if (argc == 1) /* use given output file */
52 outname = argv[0];
53 else { /* else use temporary file */
54 if (access(inpname, R_OK|W_OK) < 0) { /* check permissions */
55 sprintf(errmsg, "cannot access \"%s\"", inpname);
56 error(SYSTEM, errmsg);
57 }
58 strcpy(tempfile, inpname);
59 if ((outname = rindex(tempfile, '/')) != NULL)
60 outname++;
61 else
62 outname = tempfile;
63 sprintf(outname, "rho%d.hdk", getpid());
64 outname = tempfile;
65 }
66 /* copy holodeck file header */
67 nextipos = rhinitcopy(hdfd, inpname, outname);
68 lastopos = 0L; /* copy sections one by one */
69 while (nextipos != 0L) {
70 /* set input position; get next */
71 lseek(hdfd[0], nextipos, 0);
72 read(hdfd[0], (char *)&nextipos, sizeof(nextipos));
73 /* get output position; set last */
74 thisopos = lseek(hdfd[1], 0L, 2);
75 if (lastopos > 0L) {
76 lseek(hdfd[1], lastopos, 0);
77 write(hdfd[1], (char *)&thisopos, sizeof(thisopos));
78 lseek(hdfd[1], 0L, 2);
79 }
80 lastopos = thisopos;
81 thisopos = 0L; /* write place holder */
82 write(hdfd[1], (char *)&thisopos, sizeof(thisopos));
83 /* copy holodeck section */
84 copysect(hdfd[0], hdfd[1]);
85 }
86 /* clean up */
87 close(hdfd[0]);
88 close(hdfd[1]);
89 if (outname == tempfile && rename(outname, inpname) < 0) {
90 sprintf(errmsg, "cannot rename \"%s\" to \"%s\"",
91 outname, inpname);
92 error(SYSTEM, errmsg);
93 }
94 exit(0);
95 }
96
97
98 long
99 rhinitcopy(hfd, infn, outfn) /* open files and copy header */
100 int hfd[2]; /* returned file descriptors */
101 char *infn, *outfn;
102 {
103 FILE *infp, *outfp;
104 long ifpos;
105 /* open files for i/o */
106 if ((infp = fopen(infn, "r")) == NULL) {
107 sprintf(errmsg, "cannot open \"%s\" for reading", infn);
108 error(SYSTEM, errmsg);
109 }
110 if ((outfp = fopen(outfn, "w+")) == NULL) {
111 sprintf(errmsg, "cannot open \"%s\" for writing", outfn);
112 error(SYSTEM, errmsg);
113 }
114 /* set up signal handling */
115 if (signal(SIGINT, quit) == SIG_IGN) signal(SIGINT, SIG_IGN);
116 if (signal(SIGHUP, quit) == SIG_IGN) signal(SIGHUP, SIG_IGN);
117 if (signal(SIGTERM, quit) == SIG_IGN) signal(SIGTERM, SIG_IGN);
118 #ifdef SIGXCPU
119 if (signal(SIGXCPU, quit) == SIG_IGN) signal(SIGXCPU, SIG_IGN);
120 if (signal(SIGXFSZ, quit) == SIG_IGN) signal(SIGXFSZ, SIG_IGN);
121 #endif
122 /* copy and verify header */
123 if (checkheader(infp, HOLOFMT, outfp) < 0 || getw(infp) != HOLOMAGIC)
124 error(USER, "input not in holodeck format");
125 fputformat(HOLOFMT, outfp);
126 fputc('\n', outfp);
127 putw(HOLOMAGIC, outfp);
128 /* get descriptors and free stdio */
129 if ((hfd[0] = dup(fileno(infp))) < 0 ||
130 (hfd[1] = dup(fileno(outfp))) < 0)
131 error(SYSTEM, "dup call failed in rhinitcopy");
132 ifpos = ftell(infp);
133 fclose(infp);
134 if (fclose(outfp) == EOF)
135 error(SYSTEM, "file flushing error in rhinitcopy");
136 /* check cache size */
137 if (BKBSIZE*1024*1.5 > hdcachesize)
138 hdcachesize = BKBSIZE*1024*1.5;
139 /* return input position */
140 return(ifpos);
141 }
142
143
144 int
145 nuniq(rva, n) /* sort unique rays to front of beam list */
146 register RAYVAL *rva;
147 int n;
148 {
149 register int i, j;
150 RAYVAL rtmp;
151
152 for (j = 0; j < n; j++)
153 for (i = j+1; i < n; i++)
154 if ( rva[i].d == rva[j].d &&
155 rva[i].r[0][0]==rva[j].r[0][0] &&
156 rva[i].r[0][1]==rva[j].r[0][1] &&
157 rva[i].r[1][0]==rva[j].r[1][0] &&
158 rva[i].r[1][1]==rva[j].r[1][1] ) {
159 n--; /* swap duplicate with end */
160 copystruct(&rtmp, rva+n);
161 copystruct(rva+n, rva+i);
162 copystruct(rva+i, &rtmp);
163 i--; /* recheck one we swapped */
164 }
165 return(n);
166 }
167
168
169 static BEAMI *beamdir;
170
171 static int
172 bpcmp(b1p, b2p) /* compare beam positions on disk */
173 int *b1p, *b2p;
174 {
175 register long pdif = beamdir[*b1p].fo - beamdir[*b2p].fo;
176
177 if (pdif < 0L) return(-1);
178 return(pdif > 0L);
179 }
180
181 static HOLO *hout;
182
183 static int
184 xferclump(hp, bq, nb) /* transfer the given clump to hout and free */
185 HOLO *hp;
186 int *bq, nb;
187 {
188 register int i;
189 register BEAM *bp;
190 int n;
191
192 beamdir = hp->bi; /* sort based on file position */
193 qsort((char *)bq, nb, sizeof(*bq), bpcmp);
194 /* transfer and free each beam */
195 for (i = 0; i < nb; i++) {
196 bp = hdgetbeam(hp, bq[i]);
197 DCHECK(bp==NULL, CONSISTENCY, "empty beam in xferclump");
198 n = dupchecking ? nuniq(hdbray(bp),bp->nrm) : bp->nrm;
199 bcopy((char *)hdbray(bp), (char *)hdnewrays(hout,bq[i],n),
200 n*sizeof(RAYVAL));
201 hdfreebeam(hp, bq[i]);
202 }
203 hdfreebeam(hout, 0); /* write & free clump */
204 return(0);
205 }
206
207 copysect(ifd, ofd) /* copy holodeck section from ifd to ofd */
208 int ifd, ofd;
209 {
210 HOLO *hinp;
211 /* load input section directory */
212 hinp = hdinit(ifd, NULL);
213 /* create output section directory */
214 hout = hdinit(ofd, (HDGRID *)hinp);
215 /* clump the beams */
216 clumpbeams(hinp, 0, BKBSIZE*1024, xferclump);
217 /* clean up */
218 hddone(hinp);
219 hddone(hout);
220 }
221
222
223 eputs(s) /* put error message to stderr */
224 register char *s;
225 {
226 static int midline = 0;
227
228 if (!*s)
229 return;
230 if (!midline++) { /* prepend line with program name */
231 fputs(progname, stderr);
232 fputs(": ", stderr);
233 }
234 fputs(s, stderr);
235 if (s[strlen(s)-1] == '\n') {
236 fflush(stderr);
237 midline = 0;
238 }
239 }
240
241
242 quit(code) /* exit the program gracefully */
243 int code;
244 {
245 if (tempfile[0])
246 unlink(tempfile);
247 exit(code);
248 }