On Fri, 2012-06-15 at 09:41 +0200, Daniel Baumann wrote: > On 06/15/2012 09:02 AM, shawn wrote: > > Yes it is, but here is a patch to fix it :-) > > great, thanks. >
OOPS! That patch broke all architectures where size of pointer != 4 --- !=8 + memcpy(offset, &t, sizeof(&offset)); needed to be + memcpy(offset, &t, sizeof(found_key.offset)); fixed version attached -- -Shawn Landden
>From 3aeccdcad77a5a64795bf3308970f5f2558f766d Mon Sep 17 00:00:00 2001 From: Shawn Landen <shawnland...@gmail.com> Date: Fri, 15 Jun 2012 06:58:44 +0000 Subject: [PATCH] fix unaligned memory accesses Fix creation of volumes using mkfs.btrfs on armv5. --- ctree.h | 26 ++++++++++++++++++++------ volumes.c | 5 +++-- 2 files changed, 23 insertions(+), 8 deletions(-) diff --git a/ctree.h b/ctree.h index 6545c50..ef3f0cc 100644 --- a/ctree.h +++ b/ctree.h @@ -19,6 +19,8 @@ #ifndef __BTRFS__ #define __BTRFS__ +#include <stdint.h> + #include "list.h" #include "kerncompat.h" #include "radix-tree.h" @@ -970,13 +972,17 @@ struct btrfs_root { static inline u##bits btrfs_##name(struct extent_buffer *eb) \ { \ struct btrfs_header *h = (struct btrfs_header *)eb->data; \ - return le##bits##_to_cpu(h->member); \ + uint##bits##_t t; \ + memcpy(&t, &h->member, sizeof(h->member)); \ + return le##bits##_to_cpu(t); \ } \ static inline void btrfs_set_##name(struct extent_buffer *eb, \ u##bits val) \ { \ struct btrfs_header *h = (struct btrfs_header *)eb->data; \ - h->member = cpu_to_le##bits(val); \ + uint##bits##_t t; \ + t = cpu_to_le##bits(val); \ + memcpy(&h->member, &t, sizeof(h->member)); \ } #define BTRFS_SETGET_FUNCS(name, type, member, bits) \ @@ -984,25 +990,33 @@ static inline u##bits btrfs_##name(struct extent_buffer *eb, \ type *s) \ { \ unsigned long offset = (unsigned long)s; \ + uint##bits##_t t; \ type *p = (type *) (eb->data + offset); \ - return le##bits##_to_cpu(p->member); \ + memcpy(&t, &p->member, sizeof(p->member)); \ + return le##bits##_to_cpu(t); \ } \ static inline void btrfs_set_##name(struct extent_buffer *eb, \ type *s, u##bits val) \ { \ unsigned long offset = (unsigned long)s; \ + uint##bits##_t t; \ type *p = (type *) (eb->data + offset); \ - p->member = cpu_to_le##bits(val); \ + t = cpu_to_le##bits(val); \ + memcpy(&p->member, &t, sizeof(p->member)); \ } #define BTRFS_SETGET_STACK_FUNCS(name, type, member, bits) \ static inline u##bits btrfs_##name(type *s) \ { \ - return le##bits##_to_cpu(s->member); \ + uint##bits##_t t; \ + memcpy(&t, &s->member, sizeof(s->member)); \ + return le##bits##_to_cpu(t); \ } \ static inline void btrfs_set_##name(type *s, u##bits val) \ { \ - s->member = cpu_to_le##bits(val); \ + uint##bits##_t t; \ + t = cpu_to_le##bits(val); \ + memcpy(&s->member, &t, sizeof(s->member)); \ } BTRFS_SETGET_FUNCS(device_type, struct btrfs_dev_item, type, 64); diff --git a/volumes.c b/volumes.c index 8dca5e1..0401eeb 100644 --- a/volumes.c +++ b/volumes.c @@ -425,10 +425,11 @@ static int find_next_chunk(struct btrfs_root *root, u64 objectid, u64 *offset) if (found_key.objectid != objectid) *offset = 0; else { + u64 t; chunk = btrfs_item_ptr(path->nodes[0], path->slots[0], struct btrfs_chunk); - *offset = found_key.offset + - btrfs_chunk_length(path->nodes[0], chunk); + t = found_key.offset + btrfs_chunk_length(path->nodes[0], chunk); + memcpy(offset, &t, sizeof(found_key.offset)); } } ret = 0; -- 1.7.10.4