Page 1 of 1

StructureUnion causes problems

Posted: Sat Aug 21, 2010 8:17 pm
by Josef S
Hello community,

I'am new here and I use the german forum since ca. two years. Today I've posted in the german forum a topic about "StructureUnion" and got no consents on my problem.

So I think... let's try it here :mrgreen:

Here is my following problem:

Code: Select all

Structure Variant
  Type.i
  StructureUnion
    Integer.i
    String.s
  EndStructureUnion
EndStructure
The PB compiler forbids me to use integers and strings together in a StructureUnion. I know that this mix causes problems with "InitializeStructure", "CopyStructure" and the assignment between structured variables. But I need this combination of these datatypes in my own scriptlanguage, named Operno. I had no problems in the previous PB versions, but 4.50 RC2 builds me barriers.

Why not handle invalid StructureUnions in the compiler functions (see above), instead of handling it in the definition of a structure? The size of strings (more exact - it's pointers) is constant and the initialization is called automaticly in the first runtime assignment.

I hope you can understand my (hopefully not bad) english and also my problem. :)

Josef

Re: StructureUnion causes problems

Posted: Sat Aug 21, 2010 8:38 pm
by KJ67
Welcome Josef!

You may find this thread "problem with structure unions" intresting.

Re: StructureUnion causes problems

Posted: Sat Aug 21, 2010 8:51 pm
by Josef S
hi KJ67,

thank you for your link to this thread...

I'am sorry to say that this thread does not really solve my problem. To implement the workaround in a 26.000 lines project is crazy. :wink:

So I just hilight my suggestion:
If PB uses a failure handling in the aforementioned functions, instead within a declaration of a structure, then I can use strings and integers together in a StructureUnion.

To avoid memory leaks is no problem:

Code: Select all

Structure Variant
  Type.i
  StructureUnion
    Integer.i
    String.s
  EndStructureUnion
EndStructure
Structure VariantS ;helps to copy and release a variant
  Type.i
  String.s
EndStructure

Procedure.i CreateVariantS(String.s)
  Protected *Variant.Variant
  
  *Variant = AllocateMemory(SizeOf(Variant))
  *Variant\Type = 1 ;= String
  *Variant\String = String
  
  ProcedureReturn *Variant
EndProcedure
Procedure.i DoSomething(*Variant.Variant)
  Select *Variant\Type
    Case 0
      Debug "INT: " + Str(*Variant\Integer)
    Case 1
      Debug "STR: " + *Variant\String
  EndSelect
EndProcedure
Procedure.i FreeVariant(*Variant.Variant)
  If *Variant\Type = 1
    ;Clear the content of the string:
    ClearStructure(*Variant, VariantS)
  EndIf
  ProcedureReturn FreeMemory(*Variant)
EndProcedure
EDIT: otherwise I must recode it to something like this:

Code: Select all

Structure Variant
  Type.i
  *Memory
EndStructure
Structure VariantI
  Type.i
  Integer.i
EndStructure
Structure VariantS
  Type.i
  String.s
EndStructure

Procedure.i CreateVariantS(String.s)
  Protected *Variant.VariantS
  
  *Variant = AllocateMemory(SizeOf(Variant))
  *Variant\Type = 1 ;= String
  *Variant\String = String
  
  ProcedureReturn *Variant
EndProcedure
Procedure.i DoSomething(*Variant.Variant)
  Protected *VariantI.VariantI, *VariantS.VariantS ;unnecessary but needed :(
  
  Select *Variant\Type
    Case 0
      *VariantI = *Variant
      Debug "INT: " + Str(*VariantI\Integer)
    Case 1
      *VariantS = *Variant
      Debug "STR: " + *VariantS\String
  EndSelect
EndProcedure
Procedure.i FreeVariant(*Variant.Variant)
  If *Variant\Type = 1
    ;Clear the content of the string:
    ClearStructure(*Variant, VariantS)
  EndIf
  ProcedureReturn FreeMemory(*Variant)
EndProcedure
Josef

Re: StructureUnion causes problems

Posted: Sat Aug 21, 2010 11:26 pm
by freak
Its not about these compiler commands only. Previous versions had memory leaks whenever such a structured variable would go out of scope (any string gets leaked). Since the situation gets even more complicated with things like arrays or lists in structures, we decided to disallow the mixing of types with automatically managed memory (strings, dynamic arrays, lists, maps) with other types in unions.

If you want to mix in a string with other types, you have to allocate and manage the string memory yourself (AllocateMemory, PeekS, PokeS), because the compiler cannot do it for you as it does not know what you have put in there.

Re: StructureUnion causes problems

Posted: Sun Aug 22, 2010 12:41 am
by PMV

Code: Select all

Structure Variant
  Type.i
  StructureUnion
    *String.STRING
    Integer.i
  EndStructureUnion
EndStructure


Procedure.i CreateVariantS(String.s)
  Protected *Variant.Variant
  
  *Variant = AllocateMemory(SizeOf(Variant))
  *Variant\Type = 1 ;= String
  *Variant\String = AllocateMemory(SizeOf(STRING))
  *Variant\String\s = String
  
  ProcedureReturn *Variant
EndProcedure
Procedure.i DoSomething(*Variant.Variant)
  
  Select *Variant\Type
    Case 0
      Debug "INT: " + Str(*Variant\Integer)
    Case 1
      Debug "STR: " + *Variant\String\s
  EndSelect
EndProcedure
Procedure.i FreeVariant(*Variant.Variant)
  If *Variant\Type = 1
    ;Clear the content of the string:
    ClearStructure(*Variant\String, STRING)
    FreeMemory(*Variant\String)
  EndIf
  ProcedureReturn FreeMemory(*Variant)
EndProcedure

Re: StructureUnion causes problems

Posted: Sun Aug 22, 2010 9:04 am
by Josef S
@PMV: I am afraid that I must use this workaround. :cry:

But I also understand Freak, that local structured variables will not be correctly released with the allowed combination in the previous versions of PB.

So thank you for your answers.
I think I want to be active here for a longer time to improve my englisch. :D

Josef