orxOBJECT_KU32_FLAG_2D and orxObject_Create()

edited December 2014 in Help request
I have a problem creating the new orxObject instance without using the config.

I'm calling orxObject_Create() adding some structures to it and everything is fine. But when I try to pick the object with orxObject_Pick(), object is never picked.
So I debugged the orxObject_CreateFromConfig() and have noticed that at the end, it set the orxOBJECT_KU32_FLAG_2D as new flag for the object. So I've tried to set the orxOBJECT_KU32_FLAG_2D value (because it is private) flag to my object and everything is working right, now.

My question is, what is this flag doing? Can I somehow set it using API without using some internal constants (orxOBJECT_KU32_FLAG_2D)?

Thank You

Comments

  • edited December 2014
    I don't have the code with me to check, but that flag should be set depending on which orxGRAPHIC is linked to the object. I'll check it as soon as I can and fix it if need be. Thanks for the report. :)

    Out of curiosity, why do you prefer to use the non _FromConfig version? If you link additional structures to it, you'll be responsible for not only unlinking them but also deleting them (and handling object hierarchies gets also a bit more annoying than simply using a ChildList).

    That being said, it's not a bad practice, I was just curious. :)
  • edited December 2014
    Thanks for the reply,
    I'm using non-_FromConfig() version because sometimes I have some predefined "graphic"s and I don't know which one will be used by the given objects. So I'm dynamically creating the object and all the structures need. Maybe I could define some default object in config and use it as a "template" in the code.

    I didn't know that I'm responsible also for unlinking and deleting them. I was under impression that when the structure is linked, it will be managed by the object.

    edit: Could you point me to some source which could explain better when the structure needs to be managed explicitly and when not?
  • edited December 2014
    Well the general rule is actually rather straightforward and is all about symmetry: the one in charge of deleting something is the one who created it.

    When an orxGRAPHIC is created from within an orxObject_CreateFromConfig() call, it means the orxObject code is also in charge of deleting that orxGRAPHIC when not needed.
    If you manually create an orxGRAPHIC, even if you link it to an orxOBJECT, you'll still be in charge of its deletion (note that the unlink will be done automatically, however the orxGRAPHIC will still exist).

    From the top of my head, the only place where this rule can be bent is in when you transfer object ownership (orxObject_SetOwner()). An orxOBJECT which owns other orxOBJECTs will delete them upon its own deletion.
    Small example:
    orxOBJECT *A, *B;
    A = orxObject_Create();
    B = orxObject_Create();
    orxObject_SetOwner(B, A);
    orxObject_Delete(A); // This will also delete B as A owns B
    

    Note that when using the config property key ChildList, created sub-objets will both be parth of the 3D hierarchy of the parent at well as being owned by it. Example:

    Config:
    [A]
    ChildList = B
    
    [B]
    

    Code:
    orxOBJECT *A, *B;
    A = orxObject_CreateFromConfig("A"); // <= This also creates B as a child of A and sets A as its owner
    B = orxObject_GetOwnedChild(A);
    orxObject_SetOwner(B, orxNULL); // <= Now B is not owned by A anymore, however it's still part of its 3D hierarchy (ie. A's scale, position and rotation will still affect B)
    // By removing B's owner, you're now responsible for B's deletion (unless you want to keep it forever)
    orxObject_Delete(A); // <= This deletes only A, as a result B doesn't have a parent anymore, so effects of previous scale, position and rotation of A on B will disappear as well
    

    As a side note, if you're doing something like:
    orxGRAPHIC *G;
    orxOBJECT *O;
    
    G = orxGraphic_Create();
    O = orxObject_Create();
    orxObject_LinkStructure(O, G);
    
    orxObject_Delete(O); //<= G does still exist and its your responsibility to delete it
    

    You can do something equivalent using the config but that won't require any bookkeeping on your side:

    Config:
    [O]
    ; ...
    
    [G]
    ; ...
    

    You can then have, in code:
    orxOBJECT *O;
    
    // Links G to O in config
    orxConfig_PushSection("O");
    orxConfig_SetString("Graphic", "G");
    // Additionally you can tweak your template "O" as much as you want
    orxConfig_PopSection();
    
    // Creates O
    O = orxObject_CreateFromConfig("O"); // <= Here G is also created and linked to O, however you're not responsible of its deletion, O is
    
    orxObject_Delete(O); // <= Both O and G get deleted
    

    Cheers,

    iarwain
  • edited December 2014
    Thanks for reply
    Well the general rule is actually rather straightforward and is all about symmetry: the one in charge of deleting something is the one who created it.

    When an orxGRAPHIC is created from within an orxObject_CreateFromConfig() call, it means the orxObject code is also in charge of deleting that orxGRAPHIC when not needed.
    If you manually create an orxGRAPHIC, even if you link it to an orxOBJECT, you'll still be in charge of its deletion (note that the unlink will be done automatically, however the orxGRAPHIC will still exist).
    Are the object created with orxObject_CreateFromConfig() also automatically managed (I don't need to explicitly delete then if don't need to manage their lifetime)?
    From the top of my head, the only place where this rule can be bent is in when you transfer object ownership (orxObject_SetOwner()). An orxOBJECT which owns other orxOBJECTs will delete them upon its own deletion.
    Small example:
    orxOBJECT *A, *B;
    A = orxObject_Create();
    B = orxObject_Create();
    orxObject_SetOwner(B, A);
    orxObject_Delete(A); // This will also delete B as A owns B
    
    That make sense.
    Note that when using the config property key ChildList, created sub-objets will both be parth of the 3D hierarchy of the parent at well as being owned by it. Example:

    Config:
    [A]
    ChildList = B
    
    [B]
    

    Code:
    orxOBJECT *A, *B;
    A = orxObject_CreateFromConfig("A"); // <= This also creates B as a child of A and sets A as its owner
    B = orxObject_GetOwnedChild(A);
    orxObject_SetOwner(B, orxNULL); // <= Now B is not owned by A anymore, however it's still part of its 3D hierarchy (ie. A's scale, position and rotation will still affect B)
    // By removing B's owner, you're now responsible for B's deletion (unless you want to keep it forever)
    orxObject_Delete(A); // <= This deletes only A, as a result B doesn't have a parent anymore, so effects of previous scale, position and rotation of A on B will disappear as well
    
    Ok
    As a side note, if you're doing something like:
    orxGRAPHIC *G;
    orxOBJECT *O;
    
    G = orxGraphic_Create();
    O = orxObject_Create();
    orxObject_LinkStructure(O, G);
    
    orxObject_Delete(O); //<= G does still exist and its your responsibility to delete it
    
    So when doing something like:
    orxOBJECT *O;
    orxGRAPHIC *G;
    
    O = orxObject_CreateFromConfig(..)
    G = orxGraphic_Create();
    orxObject_LinkStructure(O, G);
    
    Then if "O" is managed, and is destroyed, I would need to destroy the "G" explicitly. On other hand, if I would use
    G = orxGraphic_CreateFromConfig(..);
    
    I wouldn't need to destroy "G", or would I?
    You can do something equivalent using the config but that won't require any bookkeeping on your side:

    Config:
    [O]
    ; ...
    
    [G]
    ; ...
    

    You can then have, in code:
    orxOBJECT *O;
    
    // Links G to O in config
    orxConfig_PushSection("O");
    orxConfig_SetString("Graphic", "G");
    // Additionally you can tweak your template "O" as much as you want
    orxConfig_PopSection();
    
    // Creates O
    O = orxObject_CreateFromConfig("O"); // <= Here G is also created and linked to O, however you're not responsible of its deletion, O is
    
    orxObject_Delete(O); // <= Both O and G get deleted
    

    But when I modify the "Graphic" value in the config and then somewhere else I would try to create "O" object, it will have the associated graphics set in PushSection()/PopSection(), am I right? Could I somehow cancel the changes made to config in the last PushSection()/PopSection() operation?

    Thanks
  • edited December 2014
    Trigve wrote:
    Are the object created with orxObject_CreateFromConfig() also automatically managed (I don't need to explicitly delete then if don't need to manage their lifetime)?

    If you issued the create call yourself (no matter if it's from config or plain), you're responsible of issuing the delete one as well. If you want to keep them forever, it's possible, but it's your decision.
    orx will collect every allocated resources when shutting down in the end.

    There are two exceptions to this (for objects only):
    - change of ownership (as illustrated earlier in this thread)
    - explicit LifeTime set on the object (either through config or by calling orxObject_SetLifeTime())
    The life time can be seen as a delayed delete.

    Lemme know if this doesn't answer your question as I'm not 100% sure what you mean by "need to manage their lifetime". :)
    So when doing something like:
    orxOBJECT *O;
    orxGRAPHIC *G;
    
    O = orxObject_CreateFromConfig(..)
    G = orxGraphic_Create();
    orxObject_LinkStructure(O, G);
    
    Then if "O" is managed, and is destroyed, I would need to destroy the "G" explicitly. On other hand, if I would use
    G = orxGraphic_CreateFromConfig(..);
    
    I wouldn't need to destroy "G", or would I?

    When "O" is deleted (you have to call it yourself as you're the one who created it, unless you change its owner or if there's a LifeTime involved), G will still exist as you're the one who created it.

    All is built on a symmetry model: the code which created something is responsible to delete it as well. Both Create() and CreateFromConfig() behave the same way with respect to ownership, so the above example will end up with the graphic still existing after "O" is deleted.
    But when I modify the "Graphic" value in the config and then somewhere else I would try to create "O" object, it will have the associated graphics set in PushSection()/PopSection(), am I right? Could I somehow cancel the changes made to config in the last PushSection()/PopSection() operation?

    You're totally correct. That's why you'd use O as a template here, not as a fully ready object.

    If you want to create a template from an existing section within altering the section, you have a couple of ways to do it:

    - Backup the value before changing it, then restore it:
    const orxSTRING Backup;
    
    orxConfig_PushSection("O");
    Backup = orxConfig_GetString("Graphic");
    orxConfig_SetString("Graphic", "G");
    
    orxObject_CreateFromConfig("O");
    
    orxConfig_SetString("Graphic", Backup);
    orxConfig_PopSection();
    

    - Create a new section inheriting from the model, this way you won't alter the model at all:
    orxConfig_PushSection("Template");
    orxConfig_SetParent("Template", "O"); // <= Now the section "Template" will inherit from all the values defined in "O"
    orxConfig_SetString("Graphic", "G"); // Overriding "Graphic" for "Template" only, without altering "O"
    orxConfig_PopSection();
    
    orxOBJECT *New, *Model;
    
    New = orxConfig_CreateFromConfig("Template");
    Model = orxConfig_CreateFromConfig("O");
    
  • edited December 2014
    As a side note, I removed the 2D flag in the object module as it was obsolete and should have disappeared a while ago.
  • edited December 2014
    Thank You for the reply,
    If you issued the create call yourself (no matter if it's from config or plain), you're responsible of issuing the delete one as well. If you want to keep them forever, it's possible, but it's your decision.
    orx will collect every allocated resources when shutting down in the end.

    There are two exceptions to this (for objects only):
    - change of ownership (as illustrated earlier in this thread)
    - explicit LifeTime set on the object (either through config or by calling orxObject_SetLifeTime())
    The life time can be seen as a delayed delete.

    Lemme know if this doesn't answer your question as I'm not 100% sure what you mean by "need to manage their lifetime". :)
    Ok. One question though. As was stated, calling orxObject_Delete() inside event handler could lead to, lets call it, undefined behavior. But in some circumstances I need to delete some object but I don't know if I'm in the event handler. But I'm deleting the object through specialized wrapper class. So could I therefor use orxObject_SetLifeTime(m_pImpl, orxFLOAT_0) instead of orxObject_Delete() in every circumstances? Or doest it have any caveats?
    orxOBJECT *O;
    orxGRAPHIC *G;
    
    O = orxObject_CreateFromConfig(..)
    G = orxGraphic_Create();
    orxObject_LinkStructure(O, G);
    
    Then if "O" is managed, and is destroyed, I would need to destroy the "G" explicitly. On other hand, if I would use
    G = orxGraphic_CreateFromConfig(..);
    
    I wouldn't need to destroy "G", or would I?

    When "O" is deleted (you have to call it yourself as you're the one who created it, unless you change its owner or if there's a LifeTime involved), G will still exist as you're the one who created it.
    Ok, understand.
    All is built on a symmetry model: the code which created something is responsible to delete it as well. Both Create() and CreateFromConfig() behave the same way with respect to ownership, so the above example will end up with the graphic still existing after "O" is deleted.
    Understood.
    You're totally correct. That's why you'd use O as a template here, not as a fully ready object.
    One more question :) Let the "O" section be our template section from which all other object should be created. So I add the graphic for 1. object. Create it. Then I need to add some other graphic for another object, so I change the "Graphic", and also need to add some other structure, so add some other stuff. Create it. Then again I need to create the third object from "O" but only with "Graphic". But as "O" was modified and now have some other structure linked to it, the new object would also have this new structure, which I don't want. Therefor I was asking if there is some mechanism to rollback the changes made.
    If you want to create a template from an existing section within altering the section, you have a couple of ways to do it:

    - Backup the value before changing it, then restore it:
    const orxSTRING Backup;
    
    orxConfig_PushSection("O");
    Backup = orxConfig_GetString("Graphic");
    orxConfig_SetString("Graphic", "G");
    
    orxObject_CreateFromConfig("O");
    
    orxConfig_SetString("Graphic", Backup);
    orxConfig_PopSection();
    

    - Create a new section inheriting from the model, this way you won't alter the model at all:
    orxConfig_PushSection("Template");
    orxConfig_SetParent("Template", "O"); // <= Now the section "Template" will inherit from all the values defined in "O"
    orxConfig_SetString("Graphic", "G"); // Overriding "Graphic" for "Template" only, without altering "O"
    orxConfig_PopSection();
    
    orxOBJECT *New, *Model;
    
    New = orxConfig_CreateFromConfig("Template");
    Model = orxConfig_CreateFromConfig("O");
    
    The second method could possibly solve the problem I have described above. But I would need to delete the "Template" section after the object creation to drop all changes to the "Template". Am I right?
  • edited December 2014
    And one question.
    Are these two, orxGraphic_Delete(orxGRAPHIC *_pstGraphic) and orxStructure_Delete (void *_pStructure), equivalent when using orxGRAPHIC as argument? Or is there some difference?
  • edited December 2014
    Trigve wrote:
    Thank You for the reply

    My pleasure!
    Ok. One question though. As was stated, calling orxObject_Delete() inside event handler could lead to, lets call it, undefined behavior. But in some circumstances I need to delete some object but I don't know if I'm in the event handler. But I'm deleting the object through specialized wrapper class. So could I therefor use orxObject_SetLifeTime(m_pImpl, orxFLOAT_0) instead of orxObject_Delete() in every circumstances? Or doest it have any caveats?

    Yes, you're right: you can always use orxObject_SetLifeTime(obj, orxFLOAT_0) in all cases.
    There isn't any real caveat unless you expect your object to be deleted right away: with a lifetime set to 0, the object will get deleted next time it's updated, which could either be in the current frame or the next one, depending where in the frame processing you are currently at.
    The other thing to keep in mind is that an object will only get deleted when its LifeTime is <= 0 if it's enabled. If the object is disabled, it'll only get deleted when it's re-enabled again.

    You can always call both SetLifeTime(orxFLOAT_0) and Enable(orxTRUE) to cover 100% cases.
    One more question :) Let the "O" section be our template section from which all other object should be created. So I add the graphic for 1. object. Create it. Then I need to add some other graphic for another object, so I change the "Graphic", and also need to add some other structure, so add some other stuff. Create it. Then again I need to create the third object from "O" but only with "Graphic". But as "O" was modified and now have some other structure linked to it, the new object would also have this new structure, which I don't want. Therefor I was asking if there is some mechanism to rollback the changes made.

    There isn't any direct mechanism to restore previous values (beside calling orxConfig_Reload() that would reload things from disk but still miss any subsequent runtime changes), however you can generalize the backup by storing all the values for all the keys in the section (there are functions that allow one to go through them). However, as you already know, I wouldn't recommend this approach as the inheritance-based one is much easier and yields better performance.
    The second method could possibly solve the problem I have described above. But I would need to delete the "Template" section after the object creation to drop all changes to the "Template". Am I right?

    You're entirely right: orxConfig_ClearSection("Template") is what you need. The section would be recreated by the next call to orxConfig_PushSection() or orxConfig_SetParent().
    And one question.
    Are these two, orxGraphic_Delete(orxGRAPHIC *_pstGraphic) and orxStructure_Delete (void *_pStructure), equivalent when using orxGRAPHIC as argument? Or is there some difference?

    There is a difference. Basically, if a structure is created by one API, it needs to be deleted by the same API. In your case, calling orxStructure_Delete on the graphic would only delete the base part of it but not the graphic-related part (for example if graphic created a texture, that texture would be dangling).

    In the future I could add more "virtual" functions to structures (right now I only track the update one), but for now you need to call the same API for creation and deletion. You can get the type of a structure (orxStructure_GetID()) if you need to implement a switch/case to create a "generic" deletion method.
    Note: orxStructure_GetID() is not to be confused with orxStrucure_GetGUID() which retrieves a GUID that can act as a "safe pointer".
  • edited December 2014
    Yes, you're right: you can always use orxObject_SetLifeTime(obj, orxFLOAT_0) in all cases.
    There isn't any real caveat unless you expect your object to be deleted right away: with a lifetime set to 0, the object will get deleted next time it's updated, which could either be in the current frame or the next one, depending where in the frame processing you are currently at.
    The other thing to keep in mind is that an object will only get deleted when its LifeTime is <= 0 if it's enabled. If the object is disabled, it'll only get deleted when it's re-enabled again.

    You can always call both SetLifeTime(orxFLOAT_0) and Enable(orxTRUE) to cover 100% cases.

    If this helps any, I have never found any real need for a delete function during any game situation. Perhaps others might, But so far, every situation setting a lifetime of 0 has been the safest and best way to remove an object entirely.
  • edited December 2014
    Thanks to both of you for the reply,
    and the last question :) Could I somehow find if I have some memory leaks? That is, is there some function that could set some flag and on the application exit orx will print all the structures/object that were still active?
  • edited December 2014
    Kinda, there is an event that will tell you when an object is destroyed, you can check manually on a small scale example if your algorithm is cleaning all the created objects.
    The event you should look for is the one with orxEVENT_TYPE_OBJECT type and orxOBJECT_EVENT_DELETE id. You can take a look here for some more info:
    https://forum.orx-project.org/discussion/6762#Comment_6764

    Also, you can compile it on linux and run your code on valgrind, it will show you all the memory errors your program has (including memory leaks).
  • edited December 2014
    orxOBJECT_EVENT_DELETE could help but then I would need to track all the object I create and then mark the particular one which was deleted. But it won't track the structures (graphic, ...).

    Also I don't think that valgrind will report any leaks, because AFAIK memory would be clean-up before the process exit (by the orx).
  • edited December 2014
    So I don't think that you want to track memory leaks. A memory leak is, by definition, a lost memory reference that is held by your program but can no longer be freed.

    I don't really know if you can watch for a particular struct being destroyed, maybe something on the profiller can help you with that.

    If I had to implement it, I would add a global counter of objects I created and one of objects destroyed (using the event handler I mentioned), then I would create a function to log those info and bind it to a clock with a 5 seconds timer and check the data.
  • edited December 2014
    Yes, but memory leak could happen in different circumstances. If you forgot to delete the orxOBJECT you've got memory leak inside orx, but not process wise (because orx is releasing all the memory upon exit). So technically it is still memory leak, but practically it may not (In my (and http://en.wikipedia.org/wiki/Memory_leak) definition, the memory leak happens when the memory acquired isn't release back when it isn't needed anymore).
    So I was referring to the memory leaks on orx boundary. And as it looks orx is managing all the stuff (structures, objects, ...) and should now which objects, structures etc are still referenced upon exit. So the information should be there.

    I Appreciate the info you provided, but I would rather used some solution integrated in orx :) I was just asking if there is something like, it isn't my number 1 priority for now.

    edit: I should rather use term resource leak rather than memory leak to avoid confusion.
  • edited December 2014
    There isn't any automated report however I could add one if need be: all the info is already available.

    In the meantime, if you want to check for "leaked" structures, in your exit function you can go through all the collections, they should all be empty. Something like:
    for(orxU32 i = 0; i < (orxU32)orxSTRUCTURE_ID_NUMBER; i++)
    {
      if(orxStructure_GetCounter((orxSTRUCTURE_ID)i) != 0)
      {
        // Leak detected!
        // Use orxStructure_GetStorageType() to know if they're organized as a tree or as a list
        // Then go through them using GetFirst/GetNext or GetChild/GetSibling
      }
    }
    
  • edited January 2015
    So I've tried the approach you've described in the last post. It is kind working but it get a lot of false positive. Mainly because if some object is destroyed by SetLifeTime() (as it is in the case when the object own some another children), the orx doesn't have a time to destroy it. Is there some workaround for this?
    Another ones are the bult-in structures.
  • edited January 2015
    Ah yes, I can see how it'd happen.
    For now, the only option would be to check for orxObject_GetLifeTime() == orxFLOAT_0 to rule out those false positives, and discard their owned children as well, or, more likely, to start with the current object and go back up looping with orxObject_GetOwner() till you either reach orxNULL (leak) or an object with a lifetime == orxFLOAT_0 (false positive).
    Not the cleanest approach but for now that should work.
  • edited January 2015
    I've also tried another approach.
    I'm cleaning all my objects in the update function (not the timer udate, but the one specified in orx_Execute()) when I'm going to quit the application. Then it looks like the next frame is still executed so it also clean up object awaiting for deletion. But it still founds some built-in objects. If they could be marked somehow as internal, I could then test for this flag and rule them out. Are there some flag for this purpose already?
    I do think your solution is more robust.
  • edited January 2015
    From the top of my head, I can't think of any internal objects that would be automatically created.

    There can be some extra structures (such as the root frame, which is internally created) or the one that have been required to remain in memory (attribute KeepInCache).

    Marking those could be an option, you can open an issue on bitbucket for this and assign it to me if you will. :)
  • edited January 2015
    I've express myself wrong :) What I mean, was that builtin objects are destroyed, but after my exit() routine, so I couldn't know there that if they're a core orx resources or they are leaks. See my log:
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 2 leaked with GUID 2
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 2 leaked with GUID 4294967330
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():217] Structure type 3 leaked with GUID 3
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 13 leaked with GUID 13
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 19 leaked with GUID 19
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 19 leaked with GUID 4294967347
    [09:37:51] [SYSTEM] [application.cpp:Application::exit():213] Structure type 19 leaked with GUID 8589934675
    
    For instance the "type 2 leaked with GUID 4294967330" is the clock created in FPS module, which is destroyed after my leak detection routine ends.
    All of this IIRC are destoryed *after* my exit() routine. I've created the ticket #69 for it.

    Thanks for your help
  • edited January 2015
    Ah yes, I see, I had completely forgotten those!

    Well, I guess the easiest would be for me to add a switch for orx to generate a resource leak log then, what do you think?

    The thing is that, when checking within orx, I can check in many different places, where all the internally created structures have already been removed.
  • edited January 2015
    iarwain wrote:
    Well, I guess the easiest would be for me to add a switch for orx to generate a resource leak log then, what do you think?

    Yes, that would be better. I have also stated it in the ticket I created.
  • edited January 2015
    I saw the update, thanks, if you have any preferred format or info you'd like to see printed, lemme know.
Sign In or Register to comment.