WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-devel

[Xen-devel] [PATCH]enable PCI serial card usage

To: "xen-devel@xxxxxxxxxxxxxxxxxxx" <xen-devel@xxxxxxxxxxxxxxxxxxx>
Subject: [Xen-devel] [PATCH]enable PCI serial card usage
From: "Wei, Gang" <gang.wei@xxxxxxxxx>
Date: Wed, 31 Mar 2010 10:40:25 +0800
Accept-language: zh-CN, en-US
Acceptlanguage: zh-CN, en-US
Cc: Keir Fraser <keir.fraser@xxxxxxxxxxxxx>
Delivery-date: Tue, 30 Mar 2010 19:42:44 -0700
Envelope-to: www-data@xxxxxxxxxxxxxxxxxxx
List-help: <mailto:xen-devel-request@lists.xensource.com?subject=help>
List-id: Xen developer discussion <xen-devel.lists.xensource.com>
List-post: <mailto:xen-devel@lists.xensource.com>
List-subscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=unsubscribe>
Sender: xen-devel-bounces@xxxxxxxxxxxxxxxxxxx
Thread-index: AcrQe4R+tgvNgRsDTUyRtRb8R9HK+g==
Thread-topic: [PATCH]enable PCI serial card usage
enable PCI serial card usage

On some machine, there is no build-in serial port and no LPC connection. To use
serial port, we have to plug in a serial card. Sometime BIOS doesn't enable the
BARs for the PCI devices which lead to that Xen can't use the add-in serial port
for early log print. This patch try to initialize the serial card and related
PCI bridge to make it usable for xen.

Usage:

Step 1. boot into bare metal Linux, get the information for the PCI serial ports
and the related PCI bridge. On my case:

#lspci -v
00:1e.0 PCI bridge: Intel Corporation 82801 PCI Bridge (rev 90) (prog-if 01     
[Subtractive decode])
        Bus: primary=00, secondary=06, subordinate=06, sec-latency=32
        I/O behind bridge: 00005000-00005fff

06:02.0 Serial controller: Lava Computer mfg Inc Lava DSerial-PCI Port A 
(prog-if 02 [16550])
        Region 0: I/O ports at 5000 [size=8]

Step 2. revise the grub.conf to include 
'com1=115200,8n1,0xPPPP,0,<port-bdf>,<bridge-bdf> console=com1'
for xen cmdline. The 0xPPPP is the base I/O port address got for the serial port
in bare metal Linux. For my case, it is 0x5000. The 0 after 0xPPPP means enable
polling model for the serial port. The <port-bdf> is the serial port BDF,
 06:02.0 in my case; the <bridge-bdf> is the bridge BDF bebind 
which the serial card locates, 00:1e.0 for my case.

Finally, good luck to you.

Signed-off-by: Wei Gang <gang.wei@xxxxxxxxx>

diff -r 0475c567c708 xen/drivers/char/ns16550.c
--- a/xen/drivers/char/ns16550.c        Tue Mar 23 09:37:59 2010 +0000
+++ b/xen/drivers/char/ns16550.c        Wed Mar 24 17:03:58 2010 +0800
@@ -19,7 +19,7 @@
 
 /*
  * Configure serial port with a string:
- *   <baud>[/<clock_hz>][,DPS[,<io-base>[,<irq>]]].
+ *   <baud>[/<clock_hz>][,DPS[,<io-base>[,<irq>[,<port-bdf>[,<bridge-bdf>]]]]].
  * The tail of the string can be omitted if platform defaults are sufficient.
  * If the baud rate is pre-configured, perhaps by a bootloader, then 'auto'
  * can be specified in place of a numeric baud rate. Polled mode is specified
@@ -40,6 +40,11 @@ static struct ns16550 {
     struct timer timer;
     unsigned int timeout_ms;
     int probing, intr_works;
+    /* on pci card */
+    unsigned int pb_bdf[3]; /* pci bridge BDF */
+    unsigned int ps_bdf[3]; /* pci serial port BDF */
+    int pb_bdf_enable:1;    /* if =1, pb-bdf effective, port behind bridge */
+    int ps_bdf_enable:1;    /* if =1, ps_bdf effective, port on pci card */
 } ns16550_com[2] = { { 0 } };
 
 /* Register offsets */
@@ -204,11 +209,28 @@ static int ns16550_getc(struct serial_po
     return 1;
 }
 
+static void pci_serial_early_init(struct ns16550 *uart)
+{
+    if ( !uart->ps_bdf_enable )
+        return;
+    
+    if ( uart->pb_bdf_enable )
+        pci_conf_write16(uart->pb_bdf[0], uart->pb_bdf[1], uart->pb_bdf[2],
+            0x1c, (uart->io_base & 0xF000) | ((uart->io_base & 0xF000) >> 8));
+
+    pci_conf_write32(uart->ps_bdf[0], uart->ps_bdf[1], uart->ps_bdf[2],
+        0x10, uart->io_base | 0x1);
+    pci_conf_write16(uart->ps_bdf[0], uart->ps_bdf[1], uart->ps_bdf[2],
+        0x4, 0x1);
+}
+
 static void __devinit ns16550_init_preirq(struct serial_port *port)
 {
     struct ns16550 *uart = port->uart;
     unsigned char lcr;
     unsigned int  divisor;
+
+    pci_serial_early_init(uart);
 
     /* I/O ports are distinguished by their size (16 bits). */
     if ( uart->io_base >= 0x10000 )
@@ -336,6 +358,19 @@ static int __init parse_parity_char(int 
     return 0;
 }
 
+static void __init parse_pci_bdf(const char **conf, unsigned int bdf[3])
+{
+    bdf[0] = simple_strtoul(*conf, conf, 16);
+    if ( **conf != ':' )
+        return;
+    (*conf)++;
+    bdf[1] = simple_strtoul(*conf, conf, 16);
+    if ( **conf != '.' )
+        return;
+    (*conf)++;
+    bdf[2] = simple_strtoul(*conf, conf, 16);
+}
+
 static int __init check_existence(struct ns16550 *uart)
 {
     unsigned char status, scratch, scratch2, scratch3;
@@ -347,6 +382,8 @@ static int __init check_existence(struct
     if ( uart->io_base >= 0x10000 )
         return 1;
 
+    pci_serial_early_init(uart);
+    
     /*
      * Do a simple existence test first; if we fail this,
      * there's no point trying anything else.
@@ -428,6 +465,18 @@ static void __init ns16550_parse_port_co
         {
             conf++;
             uart->irq = simple_strtoul(conf, &conf, 10);
+            if ( *conf == ',' )
+            {
+                conf++;
+                uart->ps_bdf_enable = 1;
+                parse_pci_bdf(&conf, &uart->ps_bdf[0]);
+                if ( *conf == ',' )
+                {
+                    conf++;
+                    uart->pb_bdf_enable = 1;
+                    parse_pci_bdf(&conf, &uart->pb_bdf[0]);
+                }
+            }
         }
     }
 

Attachment: pci_serial_v3.patch
Description: pci_serial_v3.patch

_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
<Prev in Thread] Current Thread [Next in Thread>