Skip to content

Commit feb21a7

Browse files
Googlera-maurice
authored andcommitted
Delete C++ Firestore objects when C# has no more references to them.
This was achieved by using the CppInstanceManager, which provides this functionality elsewhere in the Unity SDK. When running UIHandlerAutomated, this eliminates all 11 leaks from Firestore::GetFirestore(). PiperOrigin-RevId: 320609048
1 parent eb66965 commit feb21a7

File tree

2 files changed

+73
-0
lines changed

2 files changed

+73
-0
lines changed
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
#include "firebase/csharp/firestore_instance_management.h"
2+
3+
#include "firebase/app/client/unity/src/cpp_instance_manager.h"
4+
#include "firebase/firestore.h"
5+
6+
namespace firebase {
7+
namespace firestore {
8+
namespace csharp {
9+
10+
namespace {
11+
12+
CppInstanceManager<Firestore>& GetFirestoreInstanceManager() {
13+
// Allocate the CppInstanceManager on the heap to prevent its destructor
14+
// from executing (go/totw/110#the-fix-safe-initialization-no-destruction).
15+
static CppInstanceManager<Firestore>* firestore_instance_manager =
16+
new CppInstanceManager<Firestore>();
17+
return *firestore_instance_manager;
18+
}
19+
20+
} // namespace
21+
22+
Firestore* GetFirestoreInstance(App* app) {
23+
auto& firestore_instance_manager = GetFirestoreInstanceManager();
24+
// Acquire the lock used internally by CppInstanceManager::ReleaseReference()
25+
// to avoid racing with deletion of Firestore instances.
26+
MutexLock lock(firestore_instance_manager.mutex());
27+
Firestore* instance =
28+
Firestore::GetInstance(app, /*init_result_out=*/nullptr);
29+
firestore_instance_manager.AddReference(instance);
30+
return instance;
31+
}
32+
33+
void ReleaseFirestoreInstance(Firestore* firestore) {
34+
GetFirestoreInstanceManager().ReleaseReference(firestore);
35+
}
36+
37+
} // namespace csharp
38+
} // namespace firestore
39+
} // namespace firebase
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
#ifndef FIREBASE_FIRESTORE_CLIENT_CPP_SRC_INCLUDE_FIREBASE_CSHARP_FIRESTORE_INSTANCE_MANAGEMENT_H_
2+
#define FIREBASE_FIRESTORE_CLIENT_CPP_SRC_INCLUDE_FIREBASE_CSHARP_FIRESTORE_INSTANCE_MANAGEMENT_H_
3+
4+
namespace firebase {
5+
6+
class App;
7+
8+
namespace firestore {
9+
10+
class Firestore;
11+
12+
namespace csharp {
13+
14+
/**
15+
* Returns the Firestore instance for the given App, creating it if necessary.
16+
* This method is merely a wrapper around Firestore::GetInstance() that
17+
* increments a reference count each time a given Firestore pointer is returned.
18+
* The caller must call ReleaseFirestoreInstance() with the returned pointer
19+
* once it is no longer referenced to ensure proper garbage collection.
20+
*/
21+
Firestore* GetFirestoreInstance(App* app);
22+
23+
/**
24+
* Decrements the reference count of the given Firestore, deleting it if the
25+
* reference count becomes zero. The given Firestore pointer must have been
26+
* returned by a previous invocation of GetFirestoreInstance().
27+
*/
28+
void ReleaseFirestoreInstance(Firestore* firestore);
29+
30+
} // namespace csharp
31+
} // namespace firestore
32+
} // namespace firebase
33+
34+
#endif // FIREBASE_FIRESTORE_CLIENT_CPP_SRC_INCLUDE_FIREBASE_CSHARP_FIRESTORE_INSTANCE_MANAGEMENT_H_

0 commit comments

Comments
 (0)