|
|
1.1 root 1: #ifdef RCSIDENT
2: static char rcsid[] = "$Header: recsio.c,v 1.7 85/01/18 15:38:05 notes Rel $";
3: #endif RCSIDENT
4:
5: /*
6: * init(io,p), finish(io) struct io_f *io, char *p
7: * initopens the three i/o files and initializes session stats
8: *
9: * finish(io) closes all those files.
10: *
11: * getnrec, putnrec, getrrec, putrrec
12: * getdscr, putdscr, gettrec, puttrec
13: * each gets or puts physical records inside its appropriate file.
14: *
15: */
16:
17: #include "parms.h"
18: #include "structs.h"
19: #include <sys/types.h>
20: #include <sys/stat.h>
21:
22: long lseek (); /* for sake of lint */
23:
24: init (io, p) struct io_f *io;
25: char *p;
26: {
27: int i; /* counter */
28: struct auth_f me; /* identify self */
29:
30: if ((i = opennf (io, p)) < 0) /* try to open */
31: {
32: return (i); /* bad luck opening */
33: }
34:
35: getdscr (io, &io -> descr);
36: if (io -> descr.d_format != DBVERSION) /* bad version */
37: {
38: printf ("%s: wrong database format (is %ld, want %ld)\n",
39: io -> fullname, io -> descr.d_format, (long) DBVERSION);
40: closenf (io); /* close files */
41: return (QUITBAD);
42: }
43: getname (&me, 0); /* grab identity for permissions */
44: getperms (io, 0, me.aname); /* go establish access rights */
45:
46: io -> nrspwrit = io -> nnotwrit = 0; /* set up stats */
47: io -> nrspread = io -> nnotread = 0;
48: io -> nnotxmit = io -> nrspxmit = 0;
49: io -> nnotrcvd = io -> nrsprcvd = 0;
50: io -> nnotdrop = io -> nrspdrop = 0;
51: io -> norphans = io -> adopted = 0;
52: io -> xstring[0] = io -> xauthor[0] = '\0'; /* clear search strings */
53:
54: time (&io -> entered); /* get entry time */
55:
56: return (0); /* all set */
57: }
58:
59: /*
60: * Open a notesfile.
61: *
62: * given a name, pick the appropriate notesfile. This includes
63: * searching along "search paths" once we get that implemented.
64: * Absolute path names are permitted.
65: */
66:
67: opennf (io, p)
68: struct io_f *io;
69: char *p;
70: {
71: char fn[WDLEN];
72: char *q,
73: *r,
74: *s;
75: char *endname;
76: int i;
77: struct stat statbuf;
78:
79: if (p != (char *) NULL)
80: { /* newly-opened */
81: if (*p == '/') /* explicit path */
82: {
83: q = rindex (p, '/'); /* find last '/' */
84: for (r = p, s = io -> basedir; r < q;) /* copy directory */
85: *s++ = *r++;
86: *s++ = '\0'; /* terminate */
87: endname = ++q;
88: }
89: else
90: {
91: /*
92: * This is where we should start looking for the
93: * notesfile along a search path.
94: */
95: strcpy (io -> basedir, Mstdir); /* default dir */
96: endname = p; /* for errors */
97: }
98:
99: if (chkpath (endname))
100: {
101: printf ("Invalid notefile name: '%s'\n", p);
102: return (QUITBAD);
103: }
104: q = endname;
105: r = io -> nf;
106: i = NNLEN;
107: while ((*r++ = *q++) && --i); /* notesfile name */
108:
109: sprintf (fn, "%s/%s", io -> basedir, endname); /* open the directory */
110: if (stat (fn, &statbuf) != 0) /* see if directory */
111: {
112: printf ("No such notesfile: '%s'\n", p);
113: return (QUITNEX);
114: }
115: }
116:
117: sprintf (io -> fullname, "%s/%s", io -> basedir, io -> nf);
118:
119: sprintf (fn, "%s/%s", io -> fullname, TEXT);
120: if ((io -> fidtxt = open (fn, 2)) < 0)
121: {
122: return (QUITBAD); /* bad nf */
123: }
124:
125: sprintf (fn, "%s/%s", io -> fullname, INDEXN);
126: if ((io -> fidndx = open (fn, 2)) < 0)
127: {
128: close (io -> fidtxt);
129: return (QUITBAD);
130: }
131:
132: sprintf (fn, "%s/%s", io -> fullname, INDEXR);
133: if ((io -> fidrdx = open (fn, 2)) < 0)
134: {
135: close (io -> fidtxt);
136: close (io -> fidndx);
137: return (QUITBAD); /* bad nf */
138: }
139:
140: return 0; /* all's well */
141: }
142:
143:
144: finish (io)
145: struct io_f *io;
146: {
147: long left;
148: struct when_f lvtime; /* for days used */
149:
150: #ifdef STATS /* if keeping statistics */
151: locknf (io, DSCRLOCK); /* update statistics */
152: getdscr (io, &io -> descr);
153: io -> descr.d_notwrit += io -> nnotwrit;
154: io -> descr.d_rspwrit += io -> nrspwrit;
155: io -> descr.d_notread += io -> nnotread;
156: io -> descr.d_rspread += io -> nrspread;
157: io -> descr.d_notxmit += io -> nnotxmit;
158: io -> descr.d_rspxmit += io -> nrspxmit;
159: io -> descr.d_notrcvd += io -> nnotrcvd;
160: io -> descr.d_rsprcvd += io -> nrsprcvd;
161: io -> descr.d_notdrop += io -> nnotdrop;
162: io -> descr.d_rspdrop += io -> nrspdrop;
163: io -> descr.d_orphans += io -> norphans;
164: io -> descr.d_adopted += io -> adopted;
165: io -> descr.entries++; /* count of entries */
166: time (&left);
167: io -> descr.walltime += left - io -> entered; /* time spent in nf */
168: gettime (&lvtime);
169: if ((lvtime.w_day != io -> descr.d_lastuse.w_day) ||
170: (lvtime.w_month != io -> descr.d_lastuse.w_month) ||
171: (lvtime.w_year != io -> descr.d_lastuse.w_year))
172: {
173: io -> descr.d_daysused++;
174: copydate (&lvtime, &io -> descr.d_lastuse);
175: }
176: putdscr (io, &io -> descr); /* update the block */
177: unlocknf (io, DSCRLOCK);
178: #endif STATS /* end of stats gathering */
179:
180: closenf (io);
181: }
182:
183: closenf (io)
184: struct io_f *io;
185: {
186:
187: x (close (io -> fidtxt) < 0, "finish: text fail");
188: x (close (io -> fidndx) < 0, "finish: nindx fail");
189: x (close (io -> fidrdx) < 0, "finish: rindx fail");
190: }
191:
192:
193:
194: getnrec (io, n, note) struct note_f *note; /* n is the number of the note to get. 0 is policy note */
195: struct io_f *io;
196: {
197: long where; /* going to seek here eventually */
198: struct descr_f *descr; /* for sizeof below */
199:
200: x (n < 0, "getnrec: negative recnum");
201: where = sizeof (*descr) + n * sizeof (*note);
202: x (lseek (io -> fidndx, where, 0) < 0, "getnrec: seek");
203: x (read (io -> fidndx, note, sizeof *note) < sizeof *note, "getnrec: read");
204: }
205:
206: putnrec (io, n, note) struct note_f *note; /* n is the number of the note to put. 0 is policy note */
207: struct io_f *io;
208: {
209: long where; /* going to seek here eventually */
210: struct descr_f *descr; /* for sizeof below */
211:
212: x (n < 0, "putnrec: negative recnum");
213: where = sizeof (*descr) + n * sizeof (*note);
214: x (lseek (io -> fidndx, where, 0) < 0, "putnrec: seek");
215: x (write (io -> fidndx, note, sizeof *note) < sizeof *note, "putnrec: write ");
216: }
217:
218: getdscr (io, descr) struct descr_f *descr;
219: struct io_f *io;
220: {
221:
222: x (lseek (io -> fidndx, 0L, 0) < 0, "getdscr: seek");
223: x (read (io -> fidndx, descr, sizeof *descr) < sizeof *descr, "getdscr: read");
224: }
225:
226: putdscr (io, descr) struct descr_f *descr;
227: struct io_f *io;
228: {
229:
230: x (lseek (io -> fidndx, 0L, 0) < 0, "putdscr: seek");
231: x (write (io -> fidndx, descr, sizeof *descr) < sizeof *descr, "putdscr: write");
232: }
233:
234: getrrec (io, n, resp) struct resp_f *resp; /* n is the number of the resp to get */
235: struct io_f *io;
236: {
237: long where; /* going to seek here eventually */
238: int a; /* size of free link */
239: x (n < 0, "getrrec: negative recnum");
240:
241: where = sizeof a + n * sizeof (*resp);
242: x (lseek (io -> fidrdx, where, 0) < 0, "getrrec: seek");
243: x (read (io -> fidrdx, resp, sizeof *resp) < sizeof *resp, "getrrec: read");
244: }
245:
246: putrrec (io, n, resp) struct resp_f *resp; /* n is the number of the resp to put */
247: struct io_f *io;
248: {
249: long where; /* going to seek here eventually */
250: int a; /* size of free link */
251: x (n < 0, "putrrec: negative recnum");
252:
253: where = sizeof a + n * sizeof (*resp);
254: x (lseek (io -> fidrdx, where, 0) < 0, "putrrec: seek");
255: x (write (io -> fidrdx, resp, sizeof *resp) < sizeof *resp, "putrrec: write");
256: }
257:
258: /*
259: * puttrec(i&io_f, &FILE, &daddr_f, long)
260: *
261: * reads cound characters from the input stream specified ad
262: * puts them into the text file. The address is returned...
263: *
264: * Almost identical to the code in "pagein.c" and should
265: * probably be the same code with the third parameter being
266: * the count and meaning "until EOF" if -1 or something..
267: *
268: * Ray Essick May 8, 1982
269: */
270: long puttrec (io, zfile, where, count)
271: struct io_f *io;
272: FILE * zfile;
273: struct daddr_f *where;
274: long count;
275: {
276:
277: int i;
278: long nchars;
279: long ignored;
280: int ignoring;
281: struct daddr_f nwhere;
282: struct txtbuf_f buf; /* hold bunches of text */
283:
284: if (count == 0) /* empty text */
285: {
286: where -> addr = 0;
287: where -> textlen = 0; /* standard empty */
288: return ((long) 0);
289: }
290:
291: locknf (io, TXTLOCK); /* grab access to the file */
292: x (lseek (io -> fidtxt, 0L, 0) < 0, "puttrec: bad seek 0");
293: x (read (io -> fidtxt, where, sizeof nwhere) < 0, "puttrec: read 0");
294: x (lseek (io -> fidtxt, where -> addr, 0) < 0, "puttrec:badseek");
295:
296: nchars = 0;
297: ignored = 0;
298: ignoring = 0;
299: i = 0;
300: while ((nchars + ignored) != count) /* grab input */
301: {
302: if (!ignoring)
303: {
304: if (i == BUFSIZE) /* flush full buffer */
305: {
306: x (write (io -> fidtxt, buf.txtbuf, BUFSIZE) != BUFSIZE,
307: "puttrec: bad text");
308: i = 0; /* reset buffer */
309: }
310: buf.txtbuf[i++] = getc (zfile);
311: if (++nchars >= io -> descr.d_longnote) /* gotta truncate */
312: ignoring++; /* start now */
313: }
314: else
315: {
316: (void) getc (zfile); /* punt */
317: ignored++;
318: }
319: }
320: if (i) /* write partial buf */
321: x (write (io -> fidtxt, buf.txtbuf, i) != i, "puttrec: bad text");
322: if (ignored) /* write warning */
323: {
324: sprintf (buf.txtbuf, "\n\n%s ignored %ld excess bytes\n",
325: System, ignored);
326: i = strlen (buf.txtbuf); /* get length */
327: x (write (io -> fidtxt, buf.txtbuf, i) != i, "puttrec: bad text");
328: nchars += i; /* count extras */
329: }
330: /*
331: * fix count of characters sucked in daddr_f structure
332: */
333: where -> textlen = nchars; /* fill header */
334: /*
335: * now fix the free pointer
336: */
337: x (lseek (io -> fidtxt, 0L, 0) < 0, "puttrec:bad reseek");
338: nwhere.addr = where -> addr + nchars;
339: if (nwhere.addr & 1) /* odd ? */
340: nwhere.addr++; /* round to word boundary */
341: x (write (io -> fidtxt, &nwhere, sizeof nwhere) != sizeof nwhere, "puttrec: badupdate");
342:
343: unlocknf (io, TXTLOCK);
344: return ((long) nchars);
345: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.