ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/rt/persist.c
Revision: 2.3
Committed: Thu Jan 21 17:01:24 1993 UTC (31 years, 3 months ago) by greg
Content type: text/plain
Branch: MAIN
Changes since 2.2: +1 -0 lines
Log Message:
added code to reset ray counters and clock on persistent restart

File Contents

# Content
1 /* Copyright (c) 1993 Regents of the University of California */
2
3 #ifndef lint
4 static char SCCSid[] = "$SunId$ LBL";
5 #endif
6
7 /*
8 * Routines for persistent rtrace and rpict processes.
9 */
10
11 #include "standard.h"
12 #include "paths.h"
13 #include <signal.h>
14 #include <sys/types.h>
15 #include <sys/stat.h>
16
17 #ifndef TIMELIM
18 #define TIMELIM (8*3600) /* time limit for holding pattern */
19 #endif
20
21 extern char *strcpy(), *index();
22
23 extern int headismine; /* boolean true if header belongs to me */
24
25 static char *persistfname = NULL; /* persist file name */
26 static int persistfd = -1; /* persist file descriptor */
27
28 static char inpname[TEMPLEN+1], outpname[TEMPLEN+1];
29
30
31 pfdetach() /* release persist (and header) resources */
32 {
33 if (persistfd >= 0)
34 close(persistfd);
35 persistfd = -1;
36 persistfname = NULL;
37 inpname[0] = '\0';
38 outpname[0] = '\0';
39 headismine = 0;
40 }
41
42
43 pfclean() /* clean up persist files */
44 {
45 if (persistfd >= 0)
46 close(persistfd);
47 if (persistfname != NULL)
48 unlink(persistfname);
49 if (inpname[0])
50 unlink(inpname);
51 if (outpname[0])
52 unlink(outpname);
53 }
54
55
56 pflock(lf) /* place or release exclusive lock on file */
57 int lf;
58 {
59 struct flock fls;
60
61 fls.l_type = lf ? F_WRLCK : F_UNLCK;
62 fls.l_whence = 0;
63 fls.l_start = 0L;
64 fls.l_len = 0L;
65 if (fcntl(persistfd, F_SETLKW, &fls) < 0)
66 error(SYSTEM, "cannot (un)lock persist file");
67 }
68
69
70 persistfile(pfn) /* open persist file and lock it */
71 char *pfn;
72 {
73 persistfd = open(pfn, O_WRONLY|O_CREAT|O_EXCL, 0666);
74 if (persistfd >= 0) {
75 persistfname = pfn;
76 pflock(1);
77 return;
78 }
79 /* file exists -- switch to i/o process */
80 persistfd = open(pfn, O_RDWR);
81 if (persistfd < 0) {
82 sprintf(errmsg, "cannot open persist file \"%s\"", pfn);
83 error(SYSTEM, errmsg);
84 }
85 pflock(1);
86 io_process(); /* never returns */
87 }
88
89
90 int sig_noop() {}
91
92
93 pfhold() /* holding pattern for idle rendering process */
94 {
95 char buf[128];
96 register int n;
97 /* close input and output descriptors */
98 close(fileno(stdin));
99 fflush(stdout);
100 close(fileno(stdout));
101 /* create named pipes for input and output */
102 if (mknod(mktemp(strcpy(inpname,TEMPLATE)), S_IFIFO|0600) < 0)
103 goto createrr;
104 if (mknod(mktemp(strcpy(outpname,TEMPLATE)), S_IFIFO|0600) < 0)
105 goto createrr;
106 sprintf(buf, "%d\n%s\n%s\n", getpid(), inpname, outpname);
107 if (lseek(persistfd, 0L, 0) < 0)
108 error(SYSTEM, "seek error on persist file in pfhold");
109 n = strlen(buf);
110 if (write(persistfd, buf, n) < n)
111 error(SYSTEM, "error writing persist file in pfhold");
112 /* wait TIMELIM for someone to signal us */
113 signal(SIGIO, sig_noop);
114 alarm(TIMELIM);
115 pflock(0);
116 pause();
117 alarm(0);
118 signal(SIGIO, SIG_DFL);
119 pflock(1);
120 /* someone wants us; reopen stdin and stdout */
121 if (freopen(inpname, "r", stdin) == NULL)
122 goto openerr;
123 if (freopen(outpname, "w", stdout) == NULL)
124 goto openerr;
125 unlink(inpname);
126 inpname[0] = '\0';
127 unlink(outpname);
128 outpname[0] = '\0';
129 clean_slate(); /* reset time and ray counters */
130 return;
131 createrr:
132 error(SYSTEM, "cannot create named pipes in pfhold");
133 openerr:
134 error(SYSTEM, "cannot open named pipes in pfhold");
135 }
136
137
138 io_process() /* just act as conduits to and from actual process */
139 {
140 register char *cp;
141 register int nr, n;
142 char buf[4096], *pfin, *pfout;
143 int pid;
144 /* load and close persist file */
145 nr = read(persistfd, buf, sizeof(buf));
146 pfdetach();
147 if (nr < 0)
148 error(SYSTEM, "cannot read persist file");
149 buf[nr] = '\0';
150 if ((cp = index(buf, '\n')) == NULL)
151 goto formerr;
152 *cp++ = '\0';
153 if ((pid = atoi(buf)) <= 0)
154 goto formerr;
155 pfin = cp;
156 if ((cp = index(cp, '\n')) == NULL)
157 goto formerr;
158 *cp++ = '\0';
159 pfout = cp;
160 if ((cp = index(cp, '\n')) == NULL)
161 goto formerr;
162 *cp++ = '\0';
163 if (cp-buf != nr)
164 goto formerr;
165 /* wake up rendering process */
166 if (kill(pid, SIGIO) < 0)
167 error(SYSTEM, "cannot signal rendering process in io_process");
168 pid = fork(); /* fork i/o process */
169 if (pid < 0)
170 error(SYSTEM, "fork failed in io_process");
171 /* connect to appropriate pipe */
172 if (pid) { /* parent passes renderer output */
173 if (freopen(pfout, "r", stdin) == NULL)
174 error(SYSTEM, "cannot open input pipe in io_process");
175 } else { /* child passes renderer input */
176 if (freopen(pfin, "w", stdout) == NULL)
177 error(SYSTEM, "cannot open input pipe in io_process");
178 }
179 /* pass input to output */
180 cp = buf; n = sizeof(buf);
181 while ((nr = read(fileno(stdin), cp, n)) > 0) {
182 nr += cp-buf;
183 if ((n = write(fileno(stdout), buf, nr)) <= 0)
184 error(SYSTEM, "write error in io_process");
185 cp = buf;
186 while (n < nr)
187 *cp++ = buf[n++];
188 n = sizeof(buf) - (cp-buf);
189 }
190 fclose(stdin);
191 fclose(stdout);
192 if (pid) /* parent waits for child */
193 wait(0);
194 exit(0); /* all done, exit (not quit!) */
195 formerr:
196 error(USER, "format error in persist file");
197 }