From 86be80086fba1f2f22c9d5ed28a6ea256541cfec Mon Sep 17 00:00:00 2001
From: Roger Pau Monne <roger.pau@citrix.com>
Date: Wed, 25 Sep 2013 16:57:20 +0200
Subject: [PATCH 3/3] ns8250: switch the putc loop to use a time based timeout

Additionally, we have to move one printf in hvm.c so that it is not
printed on resume, because it happens before we can set the vcpu_info
area, and trying to read the clock without the vcpu_info are set would
result in a panic.
---
 sys/dev/uart/uart_dev_ns8250.c |   15 ++++++++++-----
 sys/x86/xen/hvm.c              |    3 +--
 2 files changed, 11 insertions(+), 7 deletions(-)

diff --git a/sys/dev/uart/uart_dev_ns8250.c b/sys/dev/uart/uart_dev_ns8250.c
index 211d113..53c1e89 100644
--- a/sys/dev/uart/uart_dev_ns8250.c
+++ b/sys/dev/uart/uart_dev_ns8250.c
@@ -54,6 +54,9 @@ __FBSDID("$FreeBSD$");
 
 #define	DEFAULT_RCLK	1843200
 
+/* Max wait time in microseconds */
+#define	DEFAULT_WAIT	10
+
 static int broken_txfifo = 0;
 SYSCTL_INT(_hw, OID_AUTO, broken_txfifo, CTLFLAG_RW | CTLFLAG_TUN,
 	&broken_txfifo, 0, "UART FIFO has QEMU emulation bug");
@@ -314,15 +317,17 @@ ns8250_term(struct uart_bas *bas)
 static void
 ns8250_putc(struct uart_bas *bas, int c)
 {
-	int limit;
+	sbintime_t end;
 
-	limit = 250000;
-	while ((uart_getreg(bas, REG_LSR) & LSR_THRE) == 0 && --limit)
+	end = getsbinuptime() + DEFAULT_WAIT * SBT_1US;
+	while ((uart_getreg(bas, REG_LSR) & LSR_THRE) == 0 &&
+	       (end > getsbinuptime()))
 		DELAY(4);
 	uart_setreg(bas, REG_DATA, c);
 	uart_barrier(bas);
-	limit = 250000;
-	while ((uart_getreg(bas, REG_LSR) & LSR_TEMT) == 0 && --limit)
+	end = getsbinuptime() + DEFAULT_WAIT * SBT_1US;
+	while ((uart_getreg(bas, REG_LSR) & LSR_TEMT) == 0 &&
+	       (end > getsbinuptime()))
 		DELAY(4);
 }
 
diff --git a/sys/x86/xen/hvm.c b/sys/x86/xen/hvm.c
index 467c9e3..79a7e52 100644
--- a/sys/x86/xen/hvm.c
+++ b/sys/x86/xen/hvm.c
@@ -671,8 +671,6 @@ xen_hvm_disable_emulated_devices(void)
 	if (inw(XEN_MAGIC_IOPORT) != XMI_MAGIC)
 		return;
 
-	if (bootverbose)
-		printf("XEN: Disabling emulated block and network devices\n");
 	outw(XEN_MAGIC_IOPORT, XMI_UNPLUG_IDE_DISKS|XMI_UNPLUG_NICS);
 }
 
@@ -695,6 +693,7 @@ xen_hvm_init(enum xen_hvm_init_type init_type)
 		setup_xen_features();
 		cpu_ops.cpu_init = xen_hvm_cpu_init;
 		cpu_ops.cpu_resume = xen_hvm_cpu_resume;
+		printf("XEN: Disabling emulated block and network devices\n");
 		break;
 	case XEN_HVM_INIT_RESUME:
 		if (error != 0)
-- 
1.7.7.5 (Apple Git-26)

