Yahoo Groups archive

Lpc2000

Index last updated: 2026-04-28 23:31 UTC

Thread

UBYTE alignment problem in structure

UBYTE alignment problem in structure

2005-11-09 by lehmannjluc

I have the following structure definition:
=========================
#define PTR_ATTR                
#define VPC3_PTR                PTR_ATTR *
typedef struct
{
    UBYTE int_req1;
    UBYTE int_req2;
    union
    {
        struct
        {
            UBYTE int_reg1;
            UBYTE int_reg2;
            UBYTE status_L;
            UBYTE status_H;
        } (ULONG rd);
        struct
        {
            UBYTE int_ack1;
            UBYTE int_ack2;
            UBYTE int_mask_L;
            UBYTE int_mask_H;
        } wr;
    } isreg;
    UBYTE mode_reg0_L;
    //....and so on with various union and sub-structure.
}  VPC3_STRUC;
#define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
extern VPC3_STRUC_PTR     p_Vpc3;
=========================
This structure is used to point to a real hardware address.
And the code is:
=========================
#define EM_START_ADDR_BANK3	(0x83000000)
#define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
    p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
=========================
But when we compile using the Ashling dev tools with GNU compiler 
version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
&p_Vpc3->int_req1 points to 0x83000000 (which is correct) but whereas 
I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, it 
points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
0x83000008 rather than the expected 0x83000006) and so on with the 
following byte of the structure.  
It looks like the compiler aligns the union on 32 bits, so drop an 
empty 2 bytes after int_req2 element.
I searched the archive for similar problem, but also I found some 
alignment questions, none matched my problem or where even close.

I am using a library supplied by the hardware chip manufacturer and I 
cannot just rewrite the whole library.
What could be done to force the compiler to point byte after byte and 
not align to 32-bit ARM word ? If it can be done at all...

Thanks in advance for any help you can provide,
Jean-Luc Lehmann

RE: [lpc2000] UBYTE alignment problem in structure

2005-11-09 by Gromann, Klaus

attribute packed should help.
But take care, the ARM7 processor can't access 32-bit wide to an address
that is not 32-bit aligned.
If you try to read 32 bit from the address 0x83000002, you don't get the
expected result, but without any error message or exception.

Klaus
Show quoted textHide quoted text
-----Original Message-----
From: lpc2000@yahoogroups.com [mailto:lpc2000@yahoogroups.com] On Behalf
Of lehmannjluc
Sent: Wednesday, November 09, 2005 11:55 AM
To: lpc2000@yahoogroups.com
Subject: [lpc2000] UBYTE alignment problem in structure


I have the following structure definition: =========================
#define PTR_ATTR                
#define VPC3_PTR                PTR_ATTR *
typedef struct
{
    UBYTE int_req1;
    UBYTE int_req2;
    union
    {
        struct
        {
            UBYTE int_reg1;
            UBYTE int_reg2;
            UBYTE status_L;
            UBYTE status_H;
        } (ULONG rd);
        struct
        {
            UBYTE int_ack1;
            UBYTE int_ack2;
            UBYTE int_mask_L;
            UBYTE int_mask_H;
        } wr;
    } isreg;
    UBYTE mode_reg0_L;
    //....and so on with various union and sub-structure.
}  VPC3_STRUC;
#define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
extern VPC3_STRUC_PTR     p_Vpc3;
=========================
This structure is used to point to a real hardware address.
And the code is:
=========================
#define EM_START_ADDR_BANK3	(0x83000000)
#define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
    p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
========================= But when we compile using the Ashling dev
tools with GNU compiler 
version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
&p_Vpc3->int_req1 points to 0x83000000 (which is correct) but whereas 
I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, it 
points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
0x83000008 rather than the expected 0x83000006) and so on with the 
following byte of the structure.  
It looks like the compiler aligns the union on 32 bits, so drop an 
empty 2 bytes after int_req2 element.
I searched the archive for similar problem, but also I found some 
alignment questions, none matched my problem or where even close.

I am using a library supplied by the hardware chip manufacturer and I 
cannot just rewrite the whole library.
What could be done to force the compiler to point byte after byte and 
not align to 32-bit ARM word ? If it can be done at all...

Thanks in advance for any help you can provide,
Jean-Luc Lehmann






 
Yahoo! Groups Links

Re: [lpc2000] UBYTE alignment problem in structure

2005-11-09 by Tom Walsh

Gromann, Klaus wrote:

>attribute packed should help.
>But take care, the ARM7 processor can't access 32-bit wide to an address
>that is not 32-bit aligned.
>If you try to read 32 bit from the address 0x83000002, you don't get the
>expected result, but without any error message or exception.
>
>  
>

No, you cannot do that.  *THAT* is what is called "Alignment Fault" and 
an exception is thrown.

TomW


>Klaus
>
>-----Original Message-----
>From: lpc2000@yahoogroups.com [mailto:lpc2000@yahoogroups.com] On Behalf
>Of lehmannjluc
>Sent: Wednesday, November 09, 2005 11:55 AM
>To: lpc2000@yahoogroups.com
>Subject: [lpc2000] UBYTE alignment problem in structure
>
>
>I have the following structure definition: =========================
>#define PTR_ATTR                
>#define VPC3_PTR                PTR_ATTR *
>typedef struct
>{
>    UBYTE int_req1;
>    UBYTE int_req2;
>    union
>    {
>        struct
>        {
>            UBYTE int_reg1;
>            UBYTE int_reg2;
>            UBYTE status_L;
>            UBYTE status_H;
>        } (ULONG rd);
>        struct
>        {
>            UBYTE int_ack1;
>            UBYTE int_ack2;
>            UBYTE int_mask_L;
>            UBYTE int_mask_H;
>        } wr;
>    } isreg;
>    UBYTE mode_reg0_L;
>    //....and so on with various union and sub-structure.
>}  VPC3_STRUC;
>#define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
>extern VPC3_STRUC_PTR     p_Vpc3;
>=========================
>This structure is used to point to a real hardware address.
>And the code is:
>=========================
>#define EM_START_ADDR_BANK3	(0x83000000)
>#define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
>    p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
>========================= But when we compile using the Ashling dev
>tools with GNU compiler 
>version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
>&p_Vpc3->int_req1 points to 0x83000000 (which is correct) but whereas 
>I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, it 
>points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
>0x83000008 rather than the expected 0x83000006) and so on with the 
>following byte of the structure.  
>It looks like the compiler aligns the union on 32 bits, so drop an 
>empty 2 bytes after int_req2 element.
>I searched the archive for similar problem, but also I found some 
>alignment questions, none matched my problem or where even close.
>
>I am using a library supplied by the hardware chip manufacturer and I 
>cannot just rewrite the whole library.
>What could be done to force the compiler to point byte after byte and 
>not align to 32-bit ARM word ? If it can be done at all...
>
>Thanks in advance for any help you can provide,
>Jean-Luc Lehmann
>
>
>
>
>
>
> 
>Yahoo! Groups Links
>
>
>
> 
>
>
>
>
>
> 
>Yahoo! Groups Links
>
>
>
> 
>
>
>  
>


-- 
Tom Walsh - WN3L - Embedded Systems Consultant
http://openhardware.net, http://cyberiansoftware.com
"Windows? No thanks, I have work to do..."
----------------------------------------------------

Re: [lpc2000] UBYTE alignment problem in structure

2005-11-09 by Tom Walsh

lehmannjluc wrote:

>I have the following structure definition:
>=========================
>#define PTR_ATTR                
>#define VPC3_PTR                PTR_ATTR *
>typedef struct
>{
>    UBYTE int_req1;
>    UBYTE int_req2;
>    union
>    {
>        struct
>        {
>            UBYTE int_reg1;
>            UBYTE int_reg2;
>            UBYTE status_L;
>            UBYTE status_H;
>        } (ULONG rd);
>        struct
>        {
>            UBYTE int_ack1;
>            UBYTE int_ack2;
>            UBYTE int_mask_L;
>            UBYTE int_mask_H;
>        } wr;
>    } isreg;
>    UBYTE mode_reg0_L;
>    //....and so on with various union and sub-structure.
>}  VPC3_STRUC;
>#define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
>extern VPC3_STRUC_PTR     p_Vpc3;
>=========================
>This structure is used to point to a real hardware address.
>And the code is:
>=========================
>#define EM_START_ADDR_BANK3	(0x83000000)
>#define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
>    p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
>=========================
>But when we compile using the Ashling dev tools with GNU compiler 
>version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
>&p_Vpc3->int_req1 points to 0x83000000 (which is correct) but whereas 
>I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, it 
>points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
>0x83000008 rather than the expected 0x83000006) and so on with the 
>following byte of the structure.  
>It looks like the compiler aligns the union on 32 bits, so drop an 
>empty 2 bytes after int_req2 element.
>I searched the archive for similar problem, but also I found some 
>alignment questions, none matched my problem or where even close.
>  
>
Oh it is a common problem for an 8 bit programmer coming into a 32bit 
world, not just ARM but other processors.

There was a series of emails, recently, regarding data alignment of 
structure and ANSI standards.  The gist of that is that structures are 
begun on 32bit boundries (ARM) and the internal members are aligned in a 
fashion that is "comfortable" for the processor to access.

You may want to look into the "__attribute__ ((packed))" keyphrase of 
your C sources.  Also take a look at the objdump utility to see how the 
compiler generated your code..

TomW






>I am using a library supplied by the hardware chip manufacturer and I 
>cannot just rewrite the whole library.
>What could be done to force the compiler to point byte after byte and 
>not align to 32-bit ARM word ? If it can be done at all...
>
>Thanks in advance for any help you can provide,
>Jean-Luc Lehmann
>
>
>
>
>
>
> 
>Yahoo! Groups Links
>
>
>
> 
>
>
>  
>


-- 
Tom Walsh - WN3L - Embedded Systems Consultant
http://openhardware.net, http://cyberiansoftware.com
"Windows? No thanks, I have work to do..."
----------------------------------------------------

RE: [lpc2000] UBYTE alignment problem in structure

2005-11-09 by Gromann, Klaus

Hi Tom,

depends on the processor you have. I use an LPC 2292 and this one don't
have an alignement exception.

best regards
Klaus
Show quoted textHide quoted text
-----Original Message-----
From: lpc2000@yahoogroups.com [mailto:lpc2000@yahoogroups.com] On Behalf
Of Tom Walsh
Sent: Wednesday, November 09, 2005 4:12 PM
To: lpc2000@yahoogroups.com
Subject: Re: [lpc2000] UBYTE alignment problem in structure


Gromann, Klaus wrote:

>attribute packed should help.
>But take care, the ARM7 processor can't access 32-bit wide to an 
>address that is not 32-bit aligned. If you try to read 32 bit from the 
>address 0x83000002, you don't get the expected result, but without any 
>error message or exception.
>
>  
>

No, you cannot do that.  *THAT* is what is called "Alignment Fault" and 
an exception is thrown.

TomW


>Klaus
>
>-----Original Message-----
>From: lpc2000@yahoogroups.com [mailto:lpc2000@yahoogroups.com] On 
>Behalf Of lehmannjluc
>Sent: Wednesday, November 09, 2005 11:55 AM
>To: lpc2000@yahoogroups.com
>Subject: [lpc2000] UBYTE alignment problem in structure
>
>
>I have the following structure definition: =========================
>#define PTR_ATTR                
>#define VPC3_PTR                PTR_ATTR *
>typedef struct
>{
>    UBYTE int_req1;
>    UBYTE int_req2;
>    union
>    {
>        struct
>        {
>            UBYTE int_reg1;
>            UBYTE int_reg2;
>            UBYTE status_L;
>            UBYTE status_H;
>        } (ULONG rd);
>        struct
>        {
>            UBYTE int_ack1;
>            UBYTE int_ack2;
>            UBYTE int_mask_L;
>            UBYTE int_mask_H;
>        } wr;
>    } isreg;
>    UBYTE mode_reg0_L;
>    //....and so on with various union and sub-structure.
>}  VPC3_STRUC;
>#define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
>extern VPC3_STRUC_PTR     p_Vpc3;
>=========================
>This structure is used to point to a real hardware address. And the 
>code is: =========================
>#define EM_START_ADDR_BANK3	(0x83000000)
>#define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
>    p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
>========================= But when we compile using the Ashling dev
>tools with GNU compiler 
>version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
>&p_Vpc3->int_req1 points to 0x83000000 (which is correct) but whereas 
>I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, it 
>points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
>0x83000008 rather than the expected 0x83000006) and so on with the 
>following byte of the structure.  
>It looks like the compiler aligns the union on 32 bits, so drop an 
>empty 2 bytes after int_req2 element.
>I searched the archive for similar problem, but also I found some 
>alignment questions, none matched my problem or where even close.
>
>I am using a library supplied by the hardware chip manufacturer and I
>cannot just rewrite the whole library.
>What could be done to force the compiler to point byte after byte and 
>not align to 32-bit ARM word ? If it can be done at all...
>
>Thanks in advance for any help you can provide,
>Jean-Luc Lehmann
>
>
>
>
>
>
> 
>Yahoo! Groups Links
>
>
>
> 
>
>
>
>
>
> 
>Yahoo! Groups Links
>
>
>
> 
>
>
>  
>


-- 
Tom Walsh - WN3L - Embedded Systems Consultant http://openhardware.net,
http://cyberiansoftware.com "Windows? No thanks, I have work to do..."
----------------------------------------------------





 
Yahoo! Groups Links

Re: UBYTE alignment problem in structure

2005-11-09 by brendanmurphy37

Hi,

Check out a recent post - message 10244.

Your example simply re-enforces the point I made there: trying to map 
hardware registers onto structures/bit-fields is just asking for 
trouble. Unfortunately, this is mostly discovered by (bitter and 
painful) experience.

There's a suggested alternative approach in message 10244, which has 
the advantage of simplicity and most importantly will not fail, 
regardless of compiler.

As others have pointed out, using "packed" structures can help on 
your specific point, but similarly as others have also pointed out 
can introduce yet more problems related to allignment.

Hope this helps!

Brendan

P.S. If someone can say why using structures/bit-fields is a 
recommended approach for accessing hardware, I'd be interested in 
hearing it. Maybe I'm missing something....

--- In lpc2000@yahoogroups.com, "lehmannjluc" <lehmannjl@n...> wrote:
>
> I have the following structure definition:
> =========================
> #define PTR_ATTR                
> #define VPC3_PTR                PTR_ATTR *
> typedef struct
> {
>     UBYTE int_req1;
>     UBYTE int_req2;
>     union
>     {
>         struct
>         {
>             UBYTE int_reg1;
>             UBYTE int_reg2;
>             UBYTE status_L;
>             UBYTE status_H;
>         } (ULONG rd);
>         struct
>         {
>             UBYTE int_ack1;
>             UBYTE int_ack2;
>             UBYTE int_mask_L;
>             UBYTE int_mask_H;
>         } wr;
>     } isreg;
>     UBYTE mode_reg0_L;
>     //....and so on with various union and sub-structure.
> }  VPC3_STRUC;
> #define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
> extern VPC3_STRUC_PTR     p_Vpc3;
> =========================
> This structure is used to point to a real hardware address.
> And the code is:
> =========================
> #define EM_START_ADDR_BANK3	(0x83000000)
> #define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
>     p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
> =========================
> But when we compile using the Ashling dev tools with GNU compiler 
> version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
> &p_Vpc3->int_req1 points to 0x83000000 (which is correct) but 
whereas 
> I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, 
it 
> points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points to 
> 0x83000008 rather than the expected 0x83000006) and so on with the 
> following byte of the structure.  
> It looks like the compiler aligns the union on 32 bits, so drop an 
> empty 2 bytes after int_req2 element.
> I searched the archive for similar problem, but also I found some 
> alignment questions, none matched my problem or where even close.
> 
> I am using a library supplied by the hardware chip manufacturer and 
I 
> cannot just rewrite the whole library.
> What could be done to force the compiler to point byte after byte 
and 
Show quoted textHide quoted text
> not align to 32-bit ARM word ? If it can be done at all...
> 
> Thanks in advance for any help you can provide,
> Jean-Luc Lehmann
>

Re: UBYTE alignment problem in structure

2005-11-10 by lehmannjluc

Hi,

I read your message, which by the way is 10224 (not 10244), and I 
agree with you. However our problem is that we are using a library 
provided by the supplier of one of the chip we use (Profichip). So we 
have to leave with it unless we want to rewrite everything.
We tried the __attribute__ ((packed)) and also some pragma: #pragma 
pack(1) and #pragma align(1)- of course not all at the same time - 
this improved the first part of the structure but after the second 
sub-structure we continuously got a jump in the address (the compiler 
keeps on forcing alignment to 32bit there).
So we are going to start modifying the code.
Thanks for your input.
Regards,
Jean-Luc
--- In lpc2000@yahoogroups.com, "brendanmurphy37" <brendan.murphy@i...
> wrote:
>
> 
> Hi,
> 
> Check out a recent post - message 10244.
> 
> Your example simply re-enforces the point I made there: trying to 
map 
> hardware registers onto structures/bit-fields is just asking for 
> trouble. Unfortunately, this is mostly discovered by (bitter and 
> painful) experience.
> 
> There's a suggested alternative approach in message 10244, which has 
> the advantage of simplicity and most importantly will not fail, 
> regardless of compiler.
> 
> As others have pointed out, using "packed" structures can help on 
> your specific point, but similarly as others have also pointed out 
> can introduce yet more problems related to allignment.
> 
> Hope this helps!
> 
> Brendan
> 
> P.S. If someone can say why using structures/bit-fields is a 
> recommended approach for accessing hardware, I'd be interested in 
> hearing it. Maybe I'm missing something....
> 
> --- In lpc2000@yahoogroups.com, "lehmannjluc" <lehmannjl@n...> 
wrote:
> >
> > I have the following structure definition:
> > =========================
> > #define PTR_ATTR                
> > #define VPC3_PTR                PTR_ATTR *
> > typedef struct
> > {
> >     UBYTE int_req1;
> >     UBYTE int_req2;
> >     union
> >     {
> >         struct
> >         {
> >             UBYTE int_reg1;
> >             UBYTE int_reg2;
> >             UBYTE status_L;
> >             UBYTE status_H;
> >         } (ULONG rd);
> >         struct
> >         {
> >             UBYTE int_ack1;
> >             UBYTE int_ack2;
> >             UBYTE int_mask_L;
> >             UBYTE int_mask_H;
> >         } wr;
> >     } isreg;
> >     UBYTE mode_reg0_L;
> >     //....and so on with various union and sub-structure.
> > }  VPC3_STRUC;
> > #define VPC3_STRUC_PTR    VPC3_STRUC    VPC3_PTR
> > extern VPC3_STRUC_PTR     p_Vpc3;
> > =========================
> > This structure is used to point to a real hardware address.
> > And the code is:
> > =========================
> > #define EM_START_ADDR_BANK3	(0x83000000)
> > #define VPC3_ASIC_ADDRESS	(EM_START_ADDR_BANK3 + 0x0000)
> >     p_Vpc3 = (VPC3_STRUC VPC3_PTR)VPC3_ASIC_ADDRESS;
> > =========================
> > But when we compile using the Ashling dev tools with GNU compiler 
> > version 3.4.2 for a LPC2214 ARM, I have an alignment problem.
> > &p_Vpc3->int_req1 points to 0x83000000 (which is correct) but 
> whereas 
> > I would expect &p_Vpc3->isreg.rd.int_reg1 to point to 0x83000002, 
> it 
> > points to 0x83000004 (same for &p_Vpc3->mode_reg0_L which points 
to 
> > 0x83000008 rather than the expected 0x83000006) and so on with the 
> > following byte of the structure.  
> > It looks like the compiler aligns the union on 32 bits, so drop an 
> > empty 2 bytes after int_req2 element.
> > I searched the archive for similar problem, but also I found some 
> > alignment questions, none matched my problem or where even close.
> > 
> > I am using a library supplied by the hardware chip manufacturer 
and 
Show quoted textHide quoted text
> I 
> > cannot just rewrite the whole library.
> > What could be done to force the compiler to point byte after byte 
> and 
> > not align to 32-bit ARM word ? If it can be done at all...
> > 
> > Thanks in advance for any help you can provide,
> > Jean-Luc Lehmann
> >
>

Move to quarantaine

This moves the raw source file on disk only. The archive index is not changed automatically, so you still need to run a manual refresh afterward.