first attempt at reboot stuff
[unix-history] / usr / src / sys / kern / subr_prf.c
CommitLineData
0dc06be8 1/* subr_prf.c 3.4 %G% */
8cbb423c
BJ
2
3#include "../h/param.h"
4#include "../h/systm.h"
5#include "../h/seg.h"
6#include "../h/buf.h"
7#include "../h/conf.h"
96d38f03 8#include "../h/mtpr.h"
0dc06be8 9#include "../h/reboot.h"
96d38f03
BJ
10
11#ifdef TRACE
12#define TRCBUFS 4096
13char trcbuf[TRCBUFS];
14char *trcbufp = trcbuf;
15int trcwrap;
16int trcprt = TRCBUFS;
17#endif
8cbb423c
BJ
18
19/*
20 * In case console is off,
21 * panicstr contains argument to last
22 * call to panic.
23 */
24
25char *panicstr;
26
27/*
28 * Scaled down version of C Library printf.
29 * Only %s %u %d (==%u) %o %x %D are recognized.
30 * Used to print diagnostic information
31 * directly on console tty.
32 * Since it is not interrupt driven,
33 * all system activities are pretty much
34 * suspended.
35 * Printf should not be used for chit-chat.
36 */
37/*VARARGS1*/
38printf(fmt, x1)
39register char *fmt;
40unsigned x1;
96d38f03
BJ
41{
42
43 prf(fmt, &x1, 0);
44}
45
46#ifdef TRACE
47trace(fmt, x1)
48register char *fmt;
49unsigned x1;
50{
51
52 prf(fmt, &x1, 1);
53}
54
55#endif
56
57prf(fmt, adx, trace)
58register char *fmt;
59register unsigned int *adx;
8cbb423c
BJ
60{
61 register c;
8cbb423c
BJ
62 char *s;
63
8cbb423c
BJ
64loop:
65 while((c = *fmt++) != '%') {
66 if(c == '\0')
67 return;
96d38f03 68 putchar(c, trace);
8cbb423c
BJ
69 }
70 c = *fmt++;
96d38f03
BJ
71 if (c == 'X')
72 printx((long)*adx, trace);
73 else if (c == 'd' || c == 'u' || c == 'o' || c == 'x')
74 printn((long)*adx, c=='o'? 8: (c=='x'? 16:10), trace);
75 else if (c == 's') {
8cbb423c 76 s = (char *)*adx;
96d38f03
BJ
77 while (c = *s++)
78#ifdef TRACE
79 if (trace) {
80 *trcbufp++ = c;
81 if (trcbufp >= &trcbuf[TRCBUFS]) {
82 trcbufp = trcbuf;
83 trcwrap = 1;
84 }
85 } else
86#endif
87 putchar(c, trace);
8cbb423c 88 } else if (c == 'D') {
96d38f03 89 printn(*(long *)adx, 10, trace);
8cbb423c
BJ
90 adx += (sizeof(long) / sizeof(int)) - 1;
91 }
92 adx++;
93 goto loop;
94}
95
96d38f03 96printx(x, trace)
8cbb423c
BJ
97long x;
98{
99 int i;
100
101 for (i = 0; i < 8; i++)
96d38f03 102 putchar("0123456789ABCDEF"[(x>>((7-i)*4))&0xf], trace);
8cbb423c
BJ
103}
104
105/*
106 * Print an unsigned integer in base b.
107 */
96d38f03 108printn(n, b, trace)
8cbb423c
BJ
109long n;
110{
111 register long a;
112
113 if (n<0) { /* shouldn't happen */
96d38f03 114 putchar('-', trace);
8cbb423c
BJ
115 n = -n;
116 }
117 if(a = n/b)
96d38f03
BJ
118 printn(a, b, trace);
119 putchar("0123456789ABCDEF"[(int)(n%b)], trace);
8cbb423c
BJ
120}
121
122/*
0dc06be8
BJ
123 * Panic is called on unresolvable fatal errors.
124 * It syncs, prints "panic: mesg", and then reboots.
8cbb423c
BJ
125 */
126panic(s)
127char *s;
128{
129 panicstr = s;
130 update();
131 printf("panic: %s\n", s);
132 spl0();
133 for(;;)
0dc06be8 134 boot(RB_PANIC, RB_AUTOBOOT); /* 0 = automatic */
8cbb423c
BJ
135}
136
137/*
138 * prdev prints a warning message of the
139 * form "mesg on dev x/y".
140 * x and y are the major and minor parts of
141 * the device argument.
142 */
143prdev(str, dev)
144char *str;
145dev_t dev;
146{
147
148 printf("%s on dev %u/%u\n", str, major(dev), minor(dev));
149}
150
151/*
152 * deverr prints a diagnostic from
153 * a device driver.
154 * It prints the device, block number,
155 * and an octal word (usually some error
156 * status register) passed as argument.
157 */
158deverror(bp, o1, o2)
159register struct buf *bp;
160{
161
162 prdev("err", bp->b_dev);
163 printf("bn=%d er=%x,%x\n", bp->b_blkno, o1,o2);
164}
96d38f03
BJ
165
166#ifdef TRACE
167dumptrc()
168{
169 register char *cp;
170 register int pos, nch;
171
172 nch = trcprt;
173 if (nch < 0 || nch > TRCBUFS)
174 nch = TRCBUFS;
175 pos = (trcbufp - trcbuf) - nch;
176 if (pos < 0)
177 if (trcwrap)
178 pos += TRCBUFS;
179 else {
180 nch += pos;
181 pos = 0;
182 }
183 for (cp = &trcbuf[pos]; nch > 0; nch--) {
184 putchar(*cp++, 0);
185 if (cp >= &trcbuf[TRCBUFS])
186 cp = trcbuf;
187 }
188}
189#else
190/*ARGSUSED*/
191dumptrc(nch)
192 int nch;
193{
194
195}
196#endif
197
198char *msgbufp = msgbuf; /* Next saved printf character */
199/*
200 * Print a character on console or in internal trace buffer.
201 * If destination is console then the last MSGBUFS characters
202 * are saved in msgbuf for inspection later.
203 */
204putchar(c, trace)
205register c;
206{
207 register s, timo;
208
209#ifdef TRACE
210 if (trace) {
211 *trcbufp++ = c;
212 if (trcbufp >= &trcbuf[TRCBUFS]) {
213 trcbufp = trcbuf;
214 trcwrap = 1;
215 }
216 return;
217 }
218#endif
219 if (c != '\0' && c != '\r' && c != 0177) {
220 *msgbufp++ = c;
221 if (msgbufp >= &msgbuf[MSGBUFS])
222 msgbufp = msgbuf;
223 }
224 if (c == 0)
225 return;
226 cnputc(c);
227}