[libcamera-devel] [PATCH v2 05/13] libcamera: ipu3: imgu: Move the ImgUDevice class to separate files

Niklas Söderlund niklas.soderlund at ragnatech.se
Sun Jun 28 02:15:24 CEST 2020


In preparation of refactoring the IPU3 pipeline handler breakout the
ImgUDevice into its own .cpp and .h file, no functional change.

Signed-off-by: Niklas Söderlund <niklas.soderlund at ragnatech.se>
Reviewed-by: Jacopo Mondi <jacopo at jmondi.org>
---
* Changes since v1
- Remove stray newline
---
 src/libcamera/pipeline/ipu3/imgu.cpp    | 355 +++++++++++++++++++++
 src/libcamera/pipeline/ipu3/imgu.h      |  86 +++++
 src/libcamera/pipeline/ipu3/ipu3.cpp    | 404 +-----------------------
 src/libcamera/pipeline/ipu3/meson.build |   1 +
 4 files changed, 443 insertions(+), 403 deletions(-)
 create mode 100644 src/libcamera/pipeline/ipu3/imgu.cpp
 create mode 100644 src/libcamera/pipeline/ipu3/imgu.h

diff --git a/src/libcamera/pipeline/ipu3/imgu.cpp b/src/libcamera/pipeline/ipu3/imgu.cpp
new file mode 100644
index 0000000000000000..8965a51c5d26f8ae
--- /dev/null
+++ b/src/libcamera/pipeline/ipu3/imgu.cpp
@@ -0,0 +1,355 @@
+/* SPDX-License-Identifier: LGPL-2.1-or-later */
+/*
+ * Copyright (C) 2019, Google Inc.
+ *
+ * imgu.cpp - Intel IPU3 ImgU
+ */
+
+#include "imgu.h"
+
+#include <linux/media-bus-format.h>
+
+#include <libcamera/formats.h>
+#include <libcamera/stream.h>
+
+#include "libcamera/internal/log.h"
+#include "libcamera/internal/media_device.h"
+
+namespace libcamera {
+
+LOG_DECLARE_CATEGORY(IPU3)
+
+/**
+ * \brief Initialize components of the ImgU instance
+ * \param[in] mediaDevice The ImgU instance media device
+ * \param[in] index The ImgU instance index
+ *
+ * Create and open the V4L2 devices and subdevices of the ImgU instance
+ * with \a index.
+ *
+ * In case of errors the created V4L2VideoDevice and V4L2Subdevice instances
+ * are destroyed at pipeline handler delete time.
+ *
+ * \return 0 on success or a negative error code otherwise
+ */
+int ImgUDevice::init(MediaDevice *media, unsigned int index)
+{
+	int ret;
+
+	index_ = index;
+	name_ = "ipu3-imgu " + std::to_string(index_);
+	media_ = media;
+
+	/*
+	 * The media entities presence in the media device has been verified
+	 * by the match() function: no need to check for newly created
+	 * video devices and subdevice validity here.
+	 */
+	imgu_ = V4L2Subdevice::fromEntityName(media, name_);
+	ret = imgu_->open();
+	if (ret)
+		return ret;
+
+	input_ = V4L2VideoDevice::fromEntityName(media, name_ + " input");
+	ret = input_->open();
+	if (ret)
+		return ret;
+
+	output_.dev = V4L2VideoDevice::fromEntityName(media, name_ + " output");
+	ret = output_.dev->open();
+	if (ret)
+		return ret;
+
+	output_.pad = PAD_OUTPUT;
+	output_.name = "output";
+
+	viewfinder_.dev = V4L2VideoDevice::fromEntityName(media,
+							  name_ + " viewfinder");
+	ret = viewfinder_.dev->open();
+	if (ret)
+		return ret;
+
+	viewfinder_.pad = PAD_VF;
+	viewfinder_.name = "viewfinder";
+
+	stat_.dev = V4L2VideoDevice::fromEntityName(media, name_ + " 3a stat");
+	ret = stat_.dev->open();
+	if (ret)
+		return ret;
+
+	stat_.pad = PAD_STAT;
+	stat_.name = "stat";
+
+	return 0;
+}
+
+/**
+ * \brief Configure the ImgU unit input
+ * \param[in] size The ImgU input frame size
+ * \param[in] inputFormat The format to be applied to ImgU input
+ * \return 0 on success or a negative error code otherwise
+ */
+int ImgUDevice::configureInput(const Size &size,
+			       V4L2DeviceFormat *inputFormat)
+{
+	/* Configure the ImgU input video device with the requested sizes. */
+	int ret = input_->setFormat(inputFormat);
+	if (ret)
+		return ret;
+
+	LOG(IPU3, Debug) << "ImgU input format = " << inputFormat->toString();
+
+	/*
+	 * \todo The IPU3 driver implementation shall be changed to use the
+	 * input sizes as 'ImgU Input' subdevice sizes, and use the desired
+	 * GDC output sizes to configure the crop/compose rectangles.
+	 *
+	 * The current IPU3 driver implementation uses GDC sizes as the
+	 * 'ImgU Input' subdevice sizes, and the input video device sizes
+	 * to configure the crop/compose rectangles, contradicting the
+	 * V4L2 specification.
+	 */
+	Rectangle rect = {
+		.x = 0,
+		.y = 0,
+		.width = inputFormat->size.width,
+		.height = inputFormat->size.height,
+	};
+	ret = imgu_->setSelection(PAD_INPUT, V4L2_SEL_TGT_CROP, &rect);
+	if (ret)
+		return ret;
+
+	ret = imgu_->setSelection(PAD_INPUT, V4L2_SEL_TGT_COMPOSE, &rect);
+	if (ret)
+		return ret;
+
+	LOG(IPU3, Debug) << "ImgU input feeder and BDS rectangle = "
+			 << rect.toString();
+
+	V4L2SubdeviceFormat imguFormat = {};
+	imguFormat.mbus_code = MEDIA_BUS_FMT_FIXED;
+	imguFormat.size = size;
+
+	ret = imgu_->setFormat(PAD_INPUT, &imguFormat);
+	if (ret)
+		return ret;
+
+	LOG(IPU3, Debug) << "ImgU GDC format = " << imguFormat.toString();
+
+	return 0;
+}
+
+/**
+ * \brief Configure the ImgU unit \a id video output
+ * \param[in] output The ImgU output device to configure
+ * \param[in] cfg The requested configuration
+ * \return 0 on success or a negative error code otherwise
+ */
+int ImgUDevice::configureOutput(ImgUOutput *output,
+				const StreamConfiguration &cfg,
+				V4L2DeviceFormat *outputFormat)
+{
+	V4L2VideoDevice *dev = output->dev;
+	unsigned int pad = output->pad;
+
+	V4L2SubdeviceFormat imguFormat = {};
+	imguFormat.mbus_code = MEDIA_BUS_FMT_FIXED;
+	imguFormat.size = cfg.size;
+
+	int ret = imgu_->setFormat(pad, &imguFormat);
+	if (ret)
+		return ret;
+
+	/* No need to apply format to the stat node. */
+	if (output == &stat_)
+		return 0;
+
+	*outputFormat = {};
+	outputFormat->fourcc = dev->toV4L2PixelFormat(formats::NV12);
+	outputFormat->size = cfg.size;
+	outputFormat->planesCount = 2;
+
+	ret = dev->setFormat(outputFormat);
+	if (ret)
+		return ret;
+
+	LOG(IPU3, Debug) << "ImgU " << output->name << " format = "
+			 << outputFormat->toString();
+
+	return 0;
+}
+
+/**
+ * \brief Allocate buffers for all the ImgU video devices
+ */
+int ImgUDevice::allocateBuffers(unsigned int bufferCount)
+{
+	/* Share buffers between CIO2 output and ImgU input. */
+	int ret = input_->importBuffers(bufferCount);
+	if (ret) {
+		LOG(IPU3, Error) << "Failed to import ImgU input buffers";
+		return ret;
+	}
+
+	/*
+	 * The kernel fails to start if buffers are not either imported or
+	 * allocated for the statisitcs video device. As statistics buffers are
+	 * not yet used by the pipeline import buffers to save memory.
+	 *
+	 * \todo To be revised when we'll actually use the stat node.
+	 */
+	ret = stat_.dev->importBuffers(bufferCount);
+	if (ret < 0) {
+		LOG(IPU3, Error) << "Failed to allocate ImgU stat buffers";
+		goto error;
+	}
+
+	/*
+	 * Import buffers for all outputs, regardless of whether the
+	 * corresponding stream is active or inactive, as the driver needs
+	 * buffers to be requested on the V4L2 devices in order to operate.
+	 */
+	ret = output_.dev->importBuffers(bufferCount);
+	if (ret < 0) {
+		LOG(IPU3, Error) << "Failed to import ImgU output buffers";
+		goto error;
+	}
+
+	ret = viewfinder_.dev->importBuffers(bufferCount);
+	if (ret < 0) {
+		LOG(IPU3, Error) << "Failed to import ImgU viewfinder buffers";
+		goto error;
+	}
+
+	return 0;
+
+error:
+	freeBuffers();
+
+	return ret;
+}
+
+/**
+ * \brief Release buffers for all the ImgU video devices
+ */
+void ImgUDevice::freeBuffers()
+{
+	int ret;
+
+	ret = output_.dev->releaseBuffers();
+	if (ret)
+		LOG(IPU3, Error) << "Failed to release ImgU output buffers";
+
+	ret = stat_.dev->releaseBuffers();
+	if (ret)
+		LOG(IPU3, Error) << "Failed to release ImgU stat buffers";
+
+	ret = viewfinder_.dev->releaseBuffers();
+	if (ret)
+		LOG(IPU3, Error) << "Failed to release ImgU viewfinder buffers";
+
+	ret = input_->releaseBuffers();
+	if (ret)
+		LOG(IPU3, Error) << "Failed to release ImgU input buffers";
+}
+
+int ImgUDevice::start()
+{
+	int ret;
+
+	/* Start the ImgU video devices. */
+	ret = output_.dev->streamOn();
+	if (ret) {
+		LOG(IPU3, Error) << "Failed to start ImgU output";
+		return ret;
+	}
+
+	ret = viewfinder_.dev->streamOn();
+	if (ret) {
+		LOG(IPU3, Error) << "Failed to start ImgU viewfinder";
+		return ret;
+	}
+
+	ret = stat_.dev->streamOn();
+	if (ret) {
+		LOG(IPU3, Error) << "Failed to start ImgU stat";
+		return ret;
+	}
+
+	ret = input_->streamOn();
+	if (ret) {
+		LOG(IPU3, Error) << "Failed to start ImgU input";
+		return ret;
+	}
+
+	return 0;
+}
+
+int ImgUDevice::stop()
+{
+	int ret;
+
+	ret = output_.dev->streamOff();
+	ret |= viewfinder_.dev->streamOff();
+	ret |= stat_.dev->streamOff();
+	ret |= input_->streamOff();
+
+	return ret;
+}
+
+/**
+ * \brief Enable or disable a single link on the ImgU instance
+ *
+ * This method assumes the media device associated with the ImgU instance
+ * is open.
+ *
+ * \return 0 on success or a negative error code otherwise
+ */
+int ImgUDevice::linkSetup(const std::string &source, unsigned int sourcePad,
+			  const std::string &sink, unsigned int sinkPad,
+			  bool enable)
+{
+	MediaLink *link = media_->link(source, sourcePad, sink, sinkPad);
+	if (!link) {
+		LOG(IPU3, Error)
+			<< "Failed to get link: '" << source << "':"
+			<< sourcePad << " -> '" << sink << "':" << sinkPad;
+		return -ENODEV;
+	}
+
+	return link->setEnabled(enable);
+}
+
+/**
+ * \brief Enable or disable all media links in the ImgU instance to prepare
+ * for capture operations
+ *
+ * \todo This method will probably be removed or changed once links will be
+ * enabled or disabled selectively.
+ *
+ * \return 0 on success or a negative error code otherwise
+ */
+int ImgUDevice::enableLinks(bool enable)
+{
+	std::string viewfinderName = name_ + " viewfinder";
+	std::string outputName = name_ + " output";
+	std::string statName = name_ + " 3a stat";
+	std::string inputName = name_ + " input";
+	int ret;
+
+	ret = linkSetup(inputName, 0, name_, PAD_INPUT, enable);
+	if (ret)
+		return ret;
+
+	ret = linkSetup(name_, PAD_OUTPUT, outputName, 0, enable);
+	if (ret)
+		return ret;
+
+	ret = linkSetup(name_, PAD_VF, viewfinderName, 0, enable);
+	if (ret)
+		return ret;
+
+	return linkSetup(name_, PAD_STAT, statName, 0, enable);
+}
+
+} /* namespace libcamera */
diff --git a/src/libcamera/pipeline/ipu3/imgu.h b/src/libcamera/pipeline/ipu3/imgu.h
new file mode 100644
index 0000000000000000..9bb1b88e2ca8ea2d
--- /dev/null
+++ b/src/libcamera/pipeline/ipu3/imgu.h
@@ -0,0 +1,86 @@
+/* SPDX-License-Identifier: LGPL-2.1-or-later */
+/*
+ * Copyright (C) 2019, Google Inc.
+ *
+ * imgu.h - Intel IPU3 ImgU
+ */
+#ifndef __LIBCAMERA_PIPELINE_IPU3_IMGU_H__
+#define __LIBCAMERA_PIPELINE_IPU3_IMGU_H__
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include "libcamera/internal/v4l2_subdevice.h"
+#include "libcamera/internal/v4l2_videodevice.h"
+
+namespace libcamera {
+
+class FrameBuffer;
+class MediaDevice;
+struct Size;
+struct StreamConfiguration;
+
+class ImgUDevice
+{
+public:
+	static constexpr unsigned int PAD_INPUT = 0;
+	static constexpr unsigned int PAD_OUTPUT = 2;
+	static constexpr unsigned int PAD_VF = 3;
+	static constexpr unsigned int PAD_STAT = 4;
+
+	/* ImgU output descriptor: group data specific to an ImgU output. */
+	struct ImgUOutput {
+		V4L2VideoDevice *dev;
+		unsigned int pad;
+		std::string name;
+	};
+
+	ImgUDevice()
+		: imgu_(nullptr), input_(nullptr)
+	{
+		output_.dev = nullptr;
+		viewfinder_.dev = nullptr;
+		stat_.dev = nullptr;
+	}
+
+	~ImgUDevice()
+	{
+		delete imgu_;
+		delete input_;
+		delete output_.dev;
+		delete viewfinder_.dev;
+		delete stat_.dev;
+	}
+
+	int init(MediaDevice *media, unsigned int index);
+	int configureInput(const Size &size, V4L2DeviceFormat *inputFormat);
+	int configureOutput(ImgUOutput *output, const StreamConfiguration &cfg,
+			    V4L2DeviceFormat *outputFormat);
+
+	int allocateBuffers(unsigned int bufferCount);
+	void freeBuffers();
+
+	int start();
+	int stop();
+
+	int linkSetup(const std::string &source, unsigned int sourcePad,
+		      const std::string &sink, unsigned int sinkPad,
+		      bool enable);
+	int enableLinks(bool enable);
+
+	unsigned int index_;
+	std::string name_;
+	MediaDevice *media_;
+
+	V4L2Subdevice *imgu_;
+	V4L2VideoDevice *input_;
+	ImgUOutput output_;
+	ImgUOutput viewfinder_;
+	ImgUOutput stat_;
+	/* \todo Add param video device for 3A tuning */
+};
+
+} /* namespace libcamera */
+
+#endif /* __LIBCAMERA_PIPELINE_IPU3_IMGU_H__ */
diff --git a/src/libcamera/pipeline/ipu3/ipu3.cpp b/src/libcamera/pipeline/ipu3/ipu3.cpp
index fd2725c7bd0c144b..b41a789e8dc2a7b2 100644
--- a/src/libcamera/pipeline/ipu3/ipu3.cpp
+++ b/src/libcamera/pipeline/ipu3/ipu3.cpp
@@ -11,8 +11,6 @@
 #include <queue>
 #include <vector>
 
-#include <linux/media-bus-format.h>
-
 #include <libcamera/camera.h>
 #include <libcamera/formats.h>
 #include <libcamera/request.h>
@@ -25,77 +23,14 @@
 #include "libcamera/internal/pipeline_handler.h"
 #include "libcamera/internal/utils.h"
 #include "libcamera/internal/v4l2_controls.h"
-#include "libcamera/internal/v4l2_subdevice.h"
-#include "libcamera/internal/v4l2_videodevice.h"
 
 #include "cio2.h"
+#include "imgu.h"
 
 namespace libcamera {
 
 LOG_DEFINE_CATEGORY(IPU3)
 
-class ImgUDevice
-{
-public:
-	static constexpr unsigned int PAD_INPUT = 0;
-	static constexpr unsigned int PAD_OUTPUT = 2;
-	static constexpr unsigned int PAD_VF = 3;
-	static constexpr unsigned int PAD_STAT = 4;
-
-	/* ImgU output descriptor: group data specific to an ImgU output. */
-	struct ImgUOutput {
-		V4L2VideoDevice *dev;
-		unsigned int pad;
-		std::string name;
-	};
-
-	ImgUDevice()
-		: imgu_(nullptr), input_(nullptr)
-	{
-		output_.dev = nullptr;
-		viewfinder_.dev = nullptr;
-		stat_.dev = nullptr;
-	}
-
-	~ImgUDevice()
-	{
-		delete imgu_;
-		delete input_;
-		delete output_.dev;
-		delete viewfinder_.dev;
-		delete stat_.dev;
-	}
-
-	int init(MediaDevice *media, unsigned int index);
-	int configureInput(const Size &size,
-			   V4L2DeviceFormat *inputFormat);
-	int configureOutput(ImgUOutput *output,
-			    const StreamConfiguration &cfg,
-			    V4L2DeviceFormat *outputFormat);
-
-	int allocateBuffers(unsigned int bufferCount);
-	void freeBuffers();
-
-	int start();
-	int stop();
-
-	int linkSetup(const std::string &source, unsigned int sourcePad,
-		      const std::string &sink, unsigned int sinkPad,
-		      bool enable);
-	int enableLinks(bool enable);
-
-	unsigned int index_;
-	std::string name_;
-	MediaDevice *media_;
-
-	V4L2Subdevice *imgu_;
-	V4L2VideoDevice *input_;
-	ImgUOutput output_;
-	ImgUOutput viewfinder_;
-	ImgUOutput stat_;
-	/* \todo Add param video device for 3A tuning */
-};
-
 class IPU3Stream : public Stream
 {
 public:
@@ -952,343 +887,6 @@ void IPU3CameraData::cio2BufferReady(FrameBuffer *buffer)
 	imgu_->input_->queueBuffer(buffer);
 }
 
-/* -----------------------------------------------------------------------------
- * ImgU Device
- */
-
-/**
- * \brief Initialize components of the ImgU instance
- * \param[in] mediaDevice The ImgU instance media device
- * \param[in] index The ImgU instance index
- *
- * Create and open the V4L2 devices and subdevices of the ImgU instance
- * with \a index.
- *
- * In case of errors the created V4L2VideoDevice and V4L2Subdevice instances
- * are destroyed at pipeline handler delete time.
- *
- * \return 0 on success or a negative error code otherwise
- */
-int ImgUDevice::init(MediaDevice *media, unsigned int index)
-{
-	int ret;
-
-	index_ = index;
-	name_ = "ipu3-imgu " + std::to_string(index_);
-	media_ = media;
-
-	/*
-	 * The media entities presence in the media device has been verified
-	 * by the match() function: no need to check for newly created
-	 * video devices and subdevice validity here.
-	 */
-	imgu_ = V4L2Subdevice::fromEntityName(media, name_);
-	ret = imgu_->open();
-	if (ret)
-		return ret;
-
-	input_ = V4L2VideoDevice::fromEntityName(media, name_ + " input");
-	ret = input_->open();
-	if (ret)
-		return ret;
-
-	output_.dev = V4L2VideoDevice::fromEntityName(media, name_ + " output");
-	ret = output_.dev->open();
-	if (ret)
-		return ret;
-
-	output_.pad = PAD_OUTPUT;
-	output_.name = "output";
-
-	viewfinder_.dev = V4L2VideoDevice::fromEntityName(media,
-							  name_ + " viewfinder");
-	ret = viewfinder_.dev->open();
-	if (ret)
-		return ret;
-
-	viewfinder_.pad = PAD_VF;
-	viewfinder_.name = "viewfinder";
-
-	stat_.dev = V4L2VideoDevice::fromEntityName(media, name_ + " 3a stat");
-	ret = stat_.dev->open();
-	if (ret)
-		return ret;
-
-	stat_.pad = PAD_STAT;
-	stat_.name = "stat";
-
-	return 0;
-}
-
-/**
- * \brief Configure the ImgU unit input
- * \param[in] size The ImgU input frame size
- * \param[in] inputFormat The format to be applied to ImgU input
- * \return 0 on success or a negative error code otherwise
- */
-int ImgUDevice::configureInput(const Size &size,
-			       V4L2DeviceFormat *inputFormat)
-{
-	/* Configure the ImgU input video device with the requested sizes. */
-	int ret = input_->setFormat(inputFormat);
-	if (ret)
-		return ret;
-
-	LOG(IPU3, Debug) << "ImgU input format = " << inputFormat->toString();
-
-	/*
-	 * \todo The IPU3 driver implementation shall be changed to use the
-	 * input sizes as 'ImgU Input' subdevice sizes, and use the desired
-	 * GDC output sizes to configure the crop/compose rectangles.
-	 *
-	 * The current IPU3 driver implementation uses GDC sizes as the
-	 * 'ImgU Input' subdevice sizes, and the input video device sizes
-	 * to configure the crop/compose rectangles, contradicting the
-	 * V4L2 specification.
-	 */
-	Rectangle rect = {
-		.x = 0,
-		.y = 0,
-		.width = inputFormat->size.width,
-		.height = inputFormat->size.height,
-	};
-	ret = imgu_->setSelection(PAD_INPUT, V4L2_SEL_TGT_CROP, &rect);
-	if (ret)
-		return ret;
-
-	ret = imgu_->setSelection(PAD_INPUT, V4L2_SEL_TGT_COMPOSE, &rect);
-	if (ret)
-		return ret;
-
-	LOG(IPU3, Debug) << "ImgU input feeder and BDS rectangle = "
-			 << rect.toString();
-
-	V4L2SubdeviceFormat imguFormat = {};
-	imguFormat.mbus_code = MEDIA_BUS_FMT_FIXED;
-	imguFormat.size = size;
-
-	ret = imgu_->setFormat(PAD_INPUT, &imguFormat);
-	if (ret)
-		return ret;
-
-	LOG(IPU3, Debug) << "ImgU GDC format = " << imguFormat.toString();
-
-	return 0;
-}
-
-/**
- * \brief Configure the ImgU unit \a id video output
- * \param[in] output The ImgU output device to configure
- * \param[in] cfg The requested configuration
- * \return 0 on success or a negative error code otherwise
- */
-int ImgUDevice::configureOutput(ImgUOutput *output,
-				const StreamConfiguration &cfg,
-				V4L2DeviceFormat *outputFormat)
-{
-	V4L2VideoDevice *dev = output->dev;
-	unsigned int pad = output->pad;
-
-	V4L2SubdeviceFormat imguFormat = {};
-	imguFormat.mbus_code = MEDIA_BUS_FMT_FIXED;
-	imguFormat.size = cfg.size;
-
-	int ret = imgu_->setFormat(pad, &imguFormat);
-	if (ret)
-		return ret;
-
-	/* No need to apply format to the stat node. */
-	if (output == &stat_)
-		return 0;
-
-	*outputFormat = {};
-	outputFormat->fourcc = dev->toV4L2PixelFormat(formats::NV12);
-	outputFormat->size = cfg.size;
-	outputFormat->planesCount = 2;
-
-	ret = dev->setFormat(outputFormat);
-	if (ret)
-		return ret;
-
-	LOG(IPU3, Debug) << "ImgU " << output->name << " format = "
-			 << outputFormat->toString();
-
-	return 0;
-}
-
-/**
- * \brief Allocate buffers for all the ImgU video devices
- */
-int ImgUDevice::allocateBuffers(unsigned int bufferCount)
-{
-	/* Share buffers between CIO2 output and ImgU input. */
-	int ret = input_->importBuffers(bufferCount);
-	if (ret) {
-		LOG(IPU3, Error) << "Failed to import ImgU input buffers";
-		return ret;
-	}
-
-	/*
-	 * The kernel fails to start if buffers are not either imported or
-	 * allocated for the statisitcs video device. As statistics buffers are
-	 * not yet used by the pipeline import buffers to save memory.
-	 *
-	 * \todo To be revised when we'll actually use the stat node.
-	 */
-	ret = stat_.dev->importBuffers(bufferCount);
-	if (ret < 0) {
-		LOG(IPU3, Error) << "Failed to allocate ImgU stat buffers";
-		goto error;
-	}
-
-	/*
-	 * Import buffers for all outputs, regardless of whether the
-	 * corresponding stream is active or inactive, as the driver needs
-	 * buffers to be requested on the V4L2 devices in order to operate.
-	 */
-	ret = output_.dev->importBuffers(bufferCount);
-	if (ret < 0) {
-		LOG(IPU3, Error) << "Failed to import ImgU output buffers";
-		goto error;
-	}
-
-	ret = viewfinder_.dev->importBuffers(bufferCount);
-	if (ret < 0) {
-		LOG(IPU3, Error) << "Failed to import ImgU viewfinder buffers";
-		goto error;
-	}
-
-	return 0;
-
-error:
-	freeBuffers();
-
-	return ret;
-}
-
-/**
- * \brief Release buffers for all the ImgU video devices
- */
-void ImgUDevice::freeBuffers()
-{
-	int ret;
-
-	ret = output_.dev->releaseBuffers();
-	if (ret)
-		LOG(IPU3, Error) << "Failed to release ImgU output buffers";
-
-	ret = stat_.dev->releaseBuffers();
-	if (ret)
-		LOG(IPU3, Error) << "Failed to release ImgU stat buffers";
-
-	ret = viewfinder_.dev->releaseBuffers();
-	if (ret)
-		LOG(IPU3, Error) << "Failed to release ImgU viewfinder buffers";
-
-	ret = input_->releaseBuffers();
-	if (ret)
-		LOG(IPU3, Error) << "Failed to release ImgU input buffers";
-}
-
-int ImgUDevice::start()
-{
-	int ret;
-
-	/* Start the ImgU video devices. */
-	ret = output_.dev->streamOn();
-	if (ret) {
-		LOG(IPU3, Error) << "Failed to start ImgU output";
-		return ret;
-	}
-
-	ret = viewfinder_.dev->streamOn();
-	if (ret) {
-		LOG(IPU3, Error) << "Failed to start ImgU viewfinder";
-		return ret;
-	}
-
-	ret = stat_.dev->streamOn();
-	if (ret) {
-		LOG(IPU3, Error) << "Failed to start ImgU stat";
-		return ret;
-	}
-
-	ret = input_->streamOn();
-	if (ret) {
-		LOG(IPU3, Error) << "Failed to start ImgU input";
-		return ret;
-	}
-
-	return 0;
-}
-
-int ImgUDevice::stop()
-{
-	int ret;
-
-	ret = output_.dev->streamOff();
-	ret |= viewfinder_.dev->streamOff();
-	ret |= stat_.dev->streamOff();
-	ret |= input_->streamOff();
-
-	return ret;
-}
-
-/**
- * \brief Enable or disable a single link on the ImgU instance
- *
- * This method assumes the media device associated with the ImgU instance
- * is open.
- *
- * \return 0 on success or a negative error code otherwise
- */
-int ImgUDevice::linkSetup(const std::string &source, unsigned int sourcePad,
-			  const std::string &sink, unsigned int sinkPad,
-			  bool enable)
-{
-	MediaLink *link = media_->link(source, sourcePad, sink, sinkPad);
-	if (!link) {
-		LOG(IPU3, Error)
-			<< "Failed to get link: '" << source << "':"
-			<< sourcePad << " -> '" << sink << "':" << sinkPad;
-		return -ENODEV;
-	}
-
-	return link->setEnabled(enable);
-}
-
-/**
- * \brief Enable or disable all media links in the ImgU instance to prepare
- * for capture operations
- *
- * \todo This method will probably be removed or changed once links will be
- * enabled or disabled selectively.
- *
- * \return 0 on success or a negative error code otherwise
- */
-int ImgUDevice::enableLinks(bool enable)
-{
-	std::string viewfinderName = name_ + " viewfinder";
-	std::string outputName = name_ + " output";
-	std::string statName = name_ + " 3a stat";
-	std::string inputName = name_ + " input";
-	int ret;
-
-	ret = linkSetup(inputName, 0, name_, PAD_INPUT, enable);
-	if (ret)
-		return ret;
-
-	ret = linkSetup(name_, PAD_OUTPUT, outputName, 0, enable);
-	if (ret)
-		return ret;
-
-	ret = linkSetup(name_, PAD_VF, viewfinderName, 0, enable);
-	if (ret)
-		return ret;
-
-	return linkSetup(name_, PAD_STAT, statName, 0, enable);
-}
-
 REGISTER_PIPELINE_HANDLER(PipelineHandlerIPU3);
 
 } /* namespace libcamera */
diff --git a/src/libcamera/pipeline/ipu3/meson.build b/src/libcamera/pipeline/ipu3/meson.build
index b2602d30123f908d..d60e07ae6ccac2bc 100644
--- a/src/libcamera/pipeline/ipu3/meson.build
+++ b/src/libcamera/pipeline/ipu3/meson.build
@@ -2,5 +2,6 @@
 
 libcamera_sources += files([
     'cio2.cpp',
+    'imgu.cpp',
     'ipu3.cpp',
 ])
-- 
2.27.0



More information about the libcamera-devel mailing list