PERFORCE change 102750 for review

John Birrell jb at FreeBSD.org
Sat Jul 29 23:57:00 UTC 2006


http://perforce.freebsd.org/chv.cgi?CH=102750

Change 102750 by jb at jb_freebsd2 on 2006/07/29 23:56:06

	Add a method to write strings to the console, making them atomic
	by using a lock.
	
	On sun4v this is important because 32 processors potentially writing
	can generate complete gobbledy-gook if allowed to write on a character
	by character basis.
	
	This change ensures that a printf (for example) which formats it's
	string in a stack buffer can write the string uninterrupted. Strings
	like these generally have a new-line character at the end, so string
	writes via the new method will write the rest of the line with
	any other writes interleaved before it.

Affected files ...

.. //depot/projects/dtrace/src/sys/sun4v/sun4v/hvcons.c#2 edit

Differences ...

==== //depot/projects/dtrace/src/sys/sun4v/sun4v/hvcons.c#2 (text+ko) ====

@@ -43,12 +43,12 @@
 
 #include "opt_simulator.h"
 
+#include <machine/atomic.h>
 #include <machine/resource.h>
 #include <machine/hypervisor_api.h>
 
 #define HVCN_POLL_FREQ 10
 
-
 static d_open_t  hvcn_open;
 static d_close_t hvcn_close;
 
@@ -76,22 +76,24 @@
 static int			alt_break_state;
 #endif
 
+static int	cons_lock;
+
 static void	hvcn_tty_start(struct tty *);
 static int	hvcn_tty_param(struct tty *, struct termios *);
 static void	hvcn_tty_stop(struct tty *, int);
 static void     hvcn_timeout(void *);
+void     hvcn_rawputc(int);
 
 static cn_probe_t	hvcnprobe;
 static cn_init_t	hvcninit;
 static cn_getc_t	hvcngetc;
 static cn_checkc_t 	hvcncheckc;
 static cn_putc_t	hvcnputc;
+static cn_puts_t	hvcnputs;
 
-
 CONS_DRIVER(hvcn, hvcnprobe, hvcninit, NULL, hvcngetc,
-    hvcncheckc, hvcnputc, NULL);
+    hvcncheckc, hvcnputc, hvcnputs, NULL);
 
-
 static int
 hvcn_open(struct cdev *dev, int flag, int mode, struct thread *td)
 {
@@ -126,6 +128,7 @@
 		int polltime;
 
 		polltime = hz / HVCN_POLL_FREQ;
+polltime = 100;
 		if (polltime < 1) {
 			polltime = 1;
 		}
@@ -239,14 +242,11 @@
 	return (-1);
 }
 
-
-static void
-hvcnputc(struct consdev *cp, int c)
+void
+hvcn_rawputc(int c)
 {
+	int error = 0;
 
-	int error;
-
-	error = 0;
 	do {
 		if (c == '\n') 
 			error = hv_cnputchar('\r');
@@ -256,6 +256,29 @@
 	} while (error == H_EWOULDBLOCK);
 }
 
+static void
+hvcnputs(struct consdev *cp, char *p, int num)
+{
+	int i;
+
+	while (!atomic_cmpset_acq_int(&cons_lock, 0, 1))
+		DELAY(100);
+
+	for (i = 0; i < num; i++)
+		hvcn_rawputc(p[i]);
+
+	atomic_store_rel_int(&cons_lock, 0);
+}
+
+
+static void
+hvcnputc(struct consdev *cp, int c)
+{
+	char x = c & 0xff;
+
+	hvcnputs(cp, &x, 1);
+}
+
 static int
 hvcn_tty_param(struct tty *tp, struct termios *t)
 {


More information about the p4-projects mailing list