[{"id":10866,"web_url":"https://patchwork.libcamera.org/comment/10866/","msgid":"<20200626004318.GN5865@pendragon.ideasonboard.com>","date":"2020-06-26T00:43:18","subject":"Re: [libcamera-devel] [PATCH v4 8/9] libcamera: ipu3: cio2: Hide\n\tbuffer allocation and freeing from users","submitter":{"id":2,"url":"https://patchwork.libcamera.org/api/people/2/","name":"Laurent Pinchart","email":"laurent.pinchart@ideasonboard.com"},"content":"Hi Niklas,\n\nThank you for the patch.\n\nOn Fri, Jun 26, 2020 at 12:38:59AM +0200, Niklas Söderlund wrote:\n> The allocation and freeing of buffers for the CIO2 is handled in the\n> IPU3 pipeline handlers start() and stop() functions. These functions\n> also call CIO2Device start() and stop() at the appropriate times so\n> move the CIO2 buffer allocation/freeing inside the CIO2Device and reduce\n> the complexity of the exposed interface.\n> \n> Signed-off-by: Niklas Söderlund <niklas.soderlund@ragnatech.se>\n> Reviewed-by: Jacopo Mondi <jacopo@jmondi.org>\n> ---\n> * Changes since v3\n> - Keep CIO2Device::freeBuffers() but make it private.\n> \n> * Changes since v2\n> - Stop IMGU before CIO2\n> \n> * Changes since v1\n> - Fix potential leaking of buffers if start fails.\n> ---\n>  src/libcamera/pipeline/ipu3/cio2.cpp | 62 +++++++++++++---------------\n>  src/libcamera/pipeline/ipu3/cio2.h   |  4 +-\n>  src/libcamera/pipeline/ipu3/ipu3.cpp | 14 ++-----\n>  3 files changed, 33 insertions(+), 47 deletions(-)\n> \n> diff --git a/src/libcamera/pipeline/ipu3/cio2.cpp b/src/libcamera/pipeline/ipu3/cio2.cpp\n> index 972787a83dede203..d698cd80cba212a1 100644\n> --- a/src/libcamera/pipeline/ipu3/cio2.cpp\n> +++ b/src/libcamera/pipeline/ipu3/cio2.cpp\n> @@ -207,44 +207,12 @@ CIO2Device::generateConfiguration(Size size) const\n>  \treturn cfg;\n>  }\n>  \n> -/**\n> - * \\brief Allocate frame buffers for the CIO2 output\n> - *\n> - * Allocate frame buffers in the CIO2 video device to be used to capture frames\n> - * from the CIO2 output. The buffers are stored in the CIO2Device::buffers_\n> - * vector.\n> - *\n> - * \\return Number of buffers allocated or negative error code\n> - */\n> -int CIO2Device::allocateBuffers()\n> -{\n> -\tint ret = output_->allocateBuffers(CIO2_BUFFER_COUNT, &buffers_);\n> -\tif (ret < 0)\n> -\t\treturn ret;\n> -\n> -\tfor (std::unique_ptr<FrameBuffer> &buffer : buffers_)\n> -\t\tavailableBuffers_.push(buffer.get());\n> -\n> -\treturn ret;\n> -}\n> -\n>  int CIO2Device::exportBuffers(unsigned int count,\n>  \t\t\t      std::vector<std::unique_ptr<FrameBuffer>> *buffers)\n>  {\n>  \treturn output_->exportBuffers(count, buffers);\n>  }\n>  \n> -void CIO2Device::freeBuffers()\n> -{\n> -\t/* The default std::queue constructor is explicit with gcc 5 and 6. */\n> -\tavailableBuffers_ = std::queue<FrameBuffer *>{};\n> -\n> -\tbuffers_.clear();\n> -\n> -\tif (output_->releaseBuffers())\n> -\t\tLOG(IPU3, Error) << \"Failed to release CIO2 buffers\";\n> -}\n> -\n>  FrameBuffer *CIO2Device::getBuffer()\n>  {\n>  \tif (availableBuffers_.empty()) {\n> @@ -266,12 +234,27 @@ void CIO2Device::putBuffer(FrameBuffer *buffer)\n>  \n>  int CIO2Device::start()\n>  {\n> -\treturn output_->streamOn();\n> +\tint ret = output_->allocateBuffers(CIO2_BUFFER_COUNT, &buffers_);\n> +\tif (ret < 0)\n> +\t\treturn ret;\n> +\n> +\tfor (std::unique_ptr<FrameBuffer> &buffer : buffers_)\n> +\t\tavailableBuffers_.push(buffer.get());\n> +\n> +\tret = output_->streamOn();\n> +\tif (ret)\n> +\t\tfreeBuffers();\n> +\n> +\treturn ret;\n>  }\n>  \n>  int CIO2Device::stop()\n>  {\n> -\treturn output_->streamOff();\n> +\tint ret = output_->streamOff();\n> +\n> +\tfreeBuffers();\n> +\n> +\treturn ret;\n>  }\n>  \n>  int CIO2Device::queueBuffer(FrameBuffer *buffer)\n> @@ -279,6 +262,17 @@ int CIO2Device::queueBuffer(FrameBuffer *buffer)\n>  \treturn output_->queueBuffer(buffer);\n>  }\n>  \n> +void CIO2Device::freeBuffers()\n> +{\n> +\t/* The default std::queue constructor is explicit with gcc 5 and 6. */\n> +\tavailableBuffers_ = std::queue<FrameBuffer *>{};\n> +\n> +\tbuffers_.clear();\n> +\n> +\tif (output_->releaseBuffers())\n> +\t\tLOG(IPU3, Error) << \"Failed to release CIO2 buffers\";\n> +}\n\nYou don't have to move this function.\n\nReviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>\n\n> +\n>  void CIO2Device::cio2BufferReady(FrameBuffer *buffer)\n>  {\n>  \tbufferReady.emit(buffer);\n> diff --git a/src/libcamera/pipeline/ipu3/cio2.h b/src/libcamera/pipeline/ipu3/cio2.h\n> index 8cb90c9da7f19ecb..47c6f010eae6a64d 100644\n> --- a/src/libcamera/pipeline/ipu3/cio2.h\n> +++ b/src/libcamera/pipeline/ipu3/cio2.h\n> @@ -37,10 +37,8 @@ public:\n>  \n>  \tStreamConfiguration generateConfiguration(Size size) const;\n>  \n> -\tint allocateBuffers();\n>  \tint exportBuffers(unsigned int count,\n>  \t\t\t  std::vector<std::unique_ptr<FrameBuffer>> *buffers);\n> -\tvoid freeBuffers();\n>  \n>  \tFrameBuffer *getBuffer();\n>  \tvoid putBuffer(FrameBuffer *buffer);\n> @@ -54,6 +52,8 @@ public:\n>  \tSignal<FrameBuffer *> bufferReady;\n>  \n>  private:\n> +\tvoid freeBuffers();\n> +\n>  \tvoid cio2BufferReady(FrameBuffer *buffer);\n>  \n>  \tCameraSensor *sensor_;\n> diff --git a/src/libcamera/pipeline/ipu3/ipu3.cpp b/src/libcamera/pipeline/ipu3/ipu3.cpp\n> index 2d1ec707ea4b08fe..4818027e8db1f7a3 100644\n> --- a/src/libcamera/pipeline/ipu3/ipu3.cpp\n> +++ b/src/libcamera/pipeline/ipu3/ipu3.cpp\n> @@ -658,15 +658,10 @@ int PipelineHandlerIPU3::exportFrameBuffers(Camera *camera, Stream *stream,\n>  int PipelineHandlerIPU3::allocateBuffers(Camera *camera)\n>  {\n>  \tIPU3CameraData *data = cameraData(camera);\n> -\tCIO2Device *cio2 = &data->cio2_;\n>  \tImgUDevice *imgu = data->imgu_;\n>  \tunsigned int bufferCount;\n>  \tint ret;\n>  \n> -\tret = cio2->allocateBuffers();\n> -\tif (ret < 0)\n> -\t\treturn ret;\n> -\n>  \tbufferCount = std::max({\n>  \t\tdata->outStream_.configuration().bufferCount,\n>  \t\tdata->vfStream_.configuration().bufferCount,\n> @@ -674,10 +669,8 @@ int PipelineHandlerIPU3::allocateBuffers(Camera *camera)\n>  \t});\n>  \n>  \tret = imgu->allocateBuffers(data, bufferCount);\n> -\tif (ret < 0) {\n> -\t\tcio2->freeBuffers();\n> +\tif (ret < 0)\n>  \t\treturn ret;\n> -\t}\n>  \n>  \treturn 0;\n>  }\n> @@ -686,7 +679,6 @@ int PipelineHandlerIPU3::freeBuffers(Camera *camera)\n>  {\n>  \tIPU3CameraData *data = cameraData(camera);\n>  \n> -\tdata->cio2_.freeBuffers();\n>  \tdata->imgu_->freeBuffers(data);\n>  \n>  \treturn 0;\n> @@ -731,10 +723,10 @@ error:\n>  void PipelineHandlerIPU3::stop(Camera *camera)\n>  {\n>  \tIPU3CameraData *data = cameraData(camera);\n> -\tint ret;\n> +\tint ret = 0;\n>  \n> -\tret = data->cio2_.stop();\n>  \tret |= data->imgu_->stop();\n> +\tret |= data->cio2_.stop();\n>  \tif (ret)\n>  \t\tLOG(IPU3, Warning) << \"Failed to stop camera \"\n>  \t\t\t\t   << camera->name();","headers":{"Return-Path":"<libcamera-devel-bounces@lists.libcamera.org>","X-Original-To":"parsemail@patchwork.libcamera.org","Delivered-To":"parsemail@patchwork.libcamera.org","Received":["from lancelot.ideasonboard.com (lancelot.ideasonboard.com\n\t[92.243.16.209])\n\tby patchwork.libcamera.org (Postfix) with ESMTPS id 73C2FC0109\n\tfor <parsemail@patchwork.libcamera.org>;\n\tFri, 26 Jun 2020 00:43:22 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id DDB7E609C7;\n\tFri, 26 Jun 2020 02:43:21 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[IPv6:2001:4b98:dc2:55:216:3eff:fef7:d647])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id E6800603BA\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tFri, 26 Jun 2020 02:43:20 +0200 (CEST)","from pendragon.ideasonboard.com (81-175-216-236.bb.dnainternet.fi\n\t[81.175.216.236])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 4F78072E;\n\tFri, 26 Jun 2020 02:43:20 +0200 (CEST)"],"Authentication-Results":"lancelot.ideasonboard.com;\n\tdkim=fail reason=\"signature verification failed\" (1024-bit key;\n\tunprotected) header.d=ideasonboard.com header.i=@ideasonboard.com\n\theader.b=\"NDwWLmzg\"; dkim-atps=neutral","DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1593132200;\n\tbh=8PZHIalj8G2MjbcYGqYCvs11lwglkpb1QiFUGxrwps8=;\n\th=Date:From:To:Cc:Subject:References:In-Reply-To:From;\n\tb=NDwWLmzgl9hZgogZeYiz3+5P4PPjqkBwbNktU2MSD0mA/YaSvGg7mbLpEvVh9+Bvq\n\ttRfq5RbpRYv1dKkXE7CG0iIRne0+lRh4Is0cmbthSNZGQEaFZ0i014lyDBSBXtPfrB\n\tkVih+C9Q00FG0+NuBWvWdkLOo/FJ4k5NEqrJzLGc=","Date":"Fri, 26 Jun 2020 03:43:18 +0300","From":"Laurent Pinchart <laurent.pinchart@ideasonboard.com>","To":"Niklas =?utf-8?q?S=C3=B6derlund?= <niklas.soderlund@ragnatech.se>","Message-ID":"<20200626004318.GN5865@pendragon.ideasonboard.com>","References":"<20200625223900.1282164-1-niklas.soderlund@ragnatech.se>\n\t<20200625223900.1282164-9-niklas.soderlund@ragnatech.se>","MIME-Version":"1.0","Content-Disposition":"inline","In-Reply-To":"<20200625223900.1282164-9-niklas.soderlund@ragnatech.se>","Subject":"Re: [libcamera-devel] [PATCH v4 8/9] libcamera: ipu3: cio2: Hide\n\tbuffer allocation and freeing from users","X-BeenThere":"libcamera-devel@lists.libcamera.org","X-Mailman-Version":"2.1.29","Precedence":"list","List-Id":"<libcamera-devel.lists.libcamera.org>","List-Unsubscribe":"<https://lists.libcamera.org/options/libcamera-devel>,\n\t<mailto:libcamera-devel-request@lists.libcamera.org?subject=unsubscribe>","List-Archive":"<https://lists.libcamera.org/pipermail/libcamera-devel/>","List-Post":"<mailto:libcamera-devel@lists.libcamera.org>","List-Help":"<mailto:libcamera-devel-request@lists.libcamera.org?subject=help>","List-Subscribe":"<https://lists.libcamera.org/listinfo/libcamera-devel>,\n\t<mailto:libcamera-devel-request@lists.libcamera.org?subject=subscribe>","Cc":"libcamera-devel@lists.libcamera.org","Content-Type":"text/plain; charset=\"utf-8\"","Content-Transfer-Encoding":"base64","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"}}]