[libcamera-devel] [PATCH 04/10] test: Add test for the Fence class

Jacopo Mondi jacopo at jmondi.org
Thu Oct 28 13:15:14 CEST 2021


Add a test for the Fence class by testing completion and expiration of
a Fence and testing that move semantic is implemented correctly.

Signed-off-by: Jacopo Mondi <jacopo at jmondi.org>
---
 test/fence.cpp   | 148 +++++++++++++++++++++++++++++++++++++++++++++++
 test/meson.build |   1 +
 2 files changed, 149 insertions(+)
 create mode 100644 test/fence.cpp

diff --git a/test/fence.cpp b/test/fence.cpp
new file mode 100644
index 000000000000..9fb92b1c250b
--- /dev/null
+++ b/test/fence.cpp
@@ -0,0 +1,148 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+/*
+ * Copyright (C) 2019, Google Inc.
+ *
+ * fence.cpp - Fence test
+ */
+
+#include <iostream>
+#include <sys/eventfd.h>
+#include <unistd.h>
+
+#include <libcamera/base/event_dispatcher_poll.h>
+#include <libcamera/base/thread.h>
+#include <libcamera/base/timer.h>
+#include <libcamera/internal/fence.h>
+
+#include "test.h"
+
+using namespace libcamera;
+using namespace std;
+
+class FenceTest : public Test
+{
+protected:
+	int init();
+	int run();
+	void cleanup();
+
+private:
+	void timeout();
+	void completed();
+
+	int eventfd_;
+	Timer timer_;
+	EventDispatcher *dispatcher;
+	Fence *fence_;
+};
+
+int FenceTest::init()
+{
+	timer_.timeout.connect(this, &FenceTest::timeout);
+	dispatcher = Thread::current()->eventDispatcher();
+
+	eventfd_ = eventfd(0, EFD_CLOEXEC | EFD_NONBLOCK);
+	if (eventfd_ < 0) {
+		cerr << "Unable to create eventfd" << endl;
+		return TestFail;
+	}
+
+	fence_ = new Fence(eventfd_);
+	if (!eventfd_) {
+		cerr << "Fence creation should not reset the file descriptor" << endl;
+		return TestFail;
+	}
+
+	if (fence_->fd() != eventfd_) {
+		cerr << "Fence file descriptor should not be duplicated" << endl;
+		return TestFail;
+	}
+
+	fence_->complete.connect(this, &FenceTest::completed);
+
+	return 0;
+}
+
+void FenceTest::timeout()
+{
+	uint64_t value = 1;
+	ssize_t ret = write(eventfd_, &value, sizeof(value));
+	if (ret != sizeof(value))
+		cerr << "Failed to write to event fd" << endl;
+
+	/* Let the fence complete on the eventfd read event. */
+	dispatcher->processEvents();
+}
+
+void FenceTest::completed()
+{
+	if (fence_->expired())
+		return;
+
+	uint64_t value;
+	ssize_t ret = read(eventfd_, &value, sizeof(value));
+	if (ret != sizeof(value))
+		cerr << "Failed to read from event fd" << endl;
+}
+
+int FenceTest::run()
+{
+	/* Activate the fence and schedule a wake-up before it expires. */
+	fence_->enable();
+	timer_.start(50);
+
+	dispatcher->processEvents();
+
+	if (fence_->expired()) {
+		cerr << "Fence should not have expired" << endl;
+		return TestFail;
+	}
+
+	if (!fence_->completed()) {
+		cerr << "Fence should have completed" << endl;
+		return TestFail;
+	}
+
+	/* Now let the fence expire. */
+	fence_->enable();
+	dispatcher->processEvents();
+
+	if (fence_->completed()) {
+		cerr << "Fence should not have completed" << endl;
+		return TestFail;
+	}
+
+	if (!fence_->expired()) {
+		cerr << "Fence should have expired" << endl;
+		return TestFail;
+	}
+
+	/*
+	 * Test fence move semantic.
+	 *
+	 * Create two temporary fences and verify we can move them.
+	 */
+	Fence fence1(eventfd_, 500);
+	Fence fence2(0, 500);
+	fence2 = std::move(fence1);
+
+	if (fence1.fd() != -1) {
+		cerr << "A moved fence should have an invalid fd" << endl;
+		return TestFail;
+	}
+
+	if (fence2.fd() != eventfd_ || fence2.timeout() != 500) {
+		cerr << "Faile to move fence" << endl;
+		return TestFail;
+	}
+
+	return 0;
+}
+
+void FenceTest::cleanup()
+{
+	close(eventfd_);
+	delete fence_;
+}
+
+TEST_REGISTER(FenceTest)
diff --git a/test/meson.build b/test/meson.build
index d0466f17d7b6..377e392628bf 100644
--- a/test/meson.build
+++ b/test/meson.build
@@ -40,6 +40,7 @@ internal_tests = [
     ['event-dispatcher',                'event-dispatcher.cpp'],
     ['event-thread',                    'event-thread.cpp'],
     ['file',                            'file.cpp'],
+    ['fence',                           'fence.cpp'],
     ['file-descriptor',                 'file-descriptor.cpp'],
     ['flags',                           'flags.cpp'],
     ['hotplug-cameras',                 'hotplug-cameras.cpp'],
-- 
2.33.1



More information about the libcamera-devel mailing list