Browse Source

Merge pull request #113209 from shiena/fix/prevent_freeze_android_camera

Prevent deadlock on Android camera
Rémi Verschelde 2 weeks ago
parent
commit
3a97723ff2
1 changed files with 21 additions and 18 deletions
  1. 21 18
      modules/camera/camera_android.cpp

+ 21 - 18
modules/camera/camera_android.cpp

@@ -489,33 +489,36 @@ void CameraFeedAndroid::onSessionClosed(void *context, ACameraCaptureSession *se
 }
 
 void CameraFeedAndroid::deactivate_feed() {
+	// First, remove image listener to prevent new callbacks.
+	if (reader != nullptr) {
+		AImageReader_setImageListener(reader, nullptr);
+	}
+
+	// Stop and close capture session.
+	// These calls may wait for pending callbacks to complete.
 	if (session != nullptr) {
 		ACameraCaptureSession_stopRepeating(session);
 		ACameraCaptureSession_close(session);
 		session = nullptr;
 	}
 
-	if (reader != nullptr) {
-		AImageReader_setImageListener(reader, nullptr);
-	}
-
-	{
-		MutexLock lock(callback_mutex);
+	// Now safe to acquire lock and clean up resources.
+	// No new callbacks will be triggered after this point.
+	MutexLock lock(callback_mutex);
 
-		if (device != nullptr) {
-			ACameraDevice_close(device);
-			device = nullptr;
-		}
+	if (device != nullptr) {
+		ACameraDevice_close(device);
+		device = nullptr;
+	}
 
-		if (reader != nullptr) {
-			AImageReader_delete(reader);
-			reader = nullptr;
-		}
+	if (reader != nullptr) {
+		AImageReader_delete(reader);
+		reader = nullptr;
+	}
 
-		if (request != nullptr) {
-			ACaptureRequest_free(request);
-			request = nullptr;
-		}
+	if (request != nullptr) {
+		ACaptureRequest_free(request);
+		request = nullptr;
 	}
 }