Jump to content
  • Advertisement
Sign in to follow this  
mrjones

Avoid referencing stack objects?

This topic is 4079 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I have registered both referencing and releasing for String class. The memory manager that handles references is keeps the references separately such that the actual objects are not aware of the reference and release mechanism. There are no memory leaks for constructed and factory made strings, but addition of strings causes memory leak. My + operator returns a string from stack, but AngelScript attempts to release its reference, but since it is from stack, it should be ignored completely. Is it somehow possible to avoid AngelScript trying to manage external pointers or should I handle it in my own memory manager by wrapping operators in separate functions and completely ignoring the pointers they return by setting the reference value to at least 2? I wouldn't want to use the same method as in the example, where reference counter is included inside the object, because I have quite many classes and it is difficult to manage them this way. The code is below, perhaps it makes more sense than my fuzzy explanation:
AngelMemoryManager<DATA::String*> AngelString::memoryManager; // Strings memory manager

String* AngelString::reference(DATA::String* str) {
  return memoryManager.reference(str); // registers the pointer and increments the value (if pointer is new, the reference is 1)
}

void AngelString::release(DATA::String* str) {
  memoryManager.release(str); // releases the pointer and decrements the value (if value is 0, the pointer is deleted)
}

// This is the string factory that creates new strings for the script
String* AngelString::factory(asUINT length, const char *s) {
  return reference(NEW(String(s, length)));
}

// This is a wrapper for the default AngelString constructor, since
// it is not possible to take the address of the constructor directly
void AngelString::construct(String* thisPointer) {
  reference(PLACEMENT_NEW(thisPointer, String()));
}

String operator + (const String& string1, const String& string2); // the declaration of addition operator 

// Current operator registration
	r = engine->RegisterObjectBehaviour("String", asBEHAVE_ADDREF,
                                      "void f()", asFUNCTION(AngelString::reference),
                                      asCALL_CDECL_OBJLAST); assert( r >= 0 );
	r = engine->RegisterObjectBehaviour("String", asBEHAVE_RELEASE,
                                      "void f()", asFUNCTION(AngelString::release),
                                      asCALL_CDECL_OBJLAST); assert( r >= 0 );

	r = engine->RegisterGlobalBehaviour(asBEHAVE_ADD, "String f(const String &in, const String &in)",
                                      asFUNCTIONPR(operator +,
                                                  (const String &, const String &),
                                                  String),
                                      asCALL_CDECL); assert( r >= 0 );
Thanks a lot to anybody who has a good idea for solving this problem.

Share this post


Link to post
Share on other sites
Advertisement
If you're mixing memory management like this you're going to have problems, reference counting and stack allocated objects don't work well together. In C++ you're ok because you manually decide when an object is reference counted or stack allocated, but in AngelScript you don't have that option.

You're telling AngelScript that the string type is memory managed through reference counting, but you're still returning the string value on the stack. The string on the stack should be destroyed directly by calling the destructor, but AngelScript has no way of knowing that. Also, what if the script decides to store a reference to the string somewhere, in that case the memory on the stack must not be destroyed.

Actually, AngelScript should probably give an error when you try to register your operator that returns the string by value, since it will never work.

Share this post


Link to post
Share on other sites
Thanks a lot. That's exactly what I wanted to know. I'll just always return new objects to AngelScript in that case or let the my memory manager ignore the externally managed pointers specifically.

[Edited by - mrjones on July 27, 2007 3:52:12 AM]

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!