[gvfs] metadata: fix misaligned accesses to 64bit data
- From: Ondrej Holy <oholy src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gvfs] metadata: fix misaligned accesses to 64bit data
- Date: Thu, 29 May 2014 14:06:46 +0000 (UTC)
commit d17e4dbfef0b9859b7d8a149b931cf685f9b4e15
Author: Michael Cree <mcree orcon net nz>
Date: Thu Apr 17 12:35:25 2014 +0200
metadata: fix misaligned accesses to 64bit data
Unfortunately the journal entries are only aligned to 32 bit boundaries
but on some 64-bit RISC architectures (e.g. Alpha) this is insufficient
to guarantee correct alignment of 64-bit accesses. This is not a show
stopper but does cause inefficient traps to the kernel and pollution of
kernel logs. Rather than fix the alignment we provide a helper function,
dependent on features specific to gcc, to correctly access a 64-bit datum
that may be misaligned.
https://bugzilla.gnome.org/show_bug.cgi?id=726456
metadata/metatree.c | 25 +++++++++++++++++++++++--
1 files changed, 23 insertions(+), 2 deletions(-)
---
diff --git a/metadata/metatree.c b/metadata/metatree.c
index a6b3183..43766c8 100644
--- a/metadata/metatree.c
+++ b/metadata/metatree.c
@@ -132,6 +132,27 @@ struct _MetaTree {
MetaJournal *journal;
};
+/* Unfortunately the journal entries are only aligned to 32 bit boundaries
+ * but on some 64-bit RISC architectures (e.g. Alpha) this is insufficient
+ * to guarantee correct alignment of 64-bit accesses. This is not a show
+ * stopper but does cause inefficient traps to the kernel and pollution of
+ * kernel logs. Rather than fix the alignment we provide a helper function,
+ * dependent on features specific to gcc, to correctly access a 64-bit datum
+ * that may be misaligned.
+ *
+ * See https://bugzilla.gnome.org/show_bug.cgi?id=726456
+ */
+#if defined(__GNUC__) && (defined(__alpha__) || defined(__mips__) || defined(__sparc__))
+struct una_u64 { guint64 x __attribute__((packed)); };
+static inline guint64 ldq_u(guint64 *p)
+{
+ const struct una_u64 *ptr = (const struct una_u64 *) p;
+ return ptr->x;
+}
+#else
+#define ldq_u(x) (*(x))
+#endif
+
static void meta_tree_refresh_locked (MetaTree *tree,
gboolean force_reread);
static MetaJournal *meta_journal_open (MetaTree *tree,
@@ -1230,7 +1251,7 @@ meta_journal_iterate (MetaJournal *journal,
break;
}
- mtime = GUINT64_FROM_BE (entry->mtime);
+ mtime = GUINT64_FROM_BE (ldq_u (&(entry->mtime)));
journal_path = &entry->path[0];
if (journal_entry_is_key_type (entry) &&
@@ -2214,7 +2235,7 @@ apply_journal_to_builder (MetaTree *tree,
entry = journal->first_entry;
while (entry < journal->last_entry)
{
- mtime = GUINT64_FROM_BE (entry->mtime);
+ mtime = GUINT64_FROM_BE (ldq_u (&(entry->mtime)));
journal_path = &entry->path[0];
switch (entry->entry_type)
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]