|
|
1.1 root 1: #if KLAATU
2: #define SERIAL_CONSOLE 1
3: #define INS8250 0x3f8 /* klaatu */
4: #endif
5:
6: #if GORT
7: #define SERIAL_CONSOLE 1
8: #define INS8250 0x290 /* gort */
9: #endif
10:
11: #ifndef INS8250
12: #define INS8250 0x3f8
13: #endif
14:
15: /*
16: * die.c -- Get information out from a very young kernel which probably
17: * can't do printf()'s.
18: */
19:
20: #include <sys/coherent.h>
21: #include <sys/mmu.h>
22: #include <ctype.h>
23:
24: #define COLOR ((char *) (0x0000B0000 + ctob(SBASE-PBASE)))
25: #define MONO ((char *) (0x0000B8000 + ctob(SBASE-PBASE)))
26: #define PAGING (0x80000000) /* Paging bit in cr0, set if paging is on. */
27: static int chirp_off;
28:
29: /*
30: * void _chirp(char c, off);
31: * Put character 'c' directly in video memory at offset 'off';
32: *
33: * This routine must not use any static variables, since the .data
34: * segment is not necessarily available yet.
35: */
36: void
37: _chirp(c, off)
38: char c;
39: int off;
40: {
41: #if SERIAL_CONSOLE
42: __putchar(c);
43: #else
44: if (!paging()) {
45: *(COLOR + off) = c;
46: *(MONO + off) = c;
47: } else {
48: *((char *) (ctob(VIDEOa) + off)) = c;
49: *((char *) (ctob(VIDEOb) + off)) = c;
50: }
51: #endif
52: } /* _chirp() */
53:
54: /*
55: * void chirp(char c);
56: * Put character 'c' directly in the first character of video memory;
57: *
58: * This routine must not use any static variables, since the .data
59: * segment is not necessarily available yet.
60: */
61: void
62: chirp(c)
63: char c;
64: {
65: _chirp(c, 158);
66: } /* chirp() */
67:
68: /*
69: * void strchirp(char *str);
70: * Put string 'str' directly in the next character of video memory;
71: * Note that calls to chirp and dchirp do not effect what mchirp considers
72: * to be the next character.
73: *
74: * This routine uses a ds variable, so it must not be used until the .data
75: * segment is available (this currently happens in the middle of mchinit).
76: */
77: void
78: strchirp(str)
79: char *str;
80: {
81: char c;
82:
83: while (c = *str++) {
84: _chirp(c, chirp_off);
85: chirp_off += 2;
86: }
87: } /* strchirp() */
88:
89: /*
90: * void mchirp(char c);
91: * Put character 'c' directly in the next character of video memory;
92: * If c == 0 reset the "next" character to be the first character.
93: * Note that calls to chirp and dchirp do not effect what mchirp considers
94: * to be the next character.
95: *
96: * This routine uses a static variable, so it must not be used until the .data
97: * segment is available (this currently happens in the middle of mchinit).
98: */
99: void
100: mchirp(c)
101: char c;
102: {
103: if ('\0' != c) {
104: _chirp(c, chirp_off);
105: chirp_off += 2;
106: }
107: else
108: chirp_off = 0;
109: } /* mchirp() */
110:
111: /*
112: * void dchirp(char c, charpos);
113: * Put character 'c' directly in the 'charpos' character of video memory;
114: *
115: * This routine must not use any static variables, since the .data
116: * segment is not necessarily available yet.
117: */
118: void
119: dchirp(c, charpos)
120: char c;
121: {
122: _chirp(c, charpos<<1);
123: } /* dchirp() */
124:
125: /*
126: * void die(char c);
127: * Put character 'c' directly in video memory, and then halt.
128: */
129: void
130: die(c)
131: char c;
132: {
133: _chirp(c, 0);
134: for (;;) {
135: halt();
136: }
137: }
138:
139: #define LINESIZE 80
140:
141: /*
142: * puts() -- put a NUL terminated string.
143: * Takes one argument--a pointer to a NUL terminated character string.
144: */
145: void
146: puts(s)
147: register char *s;
148: {
149: while (*s != '\0') {
150: mchirp(*s++);
151: }
152:
153: } /* puts() */
154:
155:
156: #define BS '\010'
157: #define DEL '\0' /* This is really what getchar() returns! */
158: #define NAK '\025'
159:
160: #define BITS_PER_INT16 16 /* Number of bits in an int16. */
161: #define DIGITS_PER_INT16 4 /* Maximum hex digits in a 16 bit number. */
162: #define DIGITS_PER_INT8 2 /* Maximum hex digits in an 8 bit number. */
163:
164: /*
165: * Print a 32/16/8 bit integers in hexadecimal.
166: */
167: void print32(num) {hexprint(num,8);}
168: void print16(num) {hexprint(num,4);}
169: void print8(num) {hexprint(num,2);}
170:
171: #if SERIAL_CONSOLE
172: #define OUTCH(c) __putchar(c)
173: #else
174: #define OUTCH(c) mchirp(c)
175: #endif
176:
177: hexprint(n, hexdigits)
178: int n, hexdigits;
179: {
180: int shift;
181: char digit, outch;
182:
183: for (shift = 4*(hexdigits-1); shift >= 0; shift -= 4) {
184: digit = (n >> shift) & 0xF;
185: if (digit > 9)
186: outch = 'A'+digit-10;
187: else
188: outch = '0'+digit;
189: OUTCH(outch);
190: }
191: OUTCH(' ');
192: }
193:
194: outch(c)
195: int c;
196: {
197: OUTCH(c);
198: }
199:
200: #define ASCII 1
201: #define XONXOFF 1
202: #define BAUD 9600
203:
204: /*
205: * file: i8251.c
206: *
207: * This version of putchar works with the serial lines.
208: * Various configurations are possible through conditional
209: * defines:
210: *
211: * BAUD default 9600
212: * specifies the baudrate, can be as high as 38400
213: *
214: * CONSOLE default COM1:
215: * is the base address of the uart
216: *
217: * ASCII default BINARY
218: * if set, maps '\n' into CR, LF and reduces input
219: * to 7-bit
220: *
221: * XONXOFF default not enabled
222: * allows user to control output
223: *
224: */
225:
226: #define THR (INS8250+0)
227: #define IER (INS8250+1)
228: #define IIR (INS8250+2)
229: #define LCR (INS8250+3)
230: #define MCR (INS8250+4)
231: #define LSR (INS8250+5)
232: #define MSR (INS8250+6)
233:
234: #define RBR THR
235: #define DLL THR
236: #define DLM IER
237:
238: #define DR 0x01
239: #define THRE 0x20
240:
241: __cinit()
242: {
243: #if SERIAL_CONSOLE
244: register rate;
245:
246: #if BAUD
247: rate = 115200L / BAUD;
248: #else
249: rate = 1;
250: #endif
251: outb(LCR, 0x00);
252: outb(IER, 0x00);
253: outb(LCR, 0x80);
254: outb(DLL, rate);
255: outb(DLM, rate>>8);
256: outb(LCR, 0x03);
257: outb(MCR, 0x03);
258: __putchar('\007');
259: __putchar('g');
260: #endif
261: }
262:
263: #define CTLQ 0021
264: #define CTLS 0023
265:
266: __getchar()
267: {
268: register c;
269:
270: while( (inb(LSR) & DR) == 0 )
271: ;
272: c = inb( RBR );
273: #if ASCII
274: c &= 0x7F;
275: #endif
276: return( c );
277: }
278:
279: __putchar( c )
280: register c;
281: {
282: register f;
283:
284: #if ASCII
285: if (c == '\n')
286: putchar( '\r' );
287: #endif
288: while( ((f=inb(LSR)) & THRE) == 0 )
289: ;
290: #if XONXOFF
291: if( (f & DR) != 0 ) {
292: f = inb( RBR ) & 0x7F;
293: if (f == CTLS) {
294: do {
295: while( (inb(LSR) & DR) == 0)
296: ;
297: f = inb( RBR ) & 0x7F;
298: } while (f != CTLQ);
299: }
300: }
301: #endif
302: outb( THR, c );
303: return( c );
304: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.