From patchwork Wed Dec 1 14:29:28 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jacopo Mondi X-Patchwork-Id: 14963 X-Patchwork-Delegate: jacopo@jmondi.org Return-Path: X-Original-To: parsemail@patchwork.libcamera.org Delivered-To: parsemail@patchwork.libcamera.org Received: from lancelot.ideasonboard.com (lancelot.ideasonboard.com [92.243.16.209]) by patchwork.libcamera.org (Postfix) with ESMTPS id 8112FC3250 for ; Wed, 1 Dec 2021 14:28:54 +0000 (UTC) Received: from lancelot.ideasonboard.com (localhost [IPv6:::1]) by lancelot.ideasonboard.com (Postfix) with ESMTP id 075B460746; Wed, 1 Dec 2021 15:28:54 +0100 (CET) Received: from relay6-d.mail.gandi.net (relay6-d.mail.gandi.net [217.70.183.198]) by lancelot.ideasonboard.com (Postfix) with ESMTPS id 785216073C for ; Wed, 1 Dec 2021 15:28:52 +0100 (CET) Received: (Authenticated sender: jacopo@jmondi.org) by relay6-d.mail.gandi.net (Postfix) with ESMTPSA id B91B1C0005; Wed, 1 Dec 2021 14:28:51 +0000 (UTC) From: Jacopo Mondi To: libcamera-devel@lists.libcamera.org Date: Wed, 1 Dec 2021 15:29:28 +0100 Message-Id: <20211201142936.107405-4-jacopo@jmondi.org> X-Mailer: git-send-email 2.33.1 In-Reply-To: <20211201142936.107405-1-jacopo@jmondi.org> References: <20211201142936.107405-1-jacopo@jmondi.org> MIME-Version: 1.0 Subject: [libcamera-devel] [PATCH v4 03/11] libcamera: fence: Introduce Fence X-BeenThere: libcamera-devel@lists.libcamera.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: libcamera-devel-bounces@lists.libcamera.org Sender: "libcamera-devel" Introduce a Fence class which models a synchronization primitive that allows to notify the availability of a resource. The Fence is modeled as a wrapper of a UniqueFD instance where read events are used to signal the Fence. The class can be later extended to support additional signalling mechanisms. Signed-off-by: Jacopo Mondi Reviewed-by: Laurent Pinchart --- include/libcamera/fence.h | 31 ++++++++++ include/libcamera/meson.build | 1 + src/libcamera/fence.cpp | 113 ++++++++++++++++++++++++++++++++++ src/libcamera/meson.build | 1 + 4 files changed, 146 insertions(+) create mode 100644 include/libcamera/fence.h create mode 100644 src/libcamera/fence.cpp diff --git a/include/libcamera/fence.h b/include/libcamera/fence.h new file mode 100644 index 000000000000..c0c916c264b4 --- /dev/null +++ b/include/libcamera/fence.h @@ -0,0 +1,31 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2021, Google Inc. + * + * internal/fence.h - Synchronization fence + */ + +#pragma once + +#include +#include + +namespace libcamera { + +class Fence +{ +public: + Fence(UniqueFD fd); + + bool isValid() const { return fd_.isValid(); } + const UniqueFD &fd() const { return fd_; } + + UniqueFD release() { return std::move(fd_); } + +private: + LIBCAMERA_DISABLE_COPY_AND_MOVE(Fence) + + UniqueFD fd_; +}; + +} /* namespace libcamera */ diff --git a/include/libcamera/meson.build b/include/libcamera/meson.build index 5f42977c034b..8c2cae00d877 100644 --- a/include/libcamera/meson.build +++ b/include/libcamera/meson.build @@ -6,6 +6,7 @@ libcamera_public_headers = files([ 'camera.h', 'camera_manager.h', 'controls.h', + 'fence.h', 'framebuffer.h', 'framebuffer_allocator.h', 'geometry.h', diff --git a/src/libcamera/fence.cpp b/src/libcamera/fence.cpp new file mode 100644 index 000000000000..bd737e9848e1 --- /dev/null +++ b/src/libcamera/fence.cpp @@ -0,0 +1,113 @@ +/* SPDX-License-Identifier: LGPL-2.1-or-later */ +/* + * Copyright (C) 2021, Google Inc. + * + * fence.cpp - Synchronization fence + */ + +#include "libcamera/fence.h" + +namespace libcamera { + +/** + * + * \file libcamera/fence.h + * \brief Synchronization fence + */ + +/** + * \class Fence + * \brief Synchronization primitive to manage resources + * + * The Fence class models a synchronization primitive that can be used by + * applications to explicitly synchronize resource usage, and can be shared by + * multiple processes. + * + * Synchronization fences are most commonly used in association with frame + * buffers. A FrameBuffer can be associated with a Fence so that the library can + * wait for the Fence to be signalled before allowing the camera device to + * actually access the memory area described by the FrameBuffer. + * + * \sa Request::addBuffer() + * + * By using synchronization fences, application can then synchronize between + * frame buffer consumers and producers, as for example a display device and a + * camera, to guarantee that new data transfers only happen once the existing + * frames have been displayed. + * + * A Fence can be realized by different event notification primitives, the most + * common of which is represented by waiting for read events to happen on a + * kernel sync file. This is currently the only mechanism supported by + * libcamera, but others can be implemented by extending or subclassing this + * class and implementing opportune handling in the core library. + * + * kernel sync file + * + * \internal + * + * The Fence class is a thin abstraction around a UniqueFD which simply allows + * to access it as a const reference or to move its ownership to the caller. + * + * The usage of the Fence class allows to abstract the underlying + * synchronization mechanism in use and implement an interface towards other + * library components that will not change when new synchronization primitives + * will be added as fences. + * + * A Fence is constructed with a UniqueFD whose ownership is moved in the Fence. + * A FrameBuffer can be associated with a Fence by passing it to the + * Request::addBuffer() function, which will move the Fence into the FrameBuffer + * itself. Once a Request is queued to the Camera, a preparation phase + * guarantees that before actually applying the Request to the hardware, all the + * valid fences of the frame buffers in a Request are correctly signalled. Once + * a Fence has completed, the library will release the FrameBuffer fence so that + * application won't be allowed to access it. + * + * An optional timeout can be started while waiting for a fence to complete. If + * waiting on a Fence fails for whatever reason, the FrameBuffer's fence is not + * reset and is made available to application for them to handle it, by + * releasing the Fence to correctly close the underlying UniqueFD. + * + * A failure in waiting for a Fence to complete will result in the Request to + * complete in failed state. + * + * \sa Request::prepare() + * \sa PipelineHandler::doQueueRequests() + */ + +/** + * \brief Create a synchronization fence + * \param[in] fd The synchronization fence file descriptor + * + * The file descriptor ownership is moved to the Fence. + */ +Fence::Fence(UniqueFD fd) + : fd_(std::move(fd)) +{ +} + +/** + * \fn Fence::isValid() + * \brief Check if a Fence is valid + * + * A Fence is valid if the file descriptor it wraps is valid. + * + * \return True if the Fence is valid, false otherwise + */ + +/** + * \fn Fence::fd() + * \brief Retrieve a constant reference to the file descriptor + * \return A const reference to the fence file descriptor + */ + +/** + * \fn Fence::release() + * \brief Release the ownership of the file descriptor + * + * Release the ownership of the wrapped file descriptor by returning it to the + * caller. + * + * \return The wrapper UniqueFD + */ + +} /* namespace libcamera */ diff --git a/src/libcamera/meson.build b/src/libcamera/meson.build index b763110e74a6..b4882a2577f5 100644 --- a/src/libcamera/meson.build +++ b/src/libcamera/meson.build @@ -14,6 +14,7 @@ libcamera_sources = files([ 'delayed_controls.cpp', 'device_enumerator.cpp', 'device_enumerator_sysfs.cpp', + 'fence.cpp', 'formats.cpp', 'framebuffer.cpp', 'framebuffer_allocator.cpp',