|
|
1.1 root 1: /*
2: * Copyright (c) 1980 Regents of the University of California.
3: * All rights reserved.
4: *
5: * Redistribution and use in source and binary forms are permitted provided
6: * that: (1) source distributions retain this entire copyright notice and
7: * comment, and (2) distributions including binaries display the following
8: * acknowledgement: ``This product includes software developed by the
9: * University of California, Berkeley and its contributors'' in the
10: * documentation or other materials provided with the distribution and in
11: * all advertising materials mentioning features or use of this software.
12: * Neither the name of the University nor the names of its contributors may
13: * be used to endorse or promote products derived from this software without
14: * specific prior written permission.
15: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
16: * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
17: * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
18: */
19:
20: #ifndef lint
21: static char sccsid[] = "@(#)mkglue.c 5.8 (Berkeley) 6/1/90";
22: #endif /* not lint */
23:
24: /*
25: * Make the bus adaptor interrupt glue files.
26: */
27: #include <stdio.h>
28: #include "config.h"
29: #include "y.tab.h"
30: #include <ctype.h>
31:
32: /*
33: * Create the UNIBUS interrupt vector glue file.
34: */
35: ubglue()
36: {
37: register FILE *fp, *gp;
38: register struct device *dp, *mp;
39:
40: fp = fopen(path("ubglue.s"), "w");
41: if (fp == 0) {
42: perror(path("ubglue.s"));
43: exit(1);
44: }
45: gp = fopen(path("ubvec.s"), "w");
46: if (gp == 0) {
47: perror(path("ubvec.s"));
48: exit(1);
49: }
50: for (dp = dtab; dp != 0; dp = dp->d_next) {
51: mp = dp->d_conn;
52: if (mp != 0 && mp != (struct device *)-1 &&
53: !eq(mp->d_name, "mba")) {
54: struct idlst *id, *id2;
55:
56: for (id = dp->d_vec; id; id = id->id_next) {
57: for (id2 = dp->d_vec; id2; id2 = id2->id_next) {
58: if (id2 == id) {
59: dump_ubavec(fp, id->id,
60: dp->d_unit);
61: break;
62: }
63: if (!strcmp(id->id, id2->id))
64: break;
65: }
66: }
67: }
68: }
69: dump_std(fp, gp);
70: for (dp = dtab; dp != 0; dp = dp->d_next) {
71: mp = dp->d_conn;
72: if (mp != 0 && mp != (struct device *)-1 &&
73: !eq(mp->d_name, "mba")) {
74: struct idlst *id, *id2;
75:
76: for (id = dp->d_vec; id; id = id->id_next) {
77: for (id2 = dp->d_vec; id2; id2 = id2->id_next) {
78: if (id2 == id) {
79: dump_intname(fp, id->id,
80: dp->d_unit);
81: break;
82: }
83: if (!strcmp(id->id, id2->id))
84: break;
85: }
86: }
87: }
88: }
89: dump_ctrs(fp);
90: (void) fclose(fp);
91: (void) fclose(gp);
92: }
93:
94: static int cntcnt = 0; /* number of interrupt counters allocated */
95:
96: /*
97: * Print a UNIBUS interrupt vector.
98: */
99: dump_ubavec(fp, vector, number)
100: register FILE *fp;
101: char *vector;
102: int number;
103: {
104: char nbuf[80];
105: register char *v = nbuf;
106:
107: (void) sprintf(v, "%s%d", vector, number);
108: fprintf(fp, "\t.globl\t_X%s\n\t.align\t2\n_X%s:\n\tpushr\t$0x3f\n",
109: v, v);
110: fprintf(fp, "\tincl\t_fltintrcnt+(4*%d)\n", cntcnt++);
111: if (strncmp(vector, "dzx", 3) == 0)
112: fprintf(fp, "\tmovl\t$%d,r0\n\tjmp\tdzdma\n\n", number);
113: else {
114: if (strncmp(vector, "uur", 3) == 0) {
115: fprintf(fp, "#ifdef UUDMA\n");
116: fprintf(fp, "\tmovl\t$%d,r0\n\tjsb\tuudma\n", number);
117: fprintf(fp, "#endif\n");
118: }
119: fprintf(fp, "\tpushl\t$%d\n", number);
120: fprintf(fp, "\tcalls\t$1,_%s\n\tpopr\t$0x3f\n", vector);
121: fprintf(fp, "\tincl\t_cnt+V_INTR\n\trei\n\n");
122: }
123: }
124:
125: /*
126: * Create the VERSAbus interrupt vector glue file.
127: */
128: vbglue()
129: {
130: register FILE *fp, *gp;
131: register struct device *dp, *mp;
132:
133: fp = fopen(path("vbglue.s"), "w");
134: if (fp == 0) {
135: perror(path("vbglue.s"));
136: exit(1);
137: }
138: gp = fopen(path("vbvec.s"), "w");
139: if (gp == 0) {
140: perror(path("vbvec.s"));
141: exit(1);
142: }
143: for (dp = dtab; dp != 0; dp = dp->d_next) {
144: struct idlst *id, *id2;
145:
146: mp = dp->d_conn;
147: if (mp == 0 || mp == (struct device *)-1 ||
148: eq(mp->d_name, "mba"))
149: continue;
150: for (id = dp->d_vec; id; id = id->id_next)
151: for (id2 = dp->d_vec; id2; id2 = id2->id_next) {
152: if (id == id2) {
153: dump_vbavec(fp, id->id, dp->d_unit);
154: break;
155: }
156: if (eq(id->id, id2->id))
157: break;
158: }
159: }
160: dump_std(fp, gp);
161: for (dp = dtab; dp != 0; dp = dp->d_next) {
162: mp = dp->d_conn;
163: if (mp != 0 && mp != (struct device *)-1 &&
164: !eq(mp->d_name, "mba")) {
165: struct idlst *id, *id2;
166:
167: for (id = dp->d_vec; id; id = id->id_next) {
168: for (id2 = dp->d_vec; id2; id2 = id2->id_next) {
169: if (id2 == id) {
170: dump_intname(fp, id->id,
171: dp->d_unit);
172: break;
173: }
174: if (eq(id->id, id2->id))
175: break;
176: }
177: }
178: }
179: }
180: dump_ctrs(fp);
181: (void) fclose(fp);
182: (void) fclose(gp);
183: }
184:
185: /*
186: * Print a VERSAbus interrupt vector
187: */
188: dump_vbavec(fp, vector, number)
189: register FILE *fp;
190: char *vector;
191: int number;
192: {
193: char nbuf[80];
194: register char *v = nbuf;
195:
196: (void) sprintf(v, "%s%d", vector, number);
197: fprintf(fp, "SCBVEC(%s):\n", v);
198: fprintf(fp, "\tCHECK_SFE(4)\n");
199: fprintf(fp, "\tSAVE_FPSTAT(4)\n");
200: fprintf(fp, "\tPUSHR\n");
201: fprintf(fp, "\tincl\t_fltintrcnt+(4*%d)\n", cntcnt++);
202: fprintf(fp, "\tpushl\t$%d\n", number);
203: fprintf(fp, "\tcallf\t$8,_%s\n", vector);
204: fprintf(fp, "\tincl\t_cnt+V_INTR\n");
205: fprintf(fp, "\tPOPR\n");
206: fprintf(fp, "\tREST_FPSTAT\n");
207: fprintf(fp, "\trei\n\n");
208: }
209:
210: /*
211: * HP9000/300 interrupts are auto-vectored.
212: * Code is hardwired in locore.s
213: */
214: hpglue() {}
215:
216: static char *vaxinames[] = {
217: "clock", "cnr", "cnx", "tur", "tux",
218: "mba0", "mba1", "mba2", "mba3",
219: "uba0", "uba1", "uba2", "uba3"
220: };
221: static char *tahoeinames[] = {
222: "clock", "cnr", "cnx", "rmtr", "rmtx", "buserr",
223: };
224: static struct stdintrs {
225: char **si_names; /* list of standard interrupt names */
226: int si_n; /* number of such names */
227: } stdintrs[] = {
228: { vaxinames, sizeof (vaxinames) / sizeof (vaxinames[0]) },
229: { tahoeinames, (sizeof (tahoeinames) / sizeof (tahoeinames[0])) }
230: };
231: /*
232: * Start the interrupt name table with the names
233: * of the standard vectors not directly associated
234: * with a bus. Also, dump the defines needed to
235: * reference the associated counters into a separate
236: * file which is prepended to locore.s.
237: */
238: dump_std(fp, gp)
239: register FILE *fp, *gp;
240: {
241: register struct stdintrs *si = &stdintrs[machine-1];
242: register char **cpp;
243: register int i;
244:
245: fprintf(fp, "\n\t.globl\t_intrnames\n");
246: fprintf(fp, "\n\t.globl\t_eintrnames\n");
247: fprintf(fp, "\t.data\n");
248: fprintf(fp, "_intrnames:\n");
249: cpp = si->si_names;
250: for (i = 0; i < si->si_n; i++) {
251: register char *cp, *tp;
252: char buf[80];
253:
254: cp = *cpp;
255: if (cp[0] == 'i' && cp[1] == 'n' && cp[2] == 't') {
256: cp += 3;
257: if (*cp == 'r')
258: cp++;
259: }
260: for (tp = buf; *cp; cp++)
261: if (islower(*cp))
262: *tp++ = toupper(*cp);
263: else
264: *tp++ = *cp;
265: *tp = '\0';
266: fprintf(gp, "#define\tI_%s\t%d\n", buf, i*sizeof (long));
267: fprintf(fp, "\t.asciz\t\"%s\"\n", *cpp);
268: cpp++;
269: }
270: }
271:
272: dump_intname(fp, vector, number)
273: register FILE *fp;
274: char *vector;
275: int number;
276: {
277: register char *cp = vector;
278:
279: fprintf(fp, "\t.asciz\t\"");
280: /*
281: * Skip any "int" or "intr" in the name.
282: */
283: while (*cp)
284: if (cp[0] == 'i' && cp[1] == 'n' && cp[2] == 't') {
285: cp += 3;
286: if (*cp == 'r')
287: cp++;
288: } else {
289: putc(*cp, fp);
290: cp++;
291: }
292: fprintf(fp, "%d\"\n", number);
293: }
294:
295: /*
296: * Reserve space for the interrupt counters.
297: */
298: dump_ctrs(fp)
299: register FILE *fp;
300: {
301: struct stdintrs *si = &stdintrs[machine-1];
302:
303: fprintf(fp, "_eintrnames:\n");
304: fprintf(fp, "\n\t.globl\t_intrcnt\n");
305: fprintf(fp, "\n\t.globl\t_eintrcnt\n");
306: fprintf(fp, "\t.align 2\n");
307: fprintf(fp, "_intrcnt:\n");
308: fprintf(fp, "\t.space\t4 * %d\n", si->si_n);
309: fprintf(fp, "_fltintrcnt:\n");
310: fprintf(fp, "\t.space\t4 * %d\n", cntcnt);
311: fprintf(fp, "_eintrcnt:\n\n");
312: fprintf(fp, "\t.text\n");
313: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.