News:

MASM32 SDK Description, downloads and other helpful links
MASM32.com New Forum Link
masmforum WebSite

Nested structure in nested union initialization

Started by MazeGen, February 26, 2008, 02:00:51 PM

Previous topic - Next topic

MazeGen

This initialization is driving me mad. Look at the ABCD structure, AN_UNION union and A_STRUCT struct declaration (you can assemble it easily):


.686
.MODEL FLAT, STDCALL

ABCD STRUCT
efg DD ?
hij DW ?
UNION AN_UNION
  union_foo DD ?
  STRUCT A_STRUCT
   struct_foo1 DW ?
   struct_foo2 DW ?
  ENDS
ENDS
klm db ?
opr dw ?
ABCD ENDS

.DATA
UNION_FOO ABCD <01, 02, {100}, 03, 04>

.CODE
Start:
mov [UNION_FOO].AN_UNION.A_STRUCT.struct_foo1, ax
mov [UNION_FOO].AN_UNION.A_STRUCT.struct_foo2, bx
END Start


AN_UNION is nested union in ABCD structure and A_STRUCT is nested structure in AN_UNION union.

I can initialize union_foo at compile-time using the UNION_FOO declaration above. However, I don't know how to initialize struct_foo1 and struct_foo2 similar way (it is possible to do it at run-time, as shown above, but it is not what I want). I suppose the way should be using double brackets (first bracket means start of nested union, second one start of nested structure):


.DATA
STRUCT_FOO ABCD <10, 20, {{100,50}}, 30, 40>


This doesn't work neither :(

I have also digged in MASM manual, but haven't found much info about such a complex nesting.

Jimg

the only way I know would be

UNION_FOO ABCD <01, 02, {3 or 4 shl 16}>

you can only initialize the first item in a union, in this case, union_foo.
you can't move union_foo below struct A_STRUCT because the first item in a union must be the largest or Masm will just initialize any extras to zeros.

By the way, there is an error in your example:
UNION_FOO ABCD <01, 02, {100}, 03, 04>
I think is incorrect, even though Masm doesn't complain about it.  The  03,04  are not used since the 100 fills union_foo and thus A_STRUCT
It should just be
UNION_FOO ABCD <01, 02, {100}>

ToutEnMasm

just bad syntax,
Quote
   mov UNION_FOO.AN_UNION.A_STRUCT.struct_foo1, ax
   mov UNION_FOO.AN_UNION.A_STRUCT.struct_foo2, bx

MazeGen

Quote from: Jimg
By the way, there is an error in your example:
UNION_FOO ABCD <01, 02, {100}, 03, 04>
I think is incorrect, even though Masm doesn't complain about it.  The  03,04  are not used since the 100 fills union_foo and thus A_STRUCT
It should just be
UNION_FOO ABCD <01, 02, {100}>

According to the listing, you're wrong here, UNION_FOO seems to be properly initialized, "03" initializes UNION_FOO.klm and "04" UNION_FOO.opr:


00000000 00000001 0002 UNION_FOO ABCD <01, 02, {100}, 03, 04>
   00000064 03
   0004


Quote from: Jimg
you can only initialize the first item in a union, in this case, union_foo.

Are you sure? I'm still hoping that there's a way how to initialize any item of an union (since we can use [UNION_FOO].AN_UNION.A_STRUCT.struct_foo1 notation, which is resolved by the assembler at compile-time without any problems).


Quote from: Jimg
you can't move union_foo below struct A_STRUCT because the first item in a union must be the largest or Masm will just initialize any extras to zeros.

Nice idea! Note that both items are the same in terms of size: both A_STRUCT and union_foo is DWORD in size.

However, I get reversed error now. Using this modification:


ABCD STRUCT
efg DD ?
hij DW ?
UNION AN_UNION
  STRUCT A_STRUCT
   struct_foo1 DW 0
   struct_foo2 DW ?
  ENDS
  union_foo DD ?
ENDS
klm db ?
opr dw ?
ABCD ENDS


I can do now

STRUCT_FOO ABCD <10, 20, {{100,50}}, 30, 40>

And I can't do

UNION_FOO ABCD <01, 02, {100}, 03, 04>

:(


Quote from: ToutEnMasm
just bad syntax,

Thanks, I have corrected my inital post.

Jimg

QuoteAccording to the listing, you're wrong here, UNION_FOO seems to be properly initialized, "03" initializes UNION_FOO.klm and "04" UNION_FOO.opr:
uh....   Not enough coffee yet this morning I guess.

QuoteI can do now

Code:
STRUCT_FOO ABCD <10, 20, {{100,50}}, 30, 40>

And I can't do

Code:
UNION_FOO ABCD <01, 02, {100}, 03, 04>

Correct. You can only initialize the first item of a union.   You could however make two structures, one each way, and initialize using the form you prefer at the time.

MazeGen

Quote from: Jimg on February 26, 2008, 05:49:49 PM
You could however make two structures, one each way, and initialize using the form you prefer at the time.

That would make the structure overcomplicated, besides the fact I can't get it working as well. I'll remove the union_foo to make the declaration simple and the initialization a bit more complicated.

Thanks for your help, Jimg.

ToutEnMasm


By experiment with the windows.sdk,a good thing to do is:
Change internal union to external union,internal union make often "internal error" with ml.
External unions and structures are less limited in size  and are no bugs.