|
|
1.1 root 1: /* $Header: dl.c,v 10.3 86/02/01 15:46:40 tony Rel $ */
2: /* dl.c downloads code into the vs100. Routines are
3: *
4: * DownLoad Determines device version and downloads firmware
5: *
6: * Takes an int which is the device to download and
7: * returns 0 if everything went well and -1 if
8: * there is some problem.
9: *
10: */
11:
12: /****************************************************************************
13: * *
14: * Copyright (c) 1983, 1984 by *
15: * DIGITAL EQUIPMENT CORPORATION, Maynard, Massachusetts. *
16: * All rights reserved. *
17: * *
18: * This software is furnished on an as-is basis and may be used and copied *
19: * only with inclusion of the above copyright notice. This software or any *
20: * other copies thereof may be provided or otherwise made available to *
21: * others only for non-commercial purposes. No title to or ownership of *
22: * the software is hereby transferred. *
23: * *
24: * The information in this software is subject to change without notice *
25: * and should not be construed as a commitment by DIGITAL EQUIPMENT *
26: * CORPORATION. *
27: * *
28: * DIGITAL assumes no responsibility for the use or reliability of its *
29: * software on equipment which is not supplied by DIGITAL. *
30: * *
31: * *
32: ****************************************************************************/
33:
34: #include "vs100.h"
35: #include <sys/ioctl.h>
36: #include "vsioctl.h"
37: #include "vssite.h"
38:
39: #define CODE_START_ADDRESS 0x1000
40:
41: #define BUFSIZE 512 /* Why not? Everyone uses 512 */
42:
43: int HexArray[128];
44: #define Hex2(p) ((HexArray[*(p)]<<4)+HexArray[*((p)+1)])
45:
46: extern int vsdev; /* File number of the workstation */
47: BitMap screen; /* The actual screen memory */
48:
49: /* Determine what version of the vs we have and download the appropriate
50: * firmware. Determining the version is not trivial and as versions change
51: * this may also have to change.
52: */
53:
54: int DownLoad ()
55: {
56: FILE *fopen(), *fd; /* The file descriptor */
57: char *AllocateSpace();
58: char *filename; /* Name of download file */
59: char *buf; /* The input buffer */
60: char inline[BUFSIZE]; /* The line from the file */
61: int bufpos; /* The current position in the buffer */
62: int linesize; /* The number of bytes represented by a line */
63: int lineaddr; /* The intended address of the line */
64: int nextaddr; /* The expected next address */
65: int destaddr; /* The destination for the current buffer */
66: caddr_t pMem; /* Program memory pointer */
67: caddr_t startAddr; /* Address to start microcode */
68: MemArea programMemory; /* Information about program memory */
69: char textVersion[5]; /* The version number reported back */
70: int version;
71: char errmessage[BUFSIZE]; /* error message buffer */
72:
73: /* Initialize the device,
74: * figure out just what version of the device we have, and
75: * get the address to load the code into
76: */
77:
78: if (PacketInit() ||
79: ioctl (vsdev, (int) VSIOINIT, (caddr_t) NULL) ||
80: ioctl (vsdev, (int) VSIOGETVER, (caddr_t) &version) ||
81: ReportStatus ((int *) textVersion, (short *) NULL, (short *) NULL,
82: &screen, (MemArea *) NULL, &programMemory,
83: (MemArea *) NULL, 1)) {
84: VSError ();
85: return(-1);
86: }
87:
88: switch (version) {
89: case 8:
90:
91: /* Everyone in the world reports 8! Fortunately I can
92: tell them apart by other means (Then why isn't that
93: the version??? You tell me!) */
94:
95: if (screen.bm_height != 800) filename = LOAD_FILE_3_8;
96: else filename = LOAD_FILE_2B;
97: break;
98:
99: case 1: /* This is an SBO, I think! */
100: filename = LOAD_FILE_SBO;
101: break;
102:
103: default:
104:
105: /* Assume we have a 3.10. We may even be right */
106:
107: filename = LOAD_FILE_3_10;
108: break;
109: }
110:
111: pMem = *(caddr_t *) programMemory.m_base;
112: startAddr = pMem + CODE_START_ADDRESS;
113:
114: /* Open the file in read mode */
115:
116: if ((fd = fopen (filename, "r")) == NULL) {
117: sprintf(errmessage, "Xvs100: Can't open uCode file %s.\n",
118: filename);
119: DeviceError(errmessage);
120: return (-1);
121: }
122:
123: InitHexArray();
124:
125: /* Read in the s-line file and copy to the workstation */
126:
127: bufpos = 0;
128: buf = AllocateSpace (BUFSIZE);
129: destaddr = 0;
130:
131: while (fgets (inline, BUFSIZE, fd) != NULL) {
132: if (inline[0] == '\n') continue;
133: if (ParseLine (inline, &linesize, &lineaddr)) break;
134: if (destaddr == 0) destaddr = nextaddr = lineaddr;
135: if (bufpos > 0 &&
136: (lineaddr != nextaddr || linesize + bufpos > BUFSIZE)) {
137: if (MoveObjectDownRom (buf, pMem + destaddr, bufpos))
138: return (-1);
139: buf = AllocateSpace (BUFSIZE);
140: bufpos = 0;
141: destaddr = nextaddr = lineaddr;
142: }
143: CopyLine (inline, buf, linesize, bufpos);
144: bufpos += linesize;
145: nextaddr += linesize;
146: }
147:
148: /* Copy the last packet */
149:
150: if (bufpos > 0) {
151: if (MoveObjectDownRom (buf, pMem + destaddr, bufpos))
152: return (-1);
153: }
154:
155: fclose (fd);
156:
157: /* Sync the writes to make sure it's all been downloaded! */
158:
159: if (SynchWrites()) return (-1);
160:
161: /* Start microcode */
162:
163: if (ioctl (vsdev, (int) VSIOSTART, (caddr_t) &startAddr)) return (-1);
164:
165: return (VSMemInit()); /* Initialize memory allocator */
166: }
167:
168: /* The following routines parse the so-called s-line format. This was
169: * lifted more or less verbatim from the vms software; I don't fully
170: * understand it and you certainly don't want to even bother trying.
171: */
172:
173: ParseLine (line, linesize, lineaddr)
174: char *line;
175: int *linesize, *lineaddr;
176: {
177: if (line[0] != 'S') DLError ("Invalid format", line);
178:
179: switch (line[1]) {
180: case '0':
181: break;
182: case '1': case '2':
183: #ifdef notdef
184: CheckLine (line); /* Checks checksum */
185: #endif
186: if (line[1] == '1') {
187: *linesize = Hex2(line+2) - 3;
188: *lineaddr = Hex (line+4, 4);
189: } else {
190: *linesize = Hex2(line+2) - 4;
191: *lineaddr = Hex (line+4, 6);
192: }
193: break;
194: case '9':
195: return (-1);
196: default:
197: DLError ("Invalid format", line);
198: break;
199: }
200: return (0);
201: }
202:
203: CopyLine (line, buffer, count, pos)
204: char *line, *buffer;
205: register int count, pos;
206: {
207: register char *start;
208:
209: if (line[1] == '1') start = line + 8;
210: else start = line + 10;
211:
212: while (--count >= 0) {
213: buffer[pos^1] = Hex2(start);
214: pos++;
215: start += 2;
216: }
217: }
218:
219: CheckLine (line)
220: register char *line;
221: {
222: register char *lp;
223: register int count;
224: register char checksum;
225:
226: lp = line + 2;
227: count = Hex2(lp);
228: checksum = 0;
229:
230: do {
231: checksum += Hex2(lp);
232: lp += 2;
233: } while (--count >= 0);
234:
235: if (checksum != 0xff) DLError ("Bad checksum", line);
236: }
237:
238: InitHexArray ()
239: {
240: register char c;
241: for (c = 'A'; c <= 'F'; c++) HexArray[c] = c - 'A' + 10;
242: for (c = 'a'; c <= 'f'; c++) HexArray[c] = c - 'a' + 10;
243: for (c= '0'; c <= '9'; c++) HexArray[c] = c - '0';
244: }
245:
246: int Hex (cp, n)
247: register char *cp;
248: register int n;
249: {
250: register int i = 0;
251: while (--n >= 0)
252: i = (i<<4) + HexArray[*cp++];
253: return (i);
254: }
255:
256: DLError (str1, str2)
257: char *str1, *str2;
258: {
259: fprintf (stderr, "Downloader: %s: %s\n", str1, str2);
260: fflush (stderr);
261: exit (1);
262: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.