Patch Detail
Show a patch.
GET /api/patches/1539/?format=api
{ "id": 1539, "url": "https://patchwork.libcamera.org/api/patches/1539/?format=api", "web_url": "https://patchwork.libcamera.org/patch/1539/", "project": { "id": 1, "url": "https://patchwork.libcamera.org/api/projects/1/?format=api", "name": "libcamera", "link_name": "libcamera", "list_id": "libcamera_core", "list_email": "libcamera-devel@lists.libcamera.org", "web_url": "", "scm_url": "", "webscm_url": "" }, "msgid": "<20190630181049.9548-7-jacopo@jmondi.org>", "date": "2019-06-30T18:10:47", "name": "[libcamera-devel,RFC,6/8] libcamera: stream: Add operation to map buffers", "commit_ref": null, "pull_url": null, "state": "superseded", "archived": false, "hash": "f70e0e6d3e1b632bd520c47b96471e6667b88384", "submitter": { "id": 3, "url": "https://patchwork.libcamera.org/api/people/3/?format=api", "name": "Jacopo Mondi", "email": "jacopo@jmondi.org" }, "delegate": null, "mbox": "https://patchwork.libcamera.org/patch/1539/mbox/", "series": [ { "id": 383, "url": "https://patchwork.libcamera.org/api/series/383/?format=api", "web_url": "https://patchwork.libcamera.org/project/libcamera/list/?series=383", "date": "2019-06-30T18:10:41", "name": "libcamera: Add support for importing external memory buffers", "version": 1, "mbox": "https://patchwork.libcamera.org/series/383/mbox/" } ], "comments": "https://patchwork.libcamera.org/api/patches/1539/comments/", "check": "pending", "checks": "https://patchwork.libcamera.org/api/patches/1539/checks/", "tags": {}, "headers": { "Return-Path": "<jacopo@jmondi.org>", "Received": [ "from relay12.mail.gandi.net (relay12.mail.gandi.net\n\t[217.70.178.232])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id C362D61F28\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tSun, 30 Jun 2019 20:09:40 +0200 (CEST)", "from uno.lan (2-224-242-101.ip172.fastwebnet.it [2.224.242.101])\n\t(Authenticated sender: jacopo@jmondi.org)\n\tby relay12.mail.gandi.net (Postfix) with ESMTPSA id 67D77200004;\n\tSun, 30 Jun 2019 18:09:40 +0000 (UTC)" ], "From": "Jacopo Mondi <jacopo@jmondi.org>", "To": "libcamera-devel@lists.libcamera.org", "Date": "Sun, 30 Jun 2019 20:10:47 +0200", "Message-Id": "<20190630181049.9548-7-jacopo@jmondi.org>", "X-Mailer": "git-send-email 2.21.0", "In-Reply-To": "<20190630181049.9548-1-jacopo@jmondi.org>", "References": "<20190630181049.9548-1-jacopo@jmondi.org>", "MIME-Version": "1.0", "Content-Transfer-Encoding": "8bit", "Subject": "[libcamera-devel] [RFC 6/8] libcamera: stream: Add operation to map\n\tbuffers", "X-BeenThere": "libcamera-devel@lists.libcamera.org", "X-Mailman-Version": "2.1.23", "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>", "X-List-Received-Date": "Sun, 30 Jun 2019 18:09:40 -0000" }, "content": "Add and operation to map external buffers provided by applications in\na Request to the Stream's internal buffers used by the pipeline handlers\nto interact with the video device.\n\nFor streams using internal memory allocation, the two buffers are the\nsame as applications effectively use Buffers from the Stream's pool\nwhere the video device memory has been exported to.\n\nSigned-off-by: Jacopo Mondi <jacopo@jmondi.org>\n---\n include/libcamera/buffer.h | 1 +\n include/libcamera/stream.h | 5 +++\n src/libcamera/stream.cpp | 66 ++++++++++++++++++++++++++++++++++++++\n 3 files changed, 72 insertions(+)", "diff": "diff --git a/include/libcamera/buffer.h b/include/libcamera/buffer.h\nindex 260a62e9e77e..d5d3dc90a096 100644\n--- a/include/libcamera/buffer.h\n+++ b/include/libcamera/buffer.h\n@@ -59,6 +59,7 @@ private:\n \tfriend class BufferPool;\n \tfriend class PipelineHandler;\n \tfriend class Request;\n+\tfriend class Stream;\n \tfriend class V4L2VideoDevice;\n \n \tvoid cancel();\ndiff --git a/include/libcamera/stream.h b/include/libcamera/stream.h\nindex 796f1aff2602..4c034c113ddb 100644\n--- a/include/libcamera/stream.h\n+++ b/include/libcamera/stream.h\n@@ -85,6 +85,8 @@ public:\n \tconst StreamConfiguration &configuration() const { return configuration_; }\n \tMemoryType memoryType() const { return memoryType_; }\n \n+\tBuffer *mapBuffer(Buffer *requestBuffer);\n+\n protected:\n \tfriend class Camera;\n \n@@ -94,6 +96,9 @@ protected:\n \tBufferPool bufferPool_;\n \tStreamConfiguration configuration_;\n \tMemoryType memoryType_;\n+\n+\tstd::vector<Buffer *> mappableBuffers_;\n+\tstd::map<unsigned int, Buffer *> bufferMaps_;\n };\n \n } /* namespace libcamera */\ndiff --git a/src/libcamera/stream.cpp b/src/libcamera/stream.cpp\nindex b6292427d3a2..f36336857ad6 100644\n--- a/src/libcamera/stream.cpp\n+++ b/src/libcamera/stream.cpp\n@@ -13,6 +13,8 @@\n #include <iomanip>\n #include <sstream>\n \n+#include <libcamera/request.h>\n+\n #include \"log.h\"\n \n /**\n@@ -445,6 +447,26 @@ void Stream::createBuffers(unsigned int count)\n \t\treturn;\n \n \tbufferPool_.createBuffers(count);\n+\n+\t/* Streams with internal memory usage do not need buffer mapping. */\n+\tif (memoryType_ == InternalMemory)\n+\t\treturn;\n+\n+\t/*\n+\t * Prepare for buffer mapping by queuing all buffers from the internal\n+\t * pool. Each external buffer presented by application will be mapped\n+\t * on an internal one.\n+\t */\n+\tmappableBuffers_.clear();\n+\tfor (Buffer &buffer : bufferPool_.buffers()) {\n+\t\t/* Reserve all planes to support mapping multiplanar buffers. */\n+\t\tbuffer.planes().clear();\n+\t\t/* \\todo: I would use VIDEO_MAX_PLANES but that's V4L2 stuff.. */\n+\t\tfor (unsigned int i = 0; i < 3; ++i)\n+\t\t\tbuffer.planes().emplace_back();\n+\n+\t\tmappableBuffers_.push_back(&buffer);\n+\t}\n }\n \n /**\n@@ -457,6 +479,50 @@ void Stream::destroyBuffers()\n \tcreateBuffers(0);\n }\n \n+/**\n+ * \\brief Map the buffer an application has associated with a Request to an\n+ * internl one\n+ *\n+ * \\todo Rewrite documentation\n+ * If the Stream uses external memory, we need to map the externally\n+ * provided buffer to an internal one, trying to keep a best effort\n+ * association based on the Buffer's last usage time.\n+ * External and internal buffers are associated by using the dmabuf\n+ * fds as key.\n+ */\n+Buffer *Stream::mapBuffer(Buffer *requestBuffer)\n+{\n+\t/*\n+\t * \\todo Multiplane APIs have one fd per plane, the key should be\n+\t * hashed using all the planes fds.\n+\t */\n+\tunsigned int key = requestBuffer->planes()[0].dmabuf();\n+\n+\t/* If the buffer has already been mapped, just return it. */\n+\tauto mapped = bufferMaps_.find(key);\n+\tif (mapped != bufferMaps_.end())\n+\t\treturn mapped->second;\n+\n+\t/*\n+\t * Remove the last recently used buffer from the circular list and\n+\t * use it for mapping.\n+\t */\n+\tauto mappable = mappableBuffers_.begin();\n+\tBuffer *buffer = *mappable;\n+\tmappableBuffers_.erase(mappable);\n+\tmappableBuffers_.push_back(buffer);\n+\n+\t/* \\todo: Support multiplanar external buffers. */\n+\tbuffer->planes()[0].setDmabuf(key, 0);\n+\n+\t/* Pipeline handlers use request_ at buffer completion time. */\n+\tbuffer->request_ = requestBuffer->request();\n+\n+\tbufferMaps_[key] = buffer;\n+\n+\treturn buffer;\n+}\n+\n /**\n * \\var Stream::bufferPool_\n * \\brief The pool of buffers associated with the stream\n", "prefixes": [ "libcamera-devel", "RFC", "6/8" ] }