Crash on GetNext()!!!



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 04/05/2006 at 09:30, xxxxxxxx wrote:

    User Information:
    Cinema 4D Version:   9 
    Platform:   Windows  ;   
    Language(s) :     C++  ;

    ---------
    Hi all,

    I've got lots of crashes when using my plugin in C4D.

    The most frequent is when using the GetNext() method.
    Here is an example where this crash is triggered:

    bool IsObjectPresent(BaseObject *obj)
    {
    BaseObject *cur = GetActiveDocument()->GetFirstObject();
    while(cur){
         if (cur==obj) return true;
         cur = cur->GetNext();     <---- here a crash is triggered
    }
    return false;
    }

    I also get some crashes sometimes when calling the AddEvent() function with a parameter (without it works well).

    I wondered if this is caused by the fact that one of these functions is called outside the main thread, so:
    - I tried to use the GeIsMainThread() function but this one also crashes!!!
    - I tried to use SpecialEventMessage() to get the main thread execute some code, but it also crashes in the main thread......

    I don't understand why calling such a simple function like GetNext() on the list of the objects can trigger a crash...

    Thanks for your help guys!

    Ben



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 04/05/2006 at 10:00, xxxxxxxx wrote:

    try while(cur!=NULL) and/or check for if(!cur) break; after your GetNext() call.



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 04/05/2006 at 10:10, xxxxxxxx wrote:

    Hi,

    Thanks for the prompt reply.

    The line 'while(cur)' is actually identical to 'while(cur!=NULL)', and the crash is triggered when cur is not NULL., so it won't fix the problem.

    Actually I never get to the 'after GetNext() call' point, so adding the 'if(!cur) break;' would not fix the problem unfortunately...

    Thanks for your help!

    Ben



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 04/05/2006 at 14:53, xxxxxxxx wrote:

    Hi,

    first of all, while(cur) is not the same as while(cur!=NULL), at least not in the field of C++. Read some advanced books on C++ to see what checking/passing etc. against NULL may give you (or not). But that´s not the discussion here. :)

    And the break check, is to prevent the while loop to start again, when the pointer check does not work (no matter why).

    If those don´t work, then I doubt it´s up to GetNext(). It must be something else (as I have plenty of code using it in the exact same matter as you did, recursively)
    Maybe arising from your code? Sometimes, the crash is not up to the function calling it. Maybe you have overridden a pointer where you shouldn´t and this sums up to a crash when GetNext() may try to get that pointer address in any way. But that´s pure speculation as I don´t know your code.

    Best
    KAtachi



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 04/05/2006 at 19:07, xxxxxxxx wrote:

    I agree with BigBen on the one point here. The 'if(!cur) break;' is superfluous - and I find that superfluous fixes are a sign of something terribly wrong either in design or coding elsewhere (yes, you note that as well). I never use fixes that apparently mask a problem - better to find the root cause and mend it. Mask fixes tend to always come back to haunt you later. :)

    I'd be interested in more on the difference between (!p) and (p == NULL) - not that I don't think there might be, just that I've not encountered it. NULL = 0, so (p == NULL) is equivalent to (p == 0) which represents a sort of unset memory address. (!p) is a boolean test which checks for all bits cleared and is equivalent to testing for 0 (or false/FALSE). NULL == false == FALSE == 0 (at least that's the standard).



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 00:41, xxxxxxxx wrote:

    0 does not have to be undefined! That depends on the function your checking it against or you passing it to. So NULL is not necessarily ==0. (I remember that this is dependant on the implementation though)

    Most of the time you won´t encounter such a situation where this is necessary (you are the best example and so am I :), but there ARE critical situations where it´s necessary to check explicitly for a NULL pointer and not rely on NULL==0.

    I remember this from "Effectively program in C++" (not sure if this is the english title, in german it´s "Effektiv C++ programmieren") by Scott Meyers. A wonderful book on advanced C++ programming. I am not sure if I misquoted him, but that´s what´s still in my mind (but I don´t have the book here any more, otherwise I could have quoted it directly out of the book :)

    So I am now always making sure that I check against NULL rather than the pointer only, to not running into such a critical problem. So to get precise information on the NULL pointer problem, refer to the book please (do I sound like an amazon vendor? :-D )

    But Scott Meyers is always on the hunt for errors in his book, so if you find out elsewise let him know (and us too). I can only judge from what he wrote and it sounded pretty plausible. :)



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:08, xxxxxxxx wrote:

    Hi,

    Thanks for all these replies!
    Sorry for my lack of knowledge on the '!=NULL' thing, I didn't know that. That sounds plausible as there are always these kind of weird things in C++ :-)

    Regarding my error, I think that you're right, 3DDesigner, I must do something wrong before calling this function. I'll try to create a simple plugin using this function and see if it works.

    I was really surprised to get all of these weird crashes whereas there is no reference to such problem on the forum...

    Ben



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:14, xxxxxxxx wrote:

    No need to apologize Ben, if I hadn´t read that book I wouldn´t have known about it either and would have thought it´s like Kuro said (it probably even is 99% of times). but you are right, sometimes C++ is simply weird :)

    Let us know when you find the problem!
    Best
    Katachi



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:18, xxxxxxxx wrote:

    I agree that scenarios exist (especially after a little research) where NULL may be '\0' or (void* )0 (bad ideas if you ask me). ;) Who knows (that's rhetorical) what other implementations are in use for embedded or more esoteric systems.

    I'd have to consult the book you reference, but actually,
    my feeling is that none of these is correct (I know, I'm better than all of them - lol). Since pointer arithmetic has standardized an 'unset pointer' to a value of 0 so that it is basically an address for no other purpose (one usually reserved by the basic system), the (!p) usage would seem more appropriate in that it is independent of bit-size, whereas comparing to 0 (or the equivalent NULL definition) would need to be converted to the appropriate size to cover the bits. For instance, if NULL is defined: #define NULL 0, that means that it is interpreted as an int (by default), but all memory addressing on 32+ bit systems is at least long int which should be: #define NULL 0L. (!p) covers all bits irrespective (they all have to be 0 for the result to return TRUE), if the NULL == 0 holds, of course.

    On the other hand, NULL won't work in situations where the pointer is used as a 'stop'. I do this quite often with arrays, as a synonym for the last index:

    MyClass* firstItem;
    MyClass* lastItem;

    for (MyClass* item = firstItem; item != lastItem; item++);

    lastItem doesn't point to an existent last item in the array or list, but one beyond it for loop cessation. In this situation, comparing lastItem to NULL (because it is in reality invalid not unset) would be catastrophic. It doesn't represent an unset pointer, but an invalid pointer in a linear block of memory.

    But, if it is a linked list, the NULL check holds (though I'm using the boolean equivalent here, I think) :

    for (MyClass* item = firstItem; item; item = item->GetNext());

    Note the subtle difference.

    Since my main languages have been C and Java (I skipped class on C++ for quite a while), I'd have to see what Meyers recommends. Always willing to learn. By the way, is it not true that a new C++ standard is in the works - yikes! More to learn.



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:28, xxxxxxxx wrote:

    hmm, maybe I got it in the wrong direction? Your statements seem feasible. I got to get that book again, not that my mind plays tricks with me and I am pointing to the exact opposite direction here and Ben curses me for this and I die a painful death. :-D

    My brother must have this lying around anywhere, so I´ll be checking this once I visit him again and let you know about it.

    About new C++ standard in the works - there is? I haven´t heard of it, but yikes! hits the spot very well. :D

    My brother is also Java and C++ programmer btw. (for Volkswagen). I seem to always sourround myself with guys like you...tss ;-D



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:30, xxxxxxxx wrote:

    Yep, C++ is weird - which is why I skipped class. Understanding how a computer works and how a language implements this knowledge are two different things, I suppose. This may be why Assembly is appealing to some - the specifications and results are about as direct as you can achieve without doing the electronics yourself. :)

    Would this be the book:

    "Effective C++ : 55 Specific Ways to Improve Your Programs and Designs (3rd Edition) (Paperback)"



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:31, xxxxxxxx wrote:

    yep, this should be the book! Although for me it was 50 ways to improve your programs and designs (I had the 2nd Edition then I guess). :)



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 01:38, xxxxxxxx wrote:

    Just wanted to add, (void* )0 seems to be the C macro you´re talking about right?

    I don´t know why C++ does not use NULL like in Smalltalk where it´s a specially defined NULL-object that you can refer to instead of a numeral representation. Then we wouldn´t have to discuss this. :)

    And I think Java does not need to worry about all this at all? But I don´t know nothing about Java actually, only that you don´t have to worry about memory and pointers.



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 02:05, xxxxxxxx wrote:

    Yes, the (void* )0 was a C implementation of NULL - interesting, but it means a conversion from a defined pointer type to void - ugly ain't it. :)

    Well, this was the 'decided upon' definition of 'NULL' for pointers way back, I guess. Whoever made the decision decided that the memory address of an unset pointer should be equal to zero - this may have its roots in assembly (it has been quite some time). The problem isn't the standard notion of null pointer equals zero as much as how it gets interpreted into each language based upon its syntax and purpose.

    Java does indeed have a null reference. You do have to worry about class allocation (new) and validity (delete) just as in C++. Even though references to instances are handled automatically by garbage collection (when there are none, the memory is released), the references to them are still subject to validation. Most of the time, this is not a concern since you may have members still referencing and the instance will persist, but if you are getting the instance reference from, say, a method, you might want to check.



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 02:11, xxxxxxxx wrote:

    Quote: Originally posted by kuroyume0161 on 05 May 2006
    >
    > * * *
    >
    > Yes, the (void* )0 was a C implementation of NULL - interesting, but it means a conversion from a defined pointer type to void - ugly ain't it. :)
    >
    > * * *

    hihi, yep :)

    > Quote: Java does indeed have a null reference. You do have to worry about class allocation (new) and validity (delete) just as in C++. Even though references to instances are handled automatically by garbage collection (when there are none, the memory is released), the references to them are still subject to validation. Most of the time, this is not a concern since you may have members still referencing and the instance will persist, but if you are getting the instance reference from, say, a method, you might want to check.
    >
    > * * *
    >
    > * * *

    Ah I see. Well, that sounds way easier though. I´ve been interested in Java since I´ve heard that ZBrush is coded in Java, which sounds like Java can be effectively used to create such applications (and I am thinking about writing sth like ZBrush just for learning purposes...darn, where is Father time?).

    Samir



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 02:18, xxxxxxxx wrote:

    All of this is interesting, if not off topic. :)

    It is interesting to note why 0 was used. At some point, someone was realizing that memory references (pointers) must become invalid for one reason or another (during initialization or when the memory is released). And a value had to be established (since memory addresses are just numbers). -1 might have been a candidate, but think of the consequences. -1 in 16-bit is 0xFFFF, which is a possibly valid 32-bit address, 0x0000FFFF. And so on for memory address sizes. Any other value could lead to similar results. But 0, to some extent, is 0 at all levels (though floating point has the odd distinction of 0 and -0 (because of the sign bit)).

    This link is interesting (C reference) : Null Pointers

    And this supports your understanding: C++ Null Pointers

    I agree that unitialized pointers are not 'unset' pointers. When you initialize pointers, it should be to NULL (and I never use 0 in this case, oddly enough).

    The things we learn...



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 02:27, xxxxxxxx wrote:

    Thanks for the links. Will check these out.

    Off topic? Naaahh. :-D



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 06:36, xxxxxxxx wrote:

    Hi all,

    Well, I found my problem!!!

    I somewhat missed the following statement in the SDK doc:
    The compiler options for Pointer-to-member representation must be set to "General-Purpose Always" and "Point to Single-Inheritance Classes" in C++ tab/C++ language (/vmg /vms). If not set the plugin will crash instantly!

    Well, the plugin was able to do a lot of things (volumetric shaders, creating objects, some motion handler, etc.) but it crashed on several things...so it was not crashing instantly unfortunately (it would have been easier to find the error in this case...)

    Now everything is working perfectly!

    Best regards,
    Ben



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 06:52, xxxxxxxx wrote:

    great that it wasn´t anything anybody suggested. :D
    Thanks for letting us know and glad you found the prob.

    Best
    Samir



  • THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED

    On 05/05/2006 at 10:34, xxxxxxxx wrote:

    Very good, Ben!

    Note that it is a good idea to use one of the included projects (either the api_lib or cinema4dsdk) as a basis for your plugin's. Then these settings will be already proper.


Log in to reply