From f7df30203dbed4fb2ef0ae92721433a00aded871 Mon Sep 17 00:00:00 2001 From: Haavard Skinnemoen Date: Mon, 9 Jul 2007 16:04:03 +0200 Subject: [PATCH] cistpl: Use get_unaligned when accessing possibly-unaligned data When trying to use the PCMCIA layer on AVR32, it crashed when parsing the CIS data because of an unaligned halfword access. So I went through cistpl.c and converted all the cases I could find of accessing data through something different than a u8 * and converted them to use get_unaligned() instead. Signed-off-by: Haavard Skinnemoen --- drivers/pcmcia/cistpl.c | 32 +++++++++++++++++--------------- 1 files changed, 17 insertions(+), 15 deletions(-) diff --git a/drivers/pcmcia/cistpl.c b/drivers/pcmcia/cistpl.c index d154dee..2ddacd4 100644 --- a/drivers/pcmcia/cistpl.c +++ b/drivers/pcmcia/cistpl.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include @@ -461,7 +462,7 @@ static int follow_link(struct pcmcia_socket *s, tuple_t *tuple) /* Get indirect link from the MFC tuple */ read_cis_cache(s, LINK_SPACE(tuple->Flags), tuple->LinkOffset, 5, link); - ofs = le32_to_cpu(*(__le32 *)(link+1)); + ofs = le32_to_cpu(get_unaligned((__le32 *)(link+1))); SPACE(tuple->Flags) = (link[0] == CISTPL_MFC_ATTR); /* Move to the next indirect link */ tuple->LinkOffset += 5; @@ -669,8 +670,9 @@ static int parse_checksum(tuple_t *tuple, cistpl_checksum_t *csum) if (tuple->TupleDataLen < 5) return CS_BAD_TUPLE; p = (u_char *)tuple->TupleData; - csum->addr = tuple->CISOffset+(short)le16_to_cpu(*(__le16 *)p)-2; - csum->len = le16_to_cpu(*(__le16 *)(p + 2)); + csum->addr = tuple->CISOffset + + (short)le16_to_cpu(get_unaligned((__le16 *)p)) -2; + csum->len = le16_to_cpu(get_unaligned((__le16 *)(p + 2))); csum->sum = *(p+4); return CS_SUCCESS; } @@ -681,7 +683,7 @@ static int parse_longlink(tuple_t *tuple, cistpl_longlink_t *link) { if (tuple->TupleDataLen < 4) return CS_BAD_TUPLE; - link->addr = le32_to_cpu(*(__le32 *)tuple->TupleData); + link->addr = le32_to_cpu(get_unaligned((__le32 *)tuple->TupleData)); return CS_SUCCESS; } @@ -700,7 +702,7 @@ static int parse_longlink_mfc(tuple_t *tuple, return CS_BAD_TUPLE; for (i = 0; i < link->nfn; i++) { link->fn[i].space = *p; p++; - link->fn[i].addr = le32_to_cpu(*(__le32 *)p); p += 4; + link->fn[i].addr = le32_to_cpu(get_unaligned((__le32 *)p)); p += 4; } return CS_SUCCESS; } @@ -791,8 +793,8 @@ static int parse_manfid(tuple_t *tuple, cistpl_manfid_t *m) if (tuple->TupleDataLen < 4) return CS_BAD_TUPLE; p = (__le16 *)tuple->TupleData; - m->manf = le16_to_cpu(p[0]); - m->card = le16_to_cpu(p[1]); + m->manf = le16_to_cpu(get_unaligned(&p[0])); + m->card = le16_to_cpu(get_unaligned(&p[1])); return CS_SUCCESS; } @@ -1091,7 +1093,7 @@ static int parse_cftable_entry(tuple_t *tuple, break; case 0x20: entry->mem.nwin = 1; - entry->mem.win[0].len = le16_to_cpu(*(__le16 *)p) << 8; + entry->mem.win[0].len = le16_to_cpu(get_unaligned((__le16 *)p)) << 8; entry->mem.win[0].card_addr = 0; entry->mem.win[0].host_addr = 0; p += 2; @@ -1099,9 +1101,9 @@ static int parse_cftable_entry(tuple_t *tuple, break; case 0x40: entry->mem.nwin = 1; - entry->mem.win[0].len = le16_to_cpu(*(__le16 *)p) << 8; + entry->mem.win[0].len = le16_to_cpu(get_unaligned((__le16 *)p)) << 8; entry->mem.win[0].card_addr = - le16_to_cpu(*(__le16 *)(p+2)) << 8; + le16_to_cpu(get_unaligned((__le16 *)(p+2))) << 8; entry->mem.win[0].host_addr = 0; p += 4; if (p > q) return CS_BAD_TUPLE; @@ -1138,7 +1140,7 @@ static int parse_bar(tuple_t *tuple, cistpl_bar_t *bar) p = (u_char *)tuple->TupleData; bar->attr = *p; p += 2; - bar->size = le32_to_cpu(*(__le32 *)p); + bar->size = le32_to_cpu(get_unaligned((__le32 *)p)); return CS_SUCCESS; } @@ -1151,7 +1153,7 @@ static int parse_config_cb(tuple_t *tuple, cistpl_config_t *config) return CS_BAD_TUPLE; config->last_idx = *(++p); p++; - config->base = le32_to_cpu(*(__le32 *)p); + config->base = le32_to_cpu(get_unaligned((__le32 *)p)); config->subtuples = tuple->TupleDataLen - 6; return CS_SUCCESS; } @@ -1267,7 +1269,7 @@ static int parse_vers_2(tuple_t *tuple, cistpl_vers_2_t *v2) v2->vers = p[0]; v2->comply = p[1]; - v2->dindex = le16_to_cpu(*(__le16 *)(p+2)); + v2->dindex = le16_to_cpu(get_unaligned((__le16 *)(p+2))); v2->vspec8 = p[6]; v2->vspec9 = p[7]; v2->nhdr = p[8]; @@ -1308,8 +1310,8 @@ static int parse_format(tuple_t *tuple, cistpl_format_t *fmt) fmt->type = p[0]; fmt->edc = p[1]; - fmt->offset = le32_to_cpu(*(__le32 *)(p+2)); - fmt->length = le32_to_cpu(*(__le32 *)(p+6)); + fmt->offset = le32_to_cpu(get_unaligned((__le32 *)(p+2))); + fmt->length = le32_to_cpu(get_unaligned((__le32 *)(p+6))); return CS_SUCCESS; } -- 1.5.2.3