From: Felix Zielcke <fzielcke@z-51.de>
To: The development of GRUB 2 <grub-devel@gnu.org>
Subject: Re: [PATCH] Re: grub-install --root-directory=/mnt /dev/sda1 fails
Date: Fri, 12 Jun 2009 12:28:23 +0200 [thread overview]
Message-ID: <1244802503.3181.0.camel@fz.local> (raw)
In-Reply-To: <1244762744.3552.65.camel@fz.local>
[-- Attachment #1: Type: text/plain, Size: 1952 bytes --]
Am Freitag, den 12.06.2009, 01:25 +0200 schrieb Felix Zielcke:
> Am Freitag, den 12.06.2009, 01:21 +0200 schrieb Felix Zielcke:
> > Am Donnerstag, den 11.06.2009, 01:00 +0200 schrieb Felix Zielcke:
> > > Am Dienstag, den 09.06.2009, 23:51 +0200 schrieb Vladimir 'phcoder'
> > > Serbinenko:
> > >
> > > > +
> > > > +char *grub_make_system_path_relative_to_its_root (char *path)
> > > > +{
> > > > +
> > > > + struct stat st;
> > > > + char buf[500], buf2[500];
> > > > Use malloc instead of static allocation
> > >
> > > Changed.
> > >
> > > > + p = strrchr (buf, '/');
> > > > + if (p != buf)
> > > > + *p = 0;
> > > > + else *++p = 0;
> > > > You assume path starts with /. You have to check this. Otherwise you
> > > > may get sigsegv
> > >
> > > Changed.
> > > > + strcpy(buf2,buf);
> > > > Just save (p - buf) instead of copying buf to buf2
> > >
> > > I did this now if realpath () isn't avaible.
> > > Now realpath is used in case it's avaible. POSIX specifies it and
> > > readlink is actually using it if it's avaible. I didn't read the source
> > > correctly.
> > > The problem is just Cygwin. It has it but it returns the cygwin path.
> > > So C:\\Windows would get /cygdrive/c/windows, which is easy to handle.
> > > But realpath ("/boot/grub") would return /boot/grub which isn't true
> > > from Windows/GRUB point of view.
> > > Maybe Christian and Bean can say something about it.
> > > MingW doestn't have it and I don't know what Windows would have, so the
> > > MingW users would still use my own way.
> >
> > Here's now a new one which aborts if realpath is avaible but doestn't
> > support (path, NULL)
> > and the fallback function is changed to dynamically allocate the memory.
> > And now all memory is properly free'd
>
> args just noticed I forgot the *free_ptr = buf2;
> I'm too lazy now to send an extra patch just for this.
Ok here's a new one which compiles without warnings.
--
Felix Zielcke
[-- Attachment #2: make_sys_path_relative.patch.6 --]
[-- Type: text/plain, Size: 4578 bytes --]
2009-06-12 Felix Zielcke <fzielcke@z-51.de>
* configure.ac (AC_CHECK_FUNCS): Add realpath.
* include/grub/util/hostdisk.c
(grub_make_system_path_relative_to_its_root): New function
prototype.
* util/hostdisk.c: Include <stdint.h>.
(grub_make_system_path_relative_to_its_root): New function.
* util/i386/pc/grub-setup.c (setup): Use
grub_make_system_path_relative_to_its_root to make core_path_dev
relative to the partition.
diff --git a/configure.ac b/configure.ac
index b0f7bb7..9d594db 100644
--- a/configure.ac
+++ b/configure.ac
@@ -196,7 +196,7 @@ if test "$target_cpu"-"$platform" = i386-pc; then
fi
# Check for functions.
-AC_CHECK_FUNCS(posix_memalign memalign asprintf)
+AC_CHECK_FUNCS(posix_memalign memalign asprintf realpath)
#
# Check for target programs.
diff --git a/include/grub/util/hostdisk.h b/include/grub/util/hostdisk.h
index 21efb0d..5c648a1 100644
--- a/include/grub/util/hostdisk.h
+++ b/include/grub/util/hostdisk.h
@@ -23,5 +23,6 @@
void grub_util_biosdisk_init (const char *dev_map);
void grub_util_biosdisk_fini (void);
char *grub_util_biosdisk_get_grub_dev (const char *os_dev);
+char *grub_make_system_path_relative_to_its_root (char *path, char **free_ptr);
#endif /* ! GRUB_BIOSDISK_MACHINE_UTIL_HEADER */
diff --git a/util/hostdisk.c b/util/hostdisk.c
index 1844a7e..25d01b2 100644
--- a/util/hostdisk.c
+++ b/util/hostdisk.c
@@ -27,6 +27,7 @@
#include <grub/misc.h>
#include <stdio.h>
+#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
@@ -1076,3 +1077,97 @@ grub_util_biosdisk_get_grub_dev (const char *os_dev)
return make_device_name (drive, -1, -1);
#endif
}
+
+char *
+grub_make_system_path_relative_to_its_root (char *path, char **free_ptr)
+{
+ struct stat st;
+ char *buf, *buf2;
+ uintptr_t offset = 0;
+ dev_t num;
+ size_t len;
+ char *p;
+#ifndef HAVE_REALPATH
+ size_t len2;
+#endif
+
+
+#ifdef HAVE_REALPATH
+ p = realpath (path, NULL);
+
+ if (p == NULL && errno != EINVAL)
+ grub_util_error ("failed to get realpath of %s", path);
+ else
+ grub_util_error ("realpath not supporting (path, NULL)");
+ len = strlen (p) + 1;
+ buf = xmalloc (len);
+ buf2 = xmalloc (len);
+# ifdef __CYGWIN__
+ if (strncmp (p, 10, "/cygdrive/") == 0)
+ strcpy (buf, p + sizeof ("/cygdrive/c") - 1);
+ else
+ grub_util_error "path not under /cygdrive/";
+# else
+ strcpy (buf, p);
+#endif
+ free (p);
+#else /* ! HAVE_REALPATH */
+# warning "The function `grub_make_system_path_relative_to_its_root' might not work on your OS correctly."
+ if (*path != '/')
+ {
+ len2 = 4096;
+ do
+ {
+ p = getcwd (buf, len)
+ if (p == NULL)
+ {
+ if (errno != ERANGE)
+ grub_util_error ("can not get current working directory");
+ else
+ len2 *= 2;
+ }
+ } while (p == NULL)
+
+ buf = xmalloc (strlen (path) + len2 + 1);
+ strcat (buf, "/");
+ strcat (buf, path);
+ }
+ else
+ {
+ buf = xmalloc (strlen (path) + 1);
+ strcpy (buf, path)
+ }
+#endif /* ! HAVE_REALPATH */
+ buf2 = xmalloc (strlen (buf) + 1);
+ strcpy (buf2, buf);
+ *free_ptr = buf2;
+ if (stat (buf, &st) < 0)
+ grub_util_error ("can not stat %s", p);
+
+ num = st.st_dev;
+ while (1)
+ {
+ p = strrchr (buf, '/');
+ if (p == NULL)
+ grub_util_error ("FIXME no / in buf");
+ if (p != buf)
+ *p = 0;
+ else
+ *++p = 0;
+
+ if (stat (buf, &st) < 0)
+ grub_util_error ("can not stat %s", buf);
+
+ if (st.st_dev != num)
+ break;
+
+ offset = p - buf;
+ if (offset == 1)
+ {
+ free (buf);
+ return buf2;
+ }
+ }
+ free (buf);
+ return buf2 + offset;
+}
diff --git a/util/i386/pc/grub-setup.c b/util/i386/pc/grub-setup.c
index bdf234c..395db9d 100644
--- a/util/i386/pc/grub-setup.c
+++ b/util/i386/pc/grub-setup.c
@@ -89,7 +89,7 @@ setup (const char *dir,
const char *root, const char *dest, int must_embed, int force)
{
char *boot_path, *core_path, *core_path_dev;
- char *boot_img, *core_img;
+ char *boot_img, *core_img, *p, *free_ptr;
size_t boot_size, core_size;
grub_uint16_t core_sectors;
grub_device_t root_dev, dest_dev;
@@ -404,7 +404,10 @@ unable_to_embed:
/* Make sure that GRUB reads the identical image as the OS. */
tmp_img = xmalloc (core_size);
- core_path_dev = grub_util_get_path (dir, core_file);
+ p = grub_util_get_path (dir, core_file);
+ core_path_dev = grub_make_system_path_relative_to_its_root (p, &free_ptr);
+ free (p);
+ free (free_ptr);
/* It is a Good Thing to sync two times. */
sync ();
next prev parent reply other threads:[~2009-06-12 10:28 UTC|newest]
Thread overview: 14+ messages / expand[flat|nested] mbox.gz Atom feed top
2009-05-06 14:31 grub-install --root-directory=/mnt /dev/sda1 fails Felix Zielcke
2009-05-06 15:12 ` Vladimir 'phcoder' Serbinenko
2009-06-01 19:39 ` Felix Zielcke
2009-06-08 21:20 ` [PATCH] " Felix Zielcke
2009-06-09 21:51 ` Vladimir 'phcoder' Serbinenko
2009-06-10 23:00 ` Felix Zielcke
2009-06-11 23:21 ` Felix Zielcke
2009-06-11 23:25 ` Felix Zielcke
2009-06-12 10:28 ` Felix Zielcke [this message]
2009-06-12 16:21 ` Pavel Roskin
2009-06-12 16:33 ` Felix Zielcke
2009-07-01 14:33 ` Felix Zielcke
2009-07-04 20:09 ` Robert Millan
2009-07-08 14:16 ` Felix Zielcke
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1244802503.3181.0.camel@fz.local \
--to=fzielcke@z-51.de \
--cc=grub-devel@gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.