The Cywin path handling is broken since make_system_path_relative_to_its_root() functionality was moved from the lib script to misc.c.

This patch should fix this. It reuses the Cygwin specific code from getroot.c:grub_get_prefix() which apparently is a different implementation of the same function.

I would suggest to remove grub_get_prefix(), it is now only used in grub-emu.c and sparc64/ieee1275/grub-setup.c. Not included in the patch, should be done in a separate commit.


2010-04-14  Christian Franke<fra...@computer.org>

        * util/grub-mkconfig_lib.in (make_system_path_relative_to_its_root):
        Remove broken Cygwin path conversion.
        * util/misc.c: [__CYGWIN__] Add include and define.
        [__CYGWIN__] (get_win32_path): Copy function from getroot.c, modify
        for Cygwin 1.7.
        (make_system_path_relative_to_its_root): Simplify loop, replace early
        return by break.
        [__CYGWIN__] Add conversion to win32 path.



--
Regards,
Christian Franke

=== modified file 'util/grub-mkconfig_lib.in'
--- util/grub-mkconfig_lib.in	2010-04-13 12:57:56 +0000
+++ util/grub-mkconfig_lib.in	2010-04-14 16:48:44 +0000
@@ -1,5 +1,5 @@
 # Helper library for grub-mkconfig
-# Copyright (C) 2007,2008,2009  Free Software Foundation, Inc.
+# Copyright (C) 2007,2008,2009,2010  Free Software Foundation, Inc.
 #
 # GRUB is free software: you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -38,21 +38,7 @@
 
 make_system_path_relative_to_its_root ()
 {
-  path="`${grub_mkrelpath} $1`"
-
-  case "`uname 2>/dev/null`" in
-    CYGWIN*)
-      # Cygwin: Check if regular or emulated mount.
-      if [ -z "$dir" ] || [ "`stat -c %D "$dir/.."`" != 620000 ] ; then
-        # Reached some mount point not below /cygdrive.
-        # GRUB does not know Cygwin's emulated mounts,
-        # convert to Win32 path and remove drive letter.
-        path=`cygpath -m "$path" | sed -n 's,^[A-Za-z]:,,p'`
-        test ! -z "$path" || return 1
-      fi ;;
-  esac
-
-  echo "$path"
+  ${grub_mkrelpath} $1
 }
 
 is_path_readable_by_grub ()

=== modified file 'util/misc.c'
--- util/misc.c	2010-04-09 23:25:46 +0000
+++ util/misc.c	2010-04-14 16:48:44 +0000
@@ -53,6 +53,11 @@
 # include <malloc.h>
 #endif
 
+#ifdef __CYGWIN__
+# include <sys/cygwin.h>
+# define DEV_CYGDRIVE_MAJOR 98
+#endif
+
 #ifdef __MINGW32__
 #include <windows.h>
 #include <winioctl.h>
@@ -456,6 +461,31 @@
   return ret;
 }
 
+#ifdef __CYGWIN__
+/* Convert POSIX path to Win32 path,
+   remove drive letter, replace backslashes.  */
+static char *
+get_win32_path (const char *path)
+{
+  char winpath[PATH_MAX];
+  if (cygwin_conv_path (CCP_POSIX_TO_WIN_A, path, winpath, sizeof(winpath)))
+    grub_util_error ("cygwin_conv_path() failed");
+
+  int len = strlen (winpath);
+  if (len > 2 && winpath[1] == ':')
+    {
+      len -= 2;
+      memmove (winpath, winpath + 2, len + 1);
+    }
+
+  int i;
+  for (i = 0; i < len; i++)
+    if (winpath[i] == '\\')
+      winpath[i] = '/';
+  return xstrdup (winpath);
+}
+#endif
+
 /* This function never prints trailing slashes (so that its output
    can be appended a slash unconditionally).  */
 char *
@@ -521,28 +551,28 @@
       /* offset == 1 means root directory.  */
       if (offset == 1)
 	{
-	  free (buf);
-	  len = strlen (buf2);
-	  while (buf2[len - 1] == '/' && len > 1)
-	    {
-	      buf2[len - 1] = '\0';
-	      len--;
-	    }
-	  if (len > 1)
-	    return buf2;
-	  else
-	    {
-	      /* This means path given is just a backslash.  As above
-		 we have to return an empty string.  */
-	      free (buf2);
-	      return xstrdup ("");
-	    }
+	  /* Include leading slash.  */
+	  offset = 0;
+	  break;
 	}
     }
   free (buf);
   buf3 = xstrdup (buf2 + offset);
   free (buf2);
 
+#ifdef __CYGWIN__
+  if (st.st_dev != (DEV_CYGDRIVE_MAJOR << 16))
+    {
+      /* Reached some mount point not below /cygdrive.
+	 GRUB does not know Cygwin's emulated mounts,
+	 convert to Win32 path.  */
+      grub_util_info ("Cygwin path = %s\n", buf3);
+      char * temp = get_win32_path (buf3);
+      free (buf3);
+      buf3 = temp;
+    }
+#endif
+
   len = strlen (buf3);
   while (buf3[len - 1] == '/' && len > 1)
     {

_______________________________________________
Grub-devel mailing list
Grub-devel@gnu.org
http://lists.gnu.org/mailman/listinfo/grub-devel

Reply via email to