xref: /csrg-svn/sys/tahoe/stand/prf.c (revision 45796)
1*45796Sbostic /*	prf.c	1.7	90/12/16	*/
225870Ssam /*	prf.c	4.3	81/05/05	*/
325870Ssam 
4*45796Sbostic #include "../include/mtpr.h"
525870Ssam 
643457Sroot #include "sys/param.h"
7*45796Sbostic #include "../tahoe/cp.h"
825870Ssam 
925870Ssam /*
1025870Ssam  * Scaled down version of C Library printf.
1125870Ssam  * Used to print diagnostic information directly on console tty.
1225870Ssam  * Since it is not interrupt driven, all system activities are
1325870Ssam  * suspended.  Printf should not be used for chit-chat.
1425870Ssam  *
1525870Ssam  * One additional format: %b is supported to decode error registers.
1625870Ssam  * Usage is:
1725870Ssam  *	printf("reg=%b\n", regval, "<base><arg>*");
1825870Ssam  * Where <base> is the output base expressed as a control character,
1925870Ssam  * e.g. \10 gives octal; \20 gives hex.  Each arg is a sequence of
2025870Ssam  * characters, the first of which gives the bit number to be inspected
2125870Ssam  * (origin 1), and the next characters (up to a control character, i.e.
2225870Ssam  * a character <= 32), give the name of the register.  Thus
2325870Ssam  *	printf("reg=%b\n", 3, "\10\2BITTWO\1BITONE\n");
2425870Ssam  * would produce output:
2525870Ssam  *	reg=2<BITTWO,BITONE>
2625870Ssam  */
2725870Ssam /*VARARGS1*/
2825870Ssam printf(fmt, x1)
2925870Ssam 	char *fmt;
3025870Ssam 	unsigned x1;
3125870Ssam {
3225870Ssam 
3325870Ssam 	prf(fmt, &x1);
3425870Ssam }
3525870Ssam 
3625870Ssam prf(fmt, adx)
3725870Ssam 	register char *fmt;
3825870Ssam 	register u_int *adx;
3925870Ssam {
4025870Ssam 	register int b, c, i;
4125870Ssam 	char *s;
4225870Ssam 	int any;
4325870Ssam 
4425870Ssam loop:
4525870Ssam 	while ((c = *fmt++) != '%') {
4629979Skarels 		if (c == '\0')
4725870Ssam 			return;
4825870Ssam 		putchar(c);
4925870Ssam 	}
5025870Ssam again:
5125870Ssam 	c = *fmt++;
5225870Ssam 	/* THIS CODE IS VAX DEPENDENT IN HANDLING %l? AND %c */
5325870Ssam 	switch (c) {
5425870Ssam 
5525870Ssam 	case 'l':
5625870Ssam 		goto again;
5725870Ssam 	case 'x': case 'X':
5825870Ssam 		b = 16;
5925870Ssam 		goto number;
6025870Ssam 	case 'd': case 'D':
6125870Ssam 	case 'u':		/* what a joke */
6225870Ssam 		b = 10;
6325870Ssam 		goto number;
6425870Ssam 	case 'o': case 'O':
6525870Ssam 		b = 8;
6625870Ssam number:
6725870Ssam 		printn((u_long)*adx, b);
6825870Ssam 		break;
6925870Ssam 	case 'c':
7025870Ssam 		b = *adx;
7125870Ssam 		for (i = 24; i >= 0; i -= 8)
7225870Ssam 			if (c = (b >> i) & 0x7f)
7325870Ssam 				putchar(c);
7425870Ssam 		break;
7525870Ssam 	case 'b':
7625870Ssam 		b = *adx++;
7725870Ssam 		s = (char *)*adx;
7825870Ssam 		printn((u_long)b, *s++);
7925870Ssam 		any = 0;
8025870Ssam 		if (b) {
8125870Ssam 			while (i = *s++) {
8225870Ssam 				if (b & (1 << (i-1))) {
8329979Skarels 					putchar(any? ',' : '<');
8425870Ssam 					any = 1;
8525870Ssam 					for (; (c = *s) > 32; s++)
8625870Ssam 						putchar(c);
8725870Ssam 				} else
8825870Ssam 					for (; *s > 32; s++)
8925870Ssam 						;
9025870Ssam 			}
9129979Skarels 			if (any)
9229979Skarels 				putchar('>');
9325870Ssam 		}
9425870Ssam 		break;
9525870Ssam 
9625870Ssam 	case 's':
9725870Ssam 		s = (char *)*adx;
9825870Ssam 		while (c = *s++)
9925870Ssam 			putchar(c);
10025870Ssam 		break;
10125870Ssam 	}
10225870Ssam 	adx++;
10325870Ssam 	goto loop;
10425870Ssam }
10525870Ssam 
10625870Ssam /*
10725870Ssam  * Print a character on console.
10825870Ssam  */
10925870Ssam struct	cpdcb_o cpout;
11025870Ssam struct	cpdcb_i cpin;
11125870Ssam 
11225870Ssam /* console requires even parity */
11325870Ssam #define EVENP
11429979Skarels 
11525870Ssam putchar(c)
11629979Skarels 	char c;
11725870Ssam {
11825870Ssam 	int time;
11925870Ssam #ifdef EVENP
12025870Ssam 	register mask, par;
12125870Ssam 
12229979Skarels 	for (par = 0, mask = 1; mask != 0200; mask <<= 1, par <<= 1)
12325870Ssam 		par ^= c&mask;
12425870Ssam 	c |= par;
12525870Ssam #endif EVENP
12625870Ssam 	cpout.cp_hdr.cp_unit = CPCONS;	/* Resets done bit */
12725870Ssam 	cpout.cp_hdr.cp_comm = CPWRITE;
12825870Ssam 	cpout.cp_hdr.cp_count = 1;
12925870Ssam 	cpout.cp_buf[0] = c;
13025870Ssam 	mtpr(CPMDCB, &cpout);
13125870Ssam 	time = 100000;				/* Delay loop */
13225870Ssam 	while (time--) {
13329979Skarels 		uncache(&cpout.cp_hdr.cp_unit);
13429979Skarels 		if (cpout.cp_hdr.cp_unit & CPDONE)
13529979Skarels 			break;
13625870Ssam 	}
13729979Skarels 	if (c == '\n')
13829979Skarels 		putchar ('\r');
13925870Ssam }
14025870Ssam 
14125870Ssam getchar()
14225870Ssam {
14329979Skarels 	char c;
14425870Ssam 
14525870Ssam 	cpin.cp_hdr.cp_unit = CPCONS;	/* Resets done bit */
14625870Ssam 	cpin.cp_hdr.cp_comm = CPREAD;
14725870Ssam 	cpin.cp_hdr.cp_count = 1;
14825870Ssam 	mtpr(CPMDCB, &cpin);
14925870Ssam 	while ((cpin.cp_hdr.cp_unit & CPDONE) == 0)
15029979Skarels 		uncache(&cpin.cp_hdr.cp_unit);
15129979Skarels 	uncache(&cpin.cpi_buf[0]);
15225870Ssam 	c = cpin.cpi_buf[0] & 0x7f;
15329979Skarels 	if (c == '\r')
15429979Skarels 		c = '\n';
15529979Skarels 	if (c != '\b' && c != '\177')
15629979Skarels 		putchar(c);
15729979Skarels 	return (c);
15825870Ssam }
15933638Sbostic 
16033638Sbostic trap(ps)
16133638Sbostic 	int ps;
16233638Sbostic {
16333638Sbostic 	printf("Trap %o\n", ps);
16433638Sbostic 	for (;;)
16533638Sbostic 		;
16633638Sbostic }
16733638Sbostic 
16833638Sbostic uncache (addr)
16933638Sbostic 	char *addr;
17033638Sbostic {
17133638Sbostic 	/* Return *(addr-0x4000); DIRTY assumes this address is valid */
17233638Sbostic 	mtpr(PDCS, addr);
17333638Sbostic }
174