Patch Detail
Show a patch.
GET /api/1.1/patches/114/?format=api
{ "id": 114, "url": "https://patchwork.libcamera.org/api/1.1/patches/114/?format=api", "web_url": "https://patchwork.libcamera.org/patch/114/", "project": { "id": 1, "url": "https://patchwork.libcamera.org/api/1.1/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": "<20181231092752.5018-2-jacopo@jmondi.org>", "date": "2018-12-31T09:27:50", "name": "[libcamera-devel,v4,1/3] libcamera: Add MediaObject class hierarchy", "commit_ref": null, "pull_url": null, "state": "superseded", "archived": false, "hash": "2a3f5dd01b6f04f504aa13545fcee54336043e2f", "submitter": { "id": 3, "url": "https://patchwork.libcamera.org/api/1.1/people/3/?format=api", "name": "Jacopo Mondi", "email": "jacopo@jmondi.org" }, "delegate": null, "mbox": "https://patchwork.libcamera.org/patch/114/mbox/", "series": [ { "id": 44, "url": "https://patchwork.libcamera.org/api/1.1/series/44/?format=api", "web_url": "https://patchwork.libcamera.org/project/libcamera/list/?series=44", "date": "2018-12-31T09:27:49", "name": "MediaDevice class and MediaObject classes", "version": 4, "mbox": "https://patchwork.libcamera.org/series/44/mbox/" } ], "comments": "https://patchwork.libcamera.org/api/patches/114/comments/", "check": "pending", "checks": "https://patchwork.libcamera.org/api/patches/114/checks/", "tags": {}, "headers": { "Return-Path": "<jacopo@jmondi.org>", "Received": [ "from relay6-d.mail.gandi.net (relay6-d.mail.gandi.net\n\t[217.70.183.198])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 7107360B33\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tMon, 31 Dec 2018 10:27:57 +0100 (CET)", "from uno.homenet.telecomitalia.it\n\t(host54-51-dynamic.16-87-r.retail.telecomitalia.it [87.16.51.54])\n\t(Authenticated sender: jacopo@jmondi.org)\n\tby relay6-d.mail.gandi.net (Postfix) with ESMTPSA id 2A78DC0003;\n\tMon, 31 Dec 2018 09:27:55 +0000 (UTC)" ], "X-Originating-IP": "87.16.51.54", "From": "Jacopo Mondi <jacopo@jmondi.org>", "To": "libcamera-devel@lists.libcamera.org", "Date": "Mon, 31 Dec 2018 10:27:50 +0100", "Message-Id": "<20181231092752.5018-2-jacopo@jmondi.org>", "X-Mailer": "git-send-email 2.20.1", "In-Reply-To": "<20181231092752.5018-1-jacopo@jmondi.org>", "References": "<20181231092752.5018-1-jacopo@jmondi.org>", "MIME-Version": "1.0", "Content-Transfer-Encoding": "8bit", "Subject": "[libcamera-devel] [PATCH v4 1/3] libcamera: Add MediaObject class\n\thierarchy", "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": "Mon, 31 Dec 2018 09:27:57 -0000" }, "content": "Add a class hierarcy to represent all media objects a media graph represents.\nAdd a base MediaObject class, which retains the global unique object id,\nand define the derived MediaEntity, MediaLink and MediaPad classes.\n\nThis hierarchy will be used by the MediaDevice objects which represents and\nhandles the media graph.\n\nReviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>\nSigned-off-by: Jacopo Mondi <jacopo@jmondi.org>\n---\n src/libcamera/include/media_object.h | 106 ++++++++++\n src/libcamera/media_object.cpp | 279 +++++++++++++++++++++++++++\n src/libcamera/meson.build | 2 +\n 3 files changed, 387 insertions(+)\n create mode 100644 src/libcamera/include/media_object.h\n create mode 100644 src/libcamera/media_object.cpp", "diff": "diff --git a/src/libcamera/include/media_object.h b/src/libcamera/include/media_object.h\nnew file mode 100644\nindex 0000000..a8bdaab\n--- /dev/null\n+++ b/src/libcamera/include/media_object.h\n@@ -0,0 +1,106 @@\n+/* SPDX-License-Identifier: LGPL-2.1-or-later */\n+/*\n+ * Copyright (C) 2018, Google Inc.\n+ *\n+ * media_object.h - Media Device objects: entities, pads and links.\n+ */\n+#ifndef __LIBCAMERA_MEDIA_OBJECT_H__\n+#define __LIBCAMERA_MEDIA_OBJECT_H__\n+\n+#include <string>\n+#include <vector>\n+\n+#include <linux/media.h>\n+\n+namespace libcamera {\n+\n+class MediaDevice;\n+class MediaEntity;\n+\n+class MediaObject\n+{\n+public:\n+\tMediaObject(unsigned int id) : id_(id) { }\n+\tvirtual ~MediaObject() { }\n+\n+\tunsigned int id() const { return id_; }\n+\n+protected:\n+\tunsigned int id_;\n+};\n+\n+class MediaPad;\n+class MediaLink : public MediaObject\n+{\n+\tfriend class MediaDevice;\n+\n+public:\n+\t~MediaLink() { }\n+\n+\tMediaPad *source() const { return source_; }\n+\tMediaPad *sink() const { return sink_; }\n+\tunsigned int flags() const { return flags_; }\n+\n+private:\n+\tMediaLink(const struct media_v2_link *link,\n+\t\t MediaPad *source, MediaPad *sink);\n+\tMediaLink(const MediaLink &) = delete;\n+\n+\tMediaPad *source_;\n+\tMediaPad *sink_;\n+\tunsigned int flags_;\n+};\n+\n+class MediaEntity;\n+class MediaPad : public MediaObject\n+{\n+\tfriend class MediaDevice;\n+\n+public:\n+\t~MediaPad();\n+\n+\tunsigned int index() const { return index_; }\n+\tMediaEntity *entity() const { return entity_; }\n+\tunsigned int flags() const { return flags_; }\n+\tconst std::vector<MediaLink *> &links() const { return links_; }\n+\n+\tvoid addLink(MediaLink *link);\n+\n+private:\n+\tMediaPad(const struct media_v2_pad *pad, MediaEntity *entity);\n+\tMediaPad(const MediaPad &) = delete;\n+\n+\tunsigned int index_;\n+\tMediaEntity *entity_;\n+\tunsigned int flags_;\n+\n+\tstd::vector<MediaLink *> links_;\n+};\n+\n+class MediaEntity : public MediaObject\n+{\n+\tfriend class MediaDevice;\n+\n+public:\n+\tconst std::string &name() const { return name_; }\n+\n+\tconst std::vector<MediaPad *> &pads() { return pads_; }\n+\n+\tconst MediaPad *getPadByIndex(unsigned int index);\n+\tconst MediaPad *getPadById(unsigned int id);\n+\n+private:\n+\tMediaEntity(const struct media_v2_entity *entity);\n+\tMediaEntity(const MediaEntity &) = delete;\n+\t~MediaEntity();\n+\n+\tstd::string name_;\n+\tstd::string devnode_;\n+\n+\tstd::vector<MediaPad *> pads_;\n+\n+\tvoid addPad(MediaPad *pad);\n+};\n+\n+} /* namespace libcamera */\n+#endif /* __LIBCAMERA_MEDIA_OBJECT_H__ */\ndiff --git a/src/libcamera/media_object.cpp b/src/libcamera/media_object.cpp\nnew file mode 100644\nindex 0000000..5f1b2a2\n--- /dev/null\n+++ b/src/libcamera/media_object.cpp\n@@ -0,0 +1,279 @@\n+/* SPDX-License-Identifier: LGPL-2.1-or-later */\n+/*\n+ * Copyright (C) 2018, Google Inc.\n+ *\n+ * media_object.cpp - Media device objects: entities, pads and links\n+ */\n+\n+#include <errno.h>\n+#include <fcntl.h>\n+#include <string.h>\n+#include <sys/stat.h>\n+\n+#include <string>\n+#include <vector>\n+\n+#include <linux/media.h>\n+\n+#include \"log.h\"\n+#include \"media_object.h\"\n+\n+/**\n+ * \\file media_object.h\n+ *\n+ * Provides a class hierarchy that represent the corresponding of media\n+ * objects exposed by the kernel's media controller APIs.\n+ *\n+ * Media Objects represented here are media entities, media pads and\n+ * media links, created with informations as obtained by the\n+ * MEDIA_IOC_G_TOPOLOGY ioctl call.\n+ *\n+ * MediaLink, MediaPad and MediaEntity are derived classes of the virtual\n+ * base class MediaObject, which maintains a globally unique id for each object.\n+ *\n+ * Media objects have private constructors to restrict the number of classes\n+ * that can instantiate them only to the 'friend' MediaDevice one. Media\n+ * objects are in facts created when a MediaDevice gets populated.\n+ */\n+\n+namespace libcamera {\n+\n+/**\n+ * \\class MediaObject\n+ * \\brief Base class for all media object types\n+ *\n+ * MediaObject is the virtual base class for all media objects in the\n+ * media graph. Each object has a globally unique id assigned, and this\n+ * base class provides that.\n+ *\n+ * MediaEntities, MediaPads and MediaLink are MediaObject derived classes.\n+ */\n+\n+/**\n+ * \\fn MediaObject::MediaObject()\n+ * \\brief Construct a MediaObject with \\a id\n+ * \\param id The globally unique media object id\n+ */\n+\n+/**\n+ * \\fn MediaObject::id()\n+ * \\brief Retrieve the media object global id\n+ * \\return The media object globally unique id\n+ */\n+\n+/**\n+ * \\var MediaObject::id_\n+ * \\brief The MediaObject globally unique id\n+ */\n+\n+/**\n+ * \\class MediaLink\n+ * \\brief Media Link object\n+ *\n+ * A MediaLink represents a 'struct media_v2_link', with associated\n+ * references to the MediaPad it connects and an internal status defined\n+ * by the MEDIA_LNK_FL_* flags captured in flags_.\n+ *\n+ * MediaLink can be enabled and disabled, with the exception of\n+ * immutable links (see MEDIA_LNK_FL_IMMUTABLE).\n+ *\n+ * MediaLinks are created between MediaPads inspecting the media graph\n+ * topology and are stored in both the source and sink MediaPad they\n+ * connect.\n+ */\n+\n+/**\n+ * \\brief Construct a MediaLink\n+ * \\param link The media link representation\n+ * \\param source The MediaPad source\n+ * \\param sink The MediaPad sink\n+ */\n+MediaLink::MediaLink(const struct media_v2_link *link, MediaPad *source,\n+\t\t MediaPad *sink)\n+\t: MediaObject(link->id), source_(source),\n+\t sink_(sink), flags_(link->flags)\n+{\n+}\n+\n+/**\n+ * \\fn MediaLink::source()\n+ * \\brief Retrieve the media link source pad\n+ * \\return The source MediaPad\n+ */\n+\n+/**\n+ * \\fn MediaLink::sink()\n+ * \\brief Retrieve the media link sink pad\n+ * \\return The sinks MediaPad\n+ */\n+\n+/**\n+ * \\fn MediaLink::flags()\n+ * \\brief Retrieve the media link flags\n+ * \\return The link flags (MEDIA_LNK_FL_*)\n+ */\n+\n+/**\n+ * \\class MediaPad\n+ * \\brief Media Pad object\n+ *\n+ * MediaPads represent a 'struct media_v2_pad', with associated list of\n+ * links and a reference to the entity they belong to.\n+ *\n+ * MediaPads are connected to other MediaPads by MediaLinks, created\n+ * inspecting the media graph topology. Data connection between pads can be\n+ * enabled or disabled operating on the link that connects the two. See\n+ * MediaLink.\n+ *\n+ * MediaPads are either 'source' pads, or 'sink' pads. This information is\n+ * captured by the MEDIA_PAD_FL_* flags as stored in the flags_ member\n+ * variable.\n+ *\n+ * Each MediaPad has a list of MediaLinks it is associated to. All links\n+ * in a source pad are outbound links, while all links in a sink pad are\n+ * inbound ones.\n+ *\n+ * Each MediaPad has a reference to the MediaEntity it belongs to.\n+ */\n+\n+/**\n+ * \\brief Create a MediaPad\n+ * \\param pad The struct media_v2_pad kernel representation\n+ * \\param entity The MediaEntity this pad belongs to\n+ */\n+MediaPad::MediaPad(const struct media_v2_pad *pad, MediaEntity *entity)\n+\t: MediaObject(pad->id), index_(pad->index), entity_(entity),\n+\t flags_(pad->flags)\n+{\n+}\n+\n+/**\n+ * \\brief Release the list of links in the pad\n+ *\n+ * This function does not delete the MediaLink pointed by the links_ list\n+ * entries.\n+ */\n+MediaPad::~MediaPad()\n+{\n+\tlinks_.clear();\n+}\n+\n+/**\n+ * \\fn MediaPad::index()\n+ * \\brief Retrieve the media pad index\n+ * \\return The 0-indexed MediaPad index\n+ */\n+\n+/**\n+ * \\fn MediaPad::entity()\n+ * \\brief Retrieve the entity the media pad belongs to\n+ * \\return The MediaEntity the pad belongs to\n+ */\n+\n+/**\n+ * \\fn MediaPad::flags()\n+ * \\brief Retrieve the media pad flags\n+ * \\return The MediaPad flags (MEDIA_PAD_FL_*)\n+ */\n+\n+/**\n+ * \\fn MediaPad::links()\n+ * \\brief Retrieve all links in the media pad\n+ * \\return A list of MediaLinks associated with the media pad\n+ */\n+\n+/**\n+ * \\brief Add a new link to this pad\n+ * \\param link The MediaLink to add\n+ */\n+void MediaPad::addLink(MediaLink *link)\n+{\n+\tlinks_.push_back(link);\n+}\n+\n+/**\n+ * \\class MediaEntity\n+ * \\brief Media entity\n+ *\n+ * A MediaEntity represents a 'struct media_v2_entity' with an associated\n+ * list of MediaPads it contains.\n+ *\n+ * Entities are created inspecting the media graph topology, and MediaPads\n+ * gets added as they are discovered.\n+ *\n+ * TODO: Add support for associating a devnode to the entity when integrating\n+ * with DeviceEnumerator.\n+ */\n+\n+/**\n+ * \\fn MediaEntity::name()\n+ * \\brief Retrieve the entity name\n+ * \\return The MediaEntity name\n+ */\n+\n+/**\n+ * \\fn MediaEntity::pads()\n+ * \\brief Retrieve all pads of a media entity\n+ * \\return The list of the entity MediaPads\n+ */\n+\n+/**\n+ * \\brief Get a pad in this entity by its index\n+ * \\param index The 0-indexed pad index\n+ * \\return The pad with index \\a index\n+ * \\return nullptr if no pad is found at \\a index\n+ */\n+const MediaPad *MediaEntity::getPadByIndex(unsigned int index)\n+{\n+\tfor (MediaPad *p : pads_)\n+\t\tif (p->index() == index)\n+\t\t\treturn p;\n+\n+\treturn nullptr;\n+}\n+\n+/**\n+ * \\brief Get a pad in this entity by its globally unique id\n+ * \\param id The pad globally unique id\n+ * \\return The pad with id \\a id\n+ * \\return nullptr if not pad with \\a id is found\n+ */\n+const MediaPad *MediaEntity::getPadById(unsigned int id)\n+{\n+\tfor (MediaPad *p : pads_)\n+\t\tif (p->id() == id)\n+\t\t\treturn p;\n+\n+\treturn nullptr;\n+}\n+\n+/**\n+ * \\brief Construct a MediaEntity\n+ * \\param entity The struct media_v2_entity kernel representation\n+ */\n+MediaEntity::MediaEntity(const struct media_v2_entity *entity)\n+\t: MediaObject(entity->id), name_(entity->name)\n+{\n+}\n+\n+/**\n+ * \\brief Release the list of pads in the entity\n+ *\n+ * This function does not delete the MediaPad instances pointed to by the\n+ * pads_ list entries.\n+ */\n+MediaEntity::~MediaEntity()\n+{\n+\tpads_.clear();\n+}\n+\n+/**\n+ * \\brief Add \\a pad to list of entity's pads\n+ * \\param pad The MediaPad to add\n+ */\n+void MediaEntity::addPad(MediaPad *pad)\n+{\n+\tpads_.push_back(pad);\n+}\n+\n+} /* namespace libcamera */\ndiff --git a/src/libcamera/meson.build b/src/libcamera/meson.build\nindex ac5bba0..2985d40 100644\n--- a/src/libcamera/meson.build\n+++ b/src/libcamera/meson.build\n@@ -4,12 +4,14 @@ libcamera_sources = files([\n 'device_enumerator.cpp',\n 'log.cpp',\n 'main.cpp',\n+ 'media_object.cpp',\n 'pipeline_handler.cpp',\n ])\n \n libcamera_headers = files([\n 'include/device_enumerator.h',\n 'include/log.h',\n+ 'include/media_object.h',\n 'include/pipeline_handler.h',\n 'include/utils.h',\n ])\n", "prefixes": [ "libcamera-devel", "v4", "1/3" ] }