grub-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [PATCH] Re: Revision 2136 breaks two-disk configuarion


From: Pavel Roskin
Subject: Re: [PATCH] Re: Revision 2136 breaks two-disk configuarion
Date: Mon, 27 Apr 2009 23:50:45 -0400

On Mon, 2009-04-27 at 18:45 -0700, David Miller wrote:

> Thanks for fixing this Pavel.  I suspect this bug is why the close was
> left as a NOP function all of this time.

Maybe.

> Please commit this as it seems you haven't already :-)

I was about to commit it when I realized that the same could be done
using a reference counter in struct grub_partition.  It may be an
overkill for this purpose, but maybe there will be more users of the
partition table in the future.  Besides, this patch could set an
example.  Please have a cursory look to make sure it's a good example.

ChangeLog:
        * grub/partition.h (struct grub_partition): Add refcount.
        (grub_partition_ref): New inline function.
        (grub_partition_unref): Likewise.
        * kern/disk.c (grub_disk_close): Use grub_partition_unref().
        * disk/fs_uuid.c (grub_fs_uuid_open): Use grub_partition_ref().

diff --git a/disk/fs_uuid.c b/disk/fs_uuid.c
index 9d83bb8..12086b2 100644
--- a/disk/fs_uuid.c
+++ b/disk/fs_uuid.c
@@ -25,6 +25,7 @@
 #include <grub/types.h>
 
 #include <grub/fs.h>
+#include <grub/partition.h>
 
 static grub_device_t
 search_fs_uuid (const char *key, unsigned long *count)
@@ -88,7 +89,7 @@ grub_fs_uuid_open (const char *name, grub_disk_t disk)
 
   disk->total_sectors = dev->disk->total_sectors;
   disk->has_partitions = 0;
-  disk->partition = dev->disk->partition;
+  disk->partition = grub_partition_ref (dev->disk->partition);
   disk->data = dev->disk;
 
   return GRUB_ERR_NONE;
diff --git a/include/grub/partition.h b/include/grub/partition.h
index 6e74cd5..c3e4d15 100644
--- a/include/grub/partition.h
+++ b/include/grub/partition.h
@@ -62,6 +62,9 @@ struct grub_partition
 
   /* The index of this partition in the partition table.  */
   int index;
+
+  /* Reference count.  */
+  int refcount;
   
   /* Partition map type specific data.  */
   void *data;
@@ -110,4 +113,23 @@ grub_partition_get_len (const grub_partition_t p)
   return p->len;
 }
 
+/* Return a copy by reference of the original partition.  */
+static inline grub_partition_t
+grub_partition_ref (grub_partition_t p)
+{
+  if (p)
+    p->refcount++;
+  return p;
+}
+
+/* Return partition to be freed if it can be freed.  */
+static inline grub_partition_t
+grub_partition_unref (const grub_partition_t p)
+{
+  if (p && p->refcount-- <= 0)
+    return p;
+  else
+    return 0;
+}
+
 #endif /* ! GRUB_PART_HEADER */
diff --git a/kern/disk.c b/kern/disk.c
index 8a92989..070cab3 100644
--- a/kern/disk.c
+++ b/kern/disk.c
@@ -324,7 +324,7 @@ grub_disk_close (grub_disk_t disk)
   /* Reset the timer.  */
   grub_last_time = grub_get_time_ms ();
 
-  grub_free (disk->partition);
+  grub_free (grub_partition_unref (disk->partition));
   grub_free ((void *) disk->name);
   grub_free (disk);
 }

-- 
Regards,
Pavel Roskin




reply via email to

[Prev in Thread] Current Thread [Next in Thread]