Browse Source

Merge pull request #1480 from AtomicGameEngine/JME-ATOMIC-FILERELEASE

[C#] Fixing unwanted reference being added on SharedPtr returns, adding RefCounted::ReleaseRefSilent
JoshEngebretson 8 years ago
parent
commit
4175fe1852

+ 5 - 0
Source/Atomic/Container/RefCounted.cpp

@@ -131,6 +131,11 @@ void RefCounted::AddRefSilent()
     (refCount_->refs_)++;
     (refCount_->refs_)++;
 }
 }
 
 
+void RefCounted::ReleaseRefSilent()
+{
+    assert(refCount_->refs_ > 0);
+    (refCount_->refs_)--;
+}
 
 
 void RefCounted::AddRefCountChangedFunction(RefCountChangedFunction function)
 void RefCounted::AddRefCountChangedFunction(RefCountChangedFunction function)
 {
 {

+ 4 - 1
Source/Atomic/Container/RefCounted.h

@@ -119,9 +119,12 @@ public:
 
 
     virtual const String& GetTypeName() const = 0;
     virtual const String& GetTypeName() const = 0;
 
 
-    /// Increment reference count. Do not call any lifetime book keeping
+    /// Increment reference count. Do not call any lifetime bookkeeping
     void AddRefSilent();
     void AddRefSilent();
 
 
+    /// Decrement reference count, do not call any lifetime bookkeeping, don't delete at refcount == 0
+    void ReleaseRefSilent();
+
     virtual ClassID GetClassID() const  = 0;
     virtual ClassID GetClassID() const  = 0;
     static ClassID GetClassIDStatic() { static const int typeID = 0; return (ClassID) &typeID; }
     static ClassID GetClassIDStatic() { static const int typeID = 0; return (ClassID) &typeID; }
 
 

+ 17 - 3
Source/ToolCore/JSBind/CSharp/CSFunctionWriter.cpp

@@ -213,7 +213,6 @@ void CSFunctionWriter::WriteNativeFunction(String& source)
         }
         }
     }
     }
 
 
-
     bool returnValue = false;
     bool returnValue = false;
     bool sharedPtrReturn = false;
     bool sharedPtrReturn = false;
 
 
@@ -231,7 +230,7 @@ void CSFunctionWriter::WriteNativeFunction(String& source)
     }
     }
     else if (function_->GetReturnClass() && function_->GetReturnType()->isSharedPtr_)
     else if (function_->GetReturnClass() && function_->GetReturnType()->isSharedPtr_)
     {
     {
-        returnStatement = ToString("SharedPtr<%s> returnValue = ", function_->GetReturnClass()->GetNativeName().CString());
+        returnStatement = ToString("SharedPtr<%s> returnValuePtr = ", function_->GetReturnClass()->GetNativeName().CString());
         sharedPtrReturn = true;
         sharedPtrReturn = true;
     }
     }
     else if (function_->GetReturnType() && function_->GetReturnType()->type_->asVectorType())
     else if (function_->GetReturnType() && function_->GetReturnType()->type_->asVectorType())
@@ -351,7 +350,22 @@ void CSFunctionWriter::WriteNativeFunction(String& source)
 
 
     if (sharedPtrReturn)
     if (sharedPtrReturn)
     {
     {
-        source += IndentLine("if (returnValue.NotNull()) returnValue->AddRef();\n");
+        // We need to keep the shared ptr return value alive through the call, without adding an unwanted reference
+
+        source += IndentLine(ToString("%s* returnValue = returnValuePtr;\n", function_->GetReturnClass()->GetNativeName().CString()));
+        source += IndentLine("if (returnValue)\n");
+        source += IndentLine("{\n");
+
+        Indent();
+
+        source += IndentLine("returnValue->AddRefSilent();\n");
+        source += IndentLine("returnValuePtr = 0;\n");
+        source += IndentLine("returnValue->ReleaseRefSilent();\n");
+
+        Dedent();
+
+        source += IndentLine("}\n");
+
         source += IndentLine("return returnValue;\n");
         source += IndentLine("return returnValue;\n");
     }
     }
     else if (returnType == "const char*")
     else if (returnType == "const char*")