nalika / rpms / grub2

Forked from rpms/grub2 2 years ago
Clone

Blame SOURCES/0351-Add-serial-on-ARC-platform.patch

f96e0b
From 856d1d38f73b370b3dd30b7ab0c362f6da7e7dcb Mon Sep 17 00:00:00 2001
f96e0b
From: Vladimir 'phcoder' Serbinenko <phcoder@gmail.com>
f96e0b
Date: Thu, 25 Apr 2013 22:40:03 +0200
f96e0b
Subject: [PATCH 351/482] 	Add serial on ARC platform.
f96e0b
f96e0b
---
f96e0b
 ChangeLog                      |   4 ++
f96e0b
 docs/grub.texi                 |   6 +-
f96e0b
 grub-core/Makefile.am          |   1 +
f96e0b
 grub-core/Makefile.core.def    |   2 +
f96e0b
 grub-core/disk/arc/arcdisk.c   |  34 +---------
f96e0b
 grub-core/kern/mips/arc/init.c |  39 +++++++++++
f96e0b
 grub-core/term/arc/console.c   |  81 ++++++++++++++---------
f96e0b
 grub-core/term/arc/serial.c    | 147 +++++++++++++++++++++++++++++++++++++++++
f96e0b
 grub-core/term/serial.c        |   9 ++-
f96e0b
 include/grub/arc/arc.h         |  11 +++
f96e0b
 include/grub/serial.h          |  16 +++++
f96e0b
 11 files changed, 279 insertions(+), 71 deletions(-)
f96e0b
 create mode 100644 grub-core/term/arc/serial.c
f96e0b
f96e0b
diff --git a/ChangeLog b/ChangeLog
f96e0b
index 94dd291..7f2c4dd 100644
f96e0b
--- a/ChangeLog
f96e0b
+++ b/ChangeLog
f96e0b
@@ -1,5 +1,9 @@
f96e0b
 2013-04-25  Vladimir Serbinenko  <phcoder@gmail.com>
f96e0b
 
f96e0b
+	Add serial on ARC platform.
f96e0b
+
f96e0b
+2013-04-25  Vladimir Serbinenko  <phcoder@gmail.com>
f96e0b
+
f96e0b
 	* grub-core/boot/powerpc/bootinfo.txt.in: Missing update from previous
f96e0b
 	commit.
f96e0b
 
f96e0b
diff --git a/docs/grub.texi b/docs/grub.texi
f96e0b
index 87d19ea..920a558 100644
f96e0b
--- a/docs/grub.texi
f96e0b
+++ b/docs/grub.texi
f96e0b
@@ -4729,8 +4729,7 @@ ARC platform is unable to change datetime (firmware doesn't seem to provide a
f96e0b
 function for it).
f96e0b
 EMU has similar limitation.
f96e0b
 
f96e0b
-ARC platform no serial port is available.
f96e0b
-EMU has similar limitation.
f96e0b
+On EMU platform no serial port is available.
f96e0b
 
f96e0b
 Console charset refers only to firmware-assisted console. gfxterm is always
f96e0b
 Unicode (see Internationalisation section for its limitations). Serial is
f96e0b
@@ -4747,9 +4746,6 @@ the actual console may be much more limited depending on firmware
f96e0b
 On BIOS network is supported only if the image is loaded through network.
f96e0b
 On sparc64 GRUB is unable to determine which server it was booted from.
f96e0b
 
f96e0b
-On platforms not having direct serial support (as indicated in the line serial)
f96e0b
-you can still redirect firmware console to serial if it allows so.
f96e0b
-
f96e0b
 Direct ATA/AHCI support allows to circumvent various firmware limitations but
f96e0b
 isn't needed for normal operation except on baremetal ports.
f96e0b
 
f96e0b
diff --git a/grub-core/Makefile.am b/grub-core/Makefile.am
f96e0b
index 6f156e7..07aad50 100644
f96e0b
--- a/grub-core/Makefile.am
f96e0b
+++ b/grub-core/Makefile.am
f96e0b
@@ -151,6 +151,7 @@ endif
f96e0b
 if COND_mips_arc
f96e0b
 KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/extcmd.h
f96e0b
 KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/arc/arc.h
f96e0b
+KERNEL_HEADER_FILES += $(top_srcdir)/include/grub/terminfo.h
f96e0b
 endif
f96e0b
 
f96e0b
 if COND_mips_qemu_mips
f96e0b
diff --git a/grub-core/Makefile.core.def b/grub-core/Makefile.core.def
f96e0b
index 8f36ea0..cdef5b4 100644
f96e0b
--- a/grub-core/Makefile.core.def
f96e0b
+++ b/grub-core/Makefile.core.def
f96e0b
@@ -1661,10 +1661,12 @@ module = {
f96e0b
   common = term/serial.c;
f96e0b
   x86 = term/ns8250.c;
f96e0b
   ieee1275 = term/ieee1275/serial.c;
f96e0b
+  mips_arc = term/arc/serial.c;
f96e0b
   efi = term/efi/serial.c;
f96e0b
 
f96e0b
   enable = terminfomodule;
f96e0b
   enable = ieee1275;
f96e0b
+  enable = mips_arc;
f96e0b
 };
f96e0b
 
f96e0b
 module = {
f96e0b
diff --git a/grub-core/disk/arc/arcdisk.c b/grub-core/disk/arc/arcdisk.c
f96e0b
index 780728f..9aefb7c 100644
f96e0b
--- a/grub-core/disk/arc/arcdisk.c
f96e0b
+++ b/grub-core/disk/arc/arcdisk.c
f96e0b
@@ -153,9 +153,7 @@ reopen (const char *name, int writable)
f96e0b
 static grub_err_t
f96e0b
 grub_arcdisk_open (const char *name, grub_disk_t disk)
f96e0b
 {
f96e0b
-  char *fullname, *optr;
f96e0b
-  const char *iptr;
f96e0b
-  int state = 0;
f96e0b
+  char *fullname;
f96e0b
   grub_err_t err;
f96e0b
   grub_arc_err_t r;
f96e0b
   struct grub_arc_fileinfo info;
f96e0b
@@ -163,35 +161,7 @@ grub_arcdisk_open (const char *name, grub_disk_t disk)
f96e0b
 
f96e0b
   if (grub_memcmp (name, "arc/", 4) != 0)
f96e0b
     return grub_error (GRUB_ERR_UNKNOWN_DEVICE, "not arc device");
f96e0b
-  fullname = grub_malloc (2 * grub_strlen (name) + sizeof (RAW_SUFFIX));
f96e0b
-  if (!fullname)
f96e0b
-    return grub_errno;
f96e0b
-  optr = fullname;
f96e0b
-  for (iptr = name + 4; *iptr; iptr++)
f96e0b
-    if (state == 0)
f96e0b
-      {
f96e0b
-	if (!grub_isdigit (*iptr))
f96e0b
-	  *optr++ = *iptr;
f96e0b
-	else
f96e0b
-	  {
f96e0b
-	    *optr++ = '(';
f96e0b
-	    *optr++ = *iptr;
f96e0b
-	    state = 1;
f96e0b
-	  }
f96e0b
-      }
f96e0b
-    else
f96e0b
-      {
f96e0b
-	if (grub_isdigit (*iptr))
f96e0b
-	  *optr++ = *iptr;
f96e0b
-	else
f96e0b
-	  {
f96e0b
-	    *optr++ = ')';
f96e0b
-	    state = 0;
f96e0b
-	  }
f96e0b
-      }
f96e0b
-  if (state)
f96e0b
-    *optr++ = ')';
f96e0b
-  grub_memcpy (optr, RAW_SUFFIX, sizeof (RAW_SUFFIX));
f96e0b
+  fullname = grub_arc_alt_name_to_norm (name, RAW_SUFFIX);
f96e0b
   disk->data = fullname;
f96e0b
   grub_dprintf ("arcdisk", "opening %s\n", fullname);
f96e0b
 
f96e0b
diff --git a/grub-core/kern/mips/arc/init.c b/grub-core/kern/mips/arc/init.c
f96e0b
index 011c63f..92a2877 100644
f96e0b
--- a/grub-core/kern/mips/arc/init.c
f96e0b
+++ b/grub-core/kern/mips/arc/init.c
f96e0b
@@ -125,6 +125,45 @@ grub_machine_mmap_iterate (grub_memory_hook_t hook, void *hook_data)
f96e0b
     }
f96e0b
 }
f96e0b
 
f96e0b
+char *
f96e0b
+grub_arc_alt_name_to_norm (const char *name, const char *suffix)
f96e0b
+{
f96e0b
+  char *optr;
f96e0b
+  const char *iptr;
f96e0b
+  char * ret = grub_malloc (2 * grub_strlen (name) + grub_strlen (suffix));
f96e0b
+  int state = 0;
f96e0b
+
f96e0b
+  if (!ret)
f96e0b
+    return NULL;
f96e0b
+  optr = ret;
f96e0b
+  for (iptr = name + 4; *iptr; iptr++)
f96e0b
+    if (state == 0)
f96e0b
+      {
f96e0b
+	if (!grub_isdigit (*iptr))
f96e0b
+	  *optr++ = *iptr;
f96e0b
+	else
f96e0b
+	  {
f96e0b
+	    *optr++ = '(';
f96e0b
+	    *optr++ = *iptr;
f96e0b
+	    state = 1;
f96e0b
+	  }
f96e0b
+      }
f96e0b
+    else
f96e0b
+      {
f96e0b
+	if (grub_isdigit (*iptr))
f96e0b
+	  *optr++ = *iptr;
f96e0b
+	else
f96e0b
+	  {
f96e0b
+	    *optr++ = ')';
f96e0b
+	    state = 0;
f96e0b
+	  }
f96e0b
+      }
f96e0b
+  if (state)
f96e0b
+    *optr++ = ')';
f96e0b
+  grub_strcpy (optr, suffix);
f96e0b
+  return ret;
f96e0b
+}
f96e0b
+
f96e0b
 extern grub_uint32_t grub_total_modules_size __attribute__ ((section(".text")));
f96e0b
 grub_addr_t grub_modbase;
f96e0b
 
f96e0b
diff --git a/grub-core/term/arc/console.c b/grub-core/term/arc/console.c
f96e0b
index 13478ea..ea4737c 100644
f96e0b
--- a/grub-core/term/arc/console.c
f96e0b
+++ b/grub-core/term/arc/console.c
f96e0b
@@ -50,6 +50,55 @@ put (struct grub_term_output *term __attribute__ ((unused)), const int c)
f96e0b
 
f96e0b
 static struct grub_terminfo_output_state grub_console_terminfo_output;
f96e0b
 
f96e0b
+int
f96e0b
+grub_arc_is_device_serial (const char *name, int alt_names)
f96e0b
+{
f96e0b
+  if (name[0] == '\0')
f96e0b
+    return 0;
f96e0b
+
f96e0b
+  const char *ptr = name + grub_strlen (name) - 1;
f96e0b
+  int i;
f96e0b
+  /*
f96e0b
+    Recognize:
f96e0b
+    serial(N)
f96e0b
+    serial(N)other(M)
f96e0b
+   */
f96e0b
+  for (i = 0; i < 2; i++)
f96e0b
+    {
f96e0b
+      if (!alt_names)
f96e0b
+	{
f96e0b
+	  if (*ptr != ')')
f96e0b
+	    return 0;
f96e0b
+	  ptr--;
f96e0b
+	}
f96e0b
+      for (; ptr >= name && grub_isdigit (*ptr); ptr--);
f96e0b
+      if (ptr < name)
f96e0b
+	return 0;
f96e0b
+      if (!alt_names)
f96e0b
+	{
f96e0b
+	  if (*ptr != '(')
f96e0b
+	    return 0;
f96e0b
+	  ptr--;
f96e0b
+	}
f96e0b
+      if (ptr + 1 >= name + sizeof ("serial") - 1
f96e0b
+	  && grub_memcmp (ptr + 1 - (sizeof ("serial") - 1),
f96e0b
+			  "serial", sizeof ("serial") - 1) == 0)
f96e0b
+	return 1;
f96e0b
+      if (!(ptr + 1 >= name + sizeof ("other") - 1
f96e0b
+	    && grub_memcmp (ptr + 1 - (sizeof ("other") - 1),
f96e0b
+			    "other", sizeof ("other") - 1) == 0))
f96e0b
+	return 0;
f96e0b
+      ptr -= sizeof ("other") - 1;
f96e0b
+      if (alt_names)
f96e0b
+	{
f96e0b
+	  if (*ptr != '/')
f96e0b
+	    return 0;
f96e0b
+	  ptr--;
f96e0b
+	}
f96e0b
+    }
f96e0b
+  return 0;
f96e0b
+}
f96e0b
+
f96e0b
 static int
f96e0b
 check_is_serial (void)
f96e0b
 {
f96e0b
@@ -71,37 +120,7 @@ check_is_serial (void)
f96e0b
     consout = GRUB_ARC_FIRMWARE_VECTOR->getenvironmentvariable ("ConsoleOut");
f96e0b
   if (!consout)
f96e0b
     return is_serial = 0;
f96e0b
-  if (consout[0] == '\0')
f96e0b
-    return is_serial = 0;
f96e0b
-
f96e0b
-  const char *ptr = consout + grub_strlen (consout) - 1;
f96e0b
-  int i;
f96e0b
-  /*
f96e0b
-    Recognize:
f96e0b
-    serial(N)
f96e0b
-    serial(N)other(M)
f96e0b
-   */
f96e0b
-  for (i = 0; i < 2; i++)
f96e0b
-    {
f96e0b
-      if (*ptr != ')')
f96e0b
-	return is_serial = 0;
f96e0b
-      ptr--;
f96e0b
-      for (; ptr >= consout && grub_isdigit (*ptr); ptr--);
f96e0b
-      if (ptr < consout)
f96e0b
-	return is_serial = 0;
f96e0b
-      if (*ptr != '(')
f96e0b
-	return is_serial = 0;
f96e0b
-      if (ptr >= consout + sizeof ("serial") - 1
f96e0b
-	  && grub_memcmp (ptr - (sizeof ("serial") - 1),
f96e0b
-			  "serial", sizeof ("serial") - 1) == 0)
f96e0b
-	return is_serial = 1;
f96e0b
-      if (!(ptr >= consout + sizeof ("other") - 1
f96e0b
-	    && grub_memcmp (ptr - (sizeof ("other") - 1),
f96e0b
-			    "other", sizeof ("other") - 1) == 0))
f96e0b
-	return is_serial = 0;
f96e0b
-      ptr -= sizeof ("other");
f96e0b
-    }
f96e0b
-  return 0;
f96e0b
+  return is_serial = grub_arc_is_device_serial (consout, 0);
f96e0b
 }
f96e0b
     
f96e0b
 static void
f96e0b
diff --git a/grub-core/term/arc/serial.c b/grub-core/term/arc/serial.c
f96e0b
new file mode 100644
f96e0b
index 0000000..87d1ce8
f96e0b
--- /dev/null
f96e0b
+++ b/grub-core/term/arc/serial.c
f96e0b
@@ -0,0 +1,147 @@
f96e0b
+/*
f96e0b
+ *  GRUB  --  GRand Unified Bootloader
f96e0b
+ *  Copyright (C) 2013  Free Software Foundation, Inc.
f96e0b
+ *
f96e0b
+ *  GRUB is free software: you can redistribute it and/or modify
f96e0b
+ *  it under the terms of the GNU General Public License as published by
f96e0b
+ *  the Free Software Foundation, either version 3 of the License, or
f96e0b
+ *  (at your option) any later version.
f96e0b
+ *
f96e0b
+ *  GRUB is distributed in the hope that it will be useful,
f96e0b
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
f96e0b
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
f96e0b
+ *  GNU General Public License for more details.
f96e0b
+ *
f96e0b
+ *  You should have received a copy of the GNU General Public License
f96e0b
+ *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
f96e0b
+ */
f96e0b
+
f96e0b
+#include <grub/serial.h>
f96e0b
+#include <grub/types.h>
f96e0b
+#include <grub/dl.h>
f96e0b
+#include <grub/misc.h>
f96e0b
+#include <grub/mm.h>
f96e0b
+#include <grub/time.h>
f96e0b
+#include <grub/i18n.h>
f96e0b
+#include <grub/arc/arc.h>
f96e0b
+
f96e0b
+
f96e0b
+static void
f96e0b
+do_real_config (struct grub_serial_port *port)
f96e0b
+{
f96e0b
+  char *name;
f96e0b
+  if (port->configured)
f96e0b
+    return;
f96e0b
+
f96e0b
+  name = grub_arc_alt_name_to_norm (port->name, "");
f96e0b
+
f96e0b
+  if (GRUB_ARC_FIRMWARE_VECTOR->open (name,GRUB_ARC_FILE_ACCESS_OPEN_RW,
f96e0b
+				      &port->handle))
f96e0b
+    port->handle_valid = 0;
f96e0b
+  else
f96e0b
+    port->handle_valid = 1;
f96e0b
+
f96e0b
+  port->configured = 1;
f96e0b
+}
f96e0b
+
f96e0b
+/* Fetch a key.  */
f96e0b
+static int
f96e0b
+serial_hw_fetch (struct grub_serial_port *port)
f96e0b
+{
f96e0b
+  unsigned long actual;
f96e0b
+  char c;
f96e0b
+
f96e0b
+  do_real_config (port);
f96e0b
+
f96e0b
+  if (!port->handle_valid)
f96e0b
+    return -1;
f96e0b
+  if (GRUB_ARC_FIRMWARE_VECTOR->read (port->handle, &c,
f96e0b
+				      1, &actual) || actual <= 0)
f96e0b
+    return -1;
f96e0b
+  return c;
f96e0b
+}
f96e0b
+
f96e0b
+/* Put a character.  */
f96e0b
+static void
f96e0b
+serial_hw_put (struct grub_serial_port *port, const int c)
f96e0b
+{
f96e0b
+  unsigned long actual;
f96e0b
+  char c0 = c;
f96e0b
+
f96e0b
+  do_real_config (port);
f96e0b
+
f96e0b
+  if (!port->handle_valid)
f96e0b
+    return;
f96e0b
+
f96e0b
+  GRUB_ARC_FIRMWARE_VECTOR->write (port->handle, &c0,
f96e0b
+				   1, &actual);
f96e0b
+}
f96e0b
+
f96e0b
+/* Initialize a serial device. PORT is the port number for a serial device.
f96e0b
+   SPEED is a DTE-DTE speed which must be one of these: 2400, 4800, 9600,
f96e0b
+   19200, 38400, 57600 and 115200. WORD_LEN is the word length to be used
f96e0b
+   for the device. Likewise, PARITY is the type of the parity and
f96e0b
+   STOP_BIT_LEN is the length of the stop bit. The possible values for
f96e0b
+   WORD_LEN, PARITY and STOP_BIT_LEN are defined in the header file as
f96e0b
+   macros.  */
f96e0b
+static grub_err_t
f96e0b
+serial_hw_configure (struct grub_serial_port *port __attribute__ ((unused)),
f96e0b
+		     struct grub_serial_config *config __attribute__ ((unused)))
f96e0b
+{
f96e0b
+  /*  FIXME: no ARC serial config available.  */
f96e0b
+
f96e0b
+  return GRUB_ERR_NONE;
f96e0b
+}
f96e0b
+
f96e0b
+struct grub_serial_driver grub_arcserial_driver =
f96e0b
+  {
f96e0b
+    .configure = serial_hw_configure,
f96e0b
+    .fetch = serial_hw_fetch,
f96e0b
+    .put = serial_hw_put
f96e0b
+  };
f96e0b
+
f96e0b
+const char *
f96e0b
+grub_arcserial_add_port (const char *path)
f96e0b
+{
f96e0b
+  struct grub_serial_port *port;
f96e0b
+  grub_err_t err;
f96e0b
+
f96e0b
+  port = grub_zalloc (sizeof (*port));
f96e0b
+  if (!port)
f96e0b
+    return NULL;
f96e0b
+  port->name = grub_strdup (path);
f96e0b
+  if (!port->name)
f96e0b
+    return NULL;
f96e0b
+
f96e0b
+  port->driver = &grub_arcserial_driver;
f96e0b
+  err = grub_serial_config_defaults (port);
f96e0b
+  if (err)
f96e0b
+    grub_print_error ();
f96e0b
+
f96e0b
+  grub_serial_register (port);
f96e0b
+
f96e0b
+  return port->name;
f96e0b
+}
f96e0b
+
f96e0b
+static int
f96e0b
+dev_iterate (const char *name,
f96e0b
+	     const struct grub_arc_component *comp __attribute__ ((unused)),
f96e0b
+	     void *data __attribute__ ((unused)))
f96e0b
+{
f96e0b
+  /* We should check consolein/consoleout flags as
f96e0b
+     well but some implementations are buggy.  */
f96e0b
+  if ((comp->flags & (GRUB_ARC_COMPONENT_FLAG_IN | GRUB_ARC_COMPONENT_FLAG_OUT))
f96e0b
+      != (GRUB_ARC_COMPONENT_FLAG_IN | GRUB_ARC_COMPONENT_FLAG_OUT))
f96e0b
+    return 0;
f96e0b
+  if (!grub_arc_is_device_serial (name, 1))
f96e0b
+    return 0;
f96e0b
+  grub_arcserial_add_port (name);
f96e0b
+  return 0;
f96e0b
+}
f96e0b
+
f96e0b
+void
f96e0b
+grub_arcserial_init (void)
f96e0b
+{
f96e0b
+  grub_arc_iterate_devs (dev_iterate, 0, 1);
f96e0b
+}
f96e0b
+
f96e0b
diff --git a/grub-core/term/serial.c b/grub-core/term/serial.c
f96e0b
index 96f9d7f..61cd80a 100644
f96e0b
--- a/grub-core/term/serial.c
f96e0b
+++ b/grub-core/term/serial.c
f96e0b
@@ -137,7 +137,7 @@ grub_serial_find (const char *name)
f96e0b
     if (grub_strcmp (port->name, name) == 0)
f96e0b
       break;
f96e0b
 
f96e0b
-#if (defined(__mips__) || defined (__i386__) || defined (__x86_64__)) && !defined(GRUB_MACHINE_EMU)
f96e0b
+#if (defined(__mips__) || defined (__i386__) || defined (__x86_64__)) && !defined(GRUB_MACHINE_EMU) && !defined(GRUB_MACHINE_ARC)
f96e0b
   if (!port && grub_memcmp (name, "port", sizeof ("port") - 1) == 0
f96e0b
       && grub_isxdigit (name [sizeof ("port") - 1]))
f96e0b
     {
f96e0b
@@ -242,7 +242,7 @@ grub_cmd_serial (grub_extcmd_context_t ctxt, int argc, char **args)
f96e0b
   err = port->driver->configure (port, &config);
f96e0b
   if (err)
f96e0b
     return err;
f96e0b
-#if !defined (GRUB_MACHINE_EMU) && (defined(__mips__) || defined (__i386__) || defined (__x86_64__))
f96e0b
+#if !defined (GRUB_MACHINE_EMU) && !defined(GRUB_MACHINE_ARC) && (defined(__mips__) || defined (__i386__) || defined (__x86_64__))
f96e0b
 
f96e0b
   /* Compatibility kludge.  */
f96e0b
   if (port->driver == &grub_ns8250_driver)
f96e0b
@@ -396,7 +396,7 @@ GRUB_MOD_INIT(serial)
f96e0b
 	       &grub_serial_terminfo_input_template,
f96e0b
 	       sizeof (grub_serial_terminfo_input));
f96e0b
 
f96e0b
-#if !defined (GRUB_MACHINE_EMU) && (defined(__mips__) || defined (__i386__) || defined (__x86_64__))
f96e0b
+#if !defined (GRUB_MACHINE_EMU) && !defined(GRUB_MACHINE_ARC) && (defined(__mips__) || defined (__i386__) || defined (__x86_64__))
f96e0b
   grub_ns8250_init ();
f96e0b
 #endif
f96e0b
 #ifdef GRUB_MACHINE_IEEE1275
f96e0b
@@ -405,6 +405,9 @@ GRUB_MOD_INIT(serial)
f96e0b
 #ifdef GRUB_MACHINE_EFI
f96e0b
   grub_efiserial_init ();
f96e0b
 #endif
f96e0b
+#ifdef GRUB_MACHINE_ARC
f96e0b
+  grub_arcserial_init ();
f96e0b
+#endif
f96e0b
 }
f96e0b
 
f96e0b
 #if defined (GRUB_MACHINE_MIPS_LOONGSON) || defined (GRUB_MACHINE_MIPS_QEMU_MIPS)
f96e0b
diff --git a/include/grub/arc/arc.h b/include/grub/arc/arc.h
f96e0b
index 8f86500..c2578f4 100644
f96e0b
--- a/include/grub/arc/arc.h
f96e0b
+++ b/include/grub/arc/arc.h
f96e0b
@@ -79,6 +79,12 @@ struct grub_arc_display_status
f96e0b
   grub_arc_uchar_t reverse_video;
f96e0b
 };
f96e0b
 
f96e0b
+enum
f96e0b
+  {
f96e0b
+    GRUB_ARC_COMPONENT_FLAG_OUT = 0x40,
f96e0b
+    GRUB_ARC_COMPONENT_FLAG_IN = 0x20,
f96e0b
+  };
f96e0b
+
f96e0b
 struct grub_arc_component
f96e0b
 {
f96e0b
   grub_arc_enum_t class;
f96e0b
@@ -262,6 +268,11 @@ int EXPORT_FUNC (grub_arc_iterate_devs) (grub_arc_iterate_devs_hook_t hook,
f96e0b
 					 void *hook_data,
f96e0b
 					 int alt_names);
f96e0b
 
f96e0b
+char *EXPORT_FUNC (grub_arc_alt_name_to_norm) (const char *name, const char *suffix);
f96e0b
+
f96e0b
+int EXPORT_FUNC (grub_arc_is_device_serial) (const char *name, int alt_names);
f96e0b
+
f96e0b
+
f96e0b
 #define FOR_ARC_CHILDREN(comp, parent) for (comp = GRUB_ARC_FIRMWARE_VECTOR->getchild (parent); comp; comp = GRUB_ARC_FIRMWARE_VECTOR->getpeer (comp))
f96e0b
 
f96e0b
 extern void grub_arcdisk_init (void);
f96e0b
diff --git a/include/grub/serial.h b/include/grub/serial.h
f96e0b
index 32f507c..20840d0 100644
f96e0b
--- a/include/grub/serial.h
f96e0b
+++ b/include/grub/serial.h
f96e0b
@@ -30,6 +30,9 @@
f96e0b
 #ifdef GRUB_MACHINE_IEEE1275
f96e0b
 #include <grub/ieee1275/ieee1275.h>
f96e0b
 #endif
f96e0b
+#ifdef GRUB_MACHINE_ARC
f96e0b
+#include <grub/arc/arc.h>
f96e0b
+#endif
f96e0b
 
f96e0b
 struct grub_serial_port;
f96e0b
 struct grub_serial_config;
f96e0b
@@ -105,6 +108,13 @@ struct grub_serial_port
f96e0b
 #ifdef GRUB_MACHINE_EFI
f96e0b
     struct grub_efi_serial_io_interface *interface;
f96e0b
 #endif
f96e0b
+#ifdef GRUB_MACHINE_ARC
f96e0b
+    struct
f96e0b
+    {
f96e0b
+      grub_arc_fileno_t handle;
f96e0b
+      int handle_valid;
f96e0b
+    };
f96e0b
+#endif
f96e0b
   };
f96e0b
   grub_term_output_t term_out;
f96e0b
   grub_term_input_t term_in;
f96e0b
@@ -170,6 +180,12 @@ void grub_ofserial_init (void);
f96e0b
 void
f96e0b
 grub_efiserial_init (void);
f96e0b
 #endif
f96e0b
+#ifdef GRUB_MACHINE_ARC
f96e0b
+void
f96e0b
+grub_arcserial_init (void);
f96e0b
+const char *
f96e0b
+grub_arcserial_add_port (const char *path);
f96e0b
+#endif
f96e0b
 
f96e0b
 struct grub_serial_port *grub_serial_find (const char *name);
f96e0b
 extern struct grub_serial_driver grub_ns8250_driver;
f96e0b
-- 
f96e0b
1.8.2.1
f96e0b