[libcamera-devel] [PATCH 4/6] libcamera: Support blocking method invocation

Jacopo Mondi jacopo at jmondi.org
Sun Oct 27 21:33:33 CET 2019


Add support for blocking method invocation by providing a conditional
variable to the InvokeMessage class operation and have the
Object::invokeMethod() caller operation to wait on the conditional
variable if the message invocationType is InvocationTypeBlocking.

Signed-off-by: Jacopo Mondi <jacopo at jmondi.org>
---
 src/libcamera/include/message.h |  5 +++++
 src/libcamera/message.cpp       | 11 +++++++++--
 src/libcamera/object.cpp        | 14 +++++++++++++-
 3 files changed, 27 insertions(+), 3 deletions(-)

diff --git a/src/libcamera/include/message.h b/src/libcamera/include/message.h
index 1cfde5669ede..cfb674adbccb 100644
--- a/src/libcamera/include/message.h
+++ b/src/libcamera/include/message.h
@@ -10,6 +10,7 @@
 #include <atomic>
 
 #include <libcamera/bound_method.h>
+#include <libcamera/object.h>
 
 namespace libcamera {
 
@@ -48,14 +49,18 @@ class InvokeMessage : public Message
 {
 public:
 	InvokeMessage(BoundMethodBase *method, void *pack,
+		      ObjectConditionVariable *cond = nullptr,
 		      bool deleteMethod = false);
 	~InvokeMessage();
 
+	ObjectConditionVariable *cond() const { return cond_; }
+
 	void invoke();
 
 private:
 	BoundMethodBase *method_;
 	void *pack_;
+	ObjectConditionVariable *cond_;
 	bool deleteMethod_;
 };
 
diff --git a/src/libcamera/message.cpp b/src/libcamera/message.cpp
index efafb655c17e..865404e81cfb 100644
--- a/src/libcamera/message.cpp
+++ b/src/libcamera/message.cpp
@@ -119,13 +119,14 @@ Message::Type Message::registerMessageType()
  * \brief Construct an InvokeMessage for method invocation on an Object
  * \param[in] method The bound method
  * \param[in] pack The packed method arguments
+ * \param[in] cond The condition variable used to signal reception of the message
  * \param[in] deleteMethod True to delete the \a method when the message is
  * destroyed
  */
 InvokeMessage::InvokeMessage(BoundMethodBase *method, void *pack,
-			     bool deleteMethod)
+			     ObjectConditionVariable *cond, bool deleteMethod)
 	: Message(Message::InvokeMessage), method_(method), pack_(pack),
-	  deleteMethod_(deleteMethod)
+	  cond_(cond), deleteMethod_(deleteMethod)
 {
 }
 
@@ -135,6 +136,12 @@ InvokeMessage::~InvokeMessage()
 		delete method_;
 }
 
+/**
+ * \fn InvokeMessage::cond()
+ * \brief Retrieve the synchronization condition variable
+ * \return The ObjectConditionVariable
+ */
+
 /**
  * \brief Invoke the method bound to InvokeMessage::method_ with arguments
  * InvokeMessage::pack_
diff --git a/src/libcamera/object.cpp b/src/libcamera/object.cpp
index 88054aba3454..ee6f5efc984c 100644
--- a/src/libcamera/object.cpp
+++ b/src/libcamera/object.cpp
@@ -196,7 +196,12 @@ void Object::message(Message *msg)
 	switch (msg->type()) {
 	case Message::InvokeMessage: {
 		InvokeMessage *iMsg = static_cast<InvokeMessage *>(msg);
+		ObjectConditionVariable *cond = iMsg->cond();
 		iMsg->invoke();
+
+		if (cond)
+			cond->notifyReception();
+
 		break;
 	}
 
@@ -223,9 +228,16 @@ void Object::message(Message *msg)
 
 void Object::invokeMethod(BoundMethodBase *method, InvocationType type, void *args)
 {
+	ObjectConditionVariable cond;
+	ObjectConditionVariable *c = type == InvocationTypeBlocking ?
+				     &cond : nullptr;
+
 	std::unique_ptr<Message> msg =
-		utils::make_unique<InvokeMessage>(method, args, true);
+		utils::make_unique<InvokeMessage>(method, args, c, true);
 	postMessage(std::move(msg));
+
+	if (c)
+		c->waitDelivery();
 }
 
 /**
-- 
2.23.0



More information about the libcamera-devel mailing list