[{"id":1170,"web_url":"https://patchwork.libcamera.org/comment/1170/","msgid":"<20190402075927.ekwz2rhzekdwdls3@uno.localdomain>","date":"2019-04-02T07:59:27","subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","submitter":{"id":3,"url":"https://patchwork.libcamera.org/api/people/3/","name":"Jacopo Mondi","email":"jacopo@jmondi.org"},"content":"Hi Niklas,\n\nOn Tue, Apr 02, 2019 at 02:53:31AM +0200, Niklas Söderlund wrote:\n> In preparation of reworking how a default configuration is retrieved\n> from a camera add stream usage hints. The hints will be used by\n> applications to describe how it intends to use a camera and replace the\n> Stream IDs role when retrieving default configuration from the camera\n> using streamConfiguration().\n>\n> Signed-off-by: Niklas Söderlund <niklas.soderlund@ragnatech.se>\n> ---\n>  include/libcamera/stream.h | 39 ++++++++++++++++++\n>  src/libcamera/stream.cpp   | 84 ++++++++++++++++++++++++++++++++++++++\n>  2 files changed, 123 insertions(+)\n>\n> diff --git a/include/libcamera/stream.h b/include/libcamera/stream.h\n> index 3e8e83a2ff245879..445b80de66217934 100644\n> --- a/include/libcamera/stream.h\n> +++ b/include/libcamera/stream.h\n> @@ -35,7 +35,46 @@ private:\n>  \tStreamConfiguration configuration_;\n>  };\n>\n> +class StreamHint\n> +{\n> +public:\n> +\tenum Type {\n> +\t\tViewfinder,\n> +\t\tVideo,\n> +\t\tStill,\n\nI would use all capitals, and lengthen 'video' and 'still' as\nSTILL_CAPTURE and VIDEO_CAPTURE\n\n> +\t};\n>\n> +\tType type() const { return type_; }\n\nconst Type &\n\n> +\n> +protected:\n> +\tStreamHint(Type type);\n> +\tStreamHint(Type type, StreamConfiguration hints);\n\n&hints\n\n> +\n> +private:\n> +\tType type_;\n> +\tStreamConfiguration hints_;\n\nI would call the configuration descriptor of an hint 'config_' not\n'hints_'.\n\n> +};\n> +\n> +class Viewfinder : public StreamHint\n> +{\n> +public:\n> +\tViewfinder(unsigned int width, unsigned int height);\n> +\n> +private:\n> +\tstatic StreamConfiguration initHints(unsigned int width, unsigned int height);\n> +};\n> +\n> +class Video : public StreamHint\n> +{\n> +public:\n> +\tVideo();\n> +};\n> +\n> +class Still : public StreamHint\n> +{\n> +public:\n> +\tStill();\n> +};\n\nI would question if these hierarchy brings any benefit or it just\nmakes more complex adding new use cases.\n\nAs I immagined this, use case hints might just be an enumeration with\na configuration associated, ie. I don't think only viewfinder should\nhave associated sizes, but it should still be possible to specify a\nmax sizes for the other streams to make sure the selected streams\ncould provide that resolution. Furthermore the base class has a\nconfiguration field, but it is only accessible for the viewfinder use\ncase, why that?\n\n>\n>  } /* namespace libcamera */\n>\n> diff --git a/src/libcamera/stream.cpp b/src/libcamera/stream.cpp\n> index c4943c91b2e6ce13..32f26a1f8e6adb2c 100644\n> --- a/src/libcamera/stream.cpp\n> +++ b/src/libcamera/stream.cpp\n> @@ -102,4 +102,88 @@ Stream::Stream()\n>   * \\return The active configuration of the stream\n>   */\n>\n> +/**\n> + * \\class StreamHint\n> + * \\brief Stream usage hint information\n> + *\n> + * The StreamHint class carries information about stream usage hints from the\n> + * application to a specific pipeline handler implementation. The pipeline\n> + * handler shall take the usage hints into account when select which stream\n> + * to use for the desired operation.\n\nI would mention Camera not pipeline handlers here, as the interface\nfor applications using hints will be the Camera class.\n\n\n> + */\n> +\n> +/**\n> + * \\enum StreamHint::Type\n> + * \\brief List of types of usage hints\n> + */\n> +\n> +/**\n> + * \\fn StreamHint::type()\n> + * \\brief Retrieve the usage hint type\n\nDon't we usually insert a blank line between \\brief and \\return?\n\n> + * \\return The hint type\n> + */\n> +\n> +/**\n> + * \\brief Create a stream hint\n> + * \\param[in] type Stream hint type\n> + */\n> +StreamHint::StreamHint(Type type)\n> +\t: type_(type), hints_()\n> +{\n> +}\n> +\n> +/**\n> + * \\brief Create a stream hint with parameters\n> + * \\param[in] type Stream hint type\n> + * \\param[in] hints Stream hint parameters\n> + */\n> +StreamHint::StreamHint(Type type, StreamConfiguration hints)\n> +\t: type_(type), hints_(hints)\n> +{\n> +}\n> +\n> +/**\n> + * \\class Viewfinder\n> + * \\brief Stream usage hint for viewfinder\n> + */\n> +\n> +/**\n> + * \\brief Create a viewfinder stream hint\n> + * \\param[in] width Desired view finder width\n\nviewfinder\n\n> + * \\param[in] height Desired view finder height\n> + */\n> +Viewfinder::Viewfinder(unsigned int width, unsigned int height)\n> +\t: StreamHint(Type::Viewfinder, initHints(width, height))\n> +{\n> +}\n> +\n> +StreamConfiguration Viewfinder::initHints(unsigned int width,\n> +\t\t\t\t\t  unsigned int height)\n> +{\n> +\tStreamConfiguration hints = {};\n> +\n> +\thints.width = width;\n> +\thints.height = height;\n> +\n> +\treturn hints;\n> +}\n\nIs this necessary? Couldn't you just pass width and height to the base\nclass constructor and let it assign hints_.widht and hints_.height\nwithout going through copies? Or you think they would be elided by\nRVO everywhere here?\n\n> +\n> +/**\n> + * \\class Video\n> + * \\brief Stream usage hint for video\n> + */\n> +Video::Video()\n> +\t: StreamHint(Type::Video)\n> +{\n> +}\n> +\n> +/**\n> + * \\class Still\n> + * \\brief Stream usage hint for still images\n> + */\n> +Still::Still()\n> +\t: StreamHint(Type::Still)\n> +{\n> +}\n> +\n>  } /* namespace libcamera */\n> --\n> 2.21.0\n>\n> _______________________________________________\n> libcamera-devel mailing list\n> libcamera-devel@lists.libcamera.org\n> https://lists.libcamera.org/listinfo/libcamera-devel","headers":{"Return-Path":"<jacopo@jmondi.org>","Received":["from relay4-d.mail.gandi.net (relay4-d.mail.gandi.net\n\t[217.70.183.196])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 20DED60DB3\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue,  2 Apr 2019 09:58:43 +0200 (CEST)","from uno.localdomain (2-224-242-101.ip172.fastwebnet.it\n\t[2.224.242.101]) (Authenticated sender: jacopo@jmondi.org)\n\tby relay4-d.mail.gandi.net (Postfix) with ESMTPSA id 992F0E0010;\n\tTue,  2 Apr 2019 07:58:42 +0000 (UTC)"],"X-Originating-IP":"2.224.242.101","Date":"Tue, 2 Apr 2019 09:59:27 +0200","From":"Jacopo Mondi <jacopo@jmondi.org>","To":"Niklas =?utf-8?q?S=C3=B6derlund?= <niklas.soderlund@ragnatech.se>","Cc":"libcamera-devel@lists.libcamera.org","Message-ID":"<20190402075927.ekwz2rhzekdwdls3@uno.localdomain>","References":"<20190402005332.25018-1-niklas.soderlund@ragnatech.se>\n\t<20190402005332.25018-5-niklas.soderlund@ragnatech.se>","MIME-Version":"1.0","Content-Type":"multipart/signed; micalg=pgp-sha256;\n\tprotocol=\"application/pgp-signature\"; boundary=\"vsg24w3suv6t3bqu\"","Content-Disposition":"inline","In-Reply-To":"<20190402005332.25018-5-niklas.soderlund@ragnatech.se>","User-Agent":"NeoMutt/20180716","Subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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":"Tue, 02 Apr 2019 07:58:43 -0000"}},{"id":1203,"web_url":"https://patchwork.libcamera.org/comment/1203/","msgid":"<20190402120214.GW23466@bigcity.dyn.berto.se>","date":"2019-04-02T12:02:14","subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","submitter":{"id":5,"url":"https://patchwork.libcamera.org/api/people/5/","name":"Niklas Söderlund","email":"niklas.soderlund@ragnatech.se"},"content":"Hi Jacopo,\n\nThanks for your feedback.\n\nOn 2019-04-02 09:59:27 +0200, Jacopo Mondi wrote:\n> Hi Niklas,\n> \n> On Tue, Apr 02, 2019 at 02:53:31AM +0200, Niklas Söderlund wrote:\n> > In preparation of reworking how a default configuration is retrieved\n> > from a camera add stream usage hints. The hints will be used by\n> > applications to describe how it intends to use a camera and replace the\n> > Stream IDs role when retrieving default configuration from the camera\n> > using streamConfiguration().\n> >\n> > Signed-off-by: Niklas Söderlund <niklas.soderlund@ragnatech.se>\n> > ---\n> >  include/libcamera/stream.h | 39 ++++++++++++++++++\n> >  src/libcamera/stream.cpp   | 84 ++++++++++++++++++++++++++++++++++++++\n> >  2 files changed, 123 insertions(+)\n> >\n> > diff --git a/include/libcamera/stream.h b/include/libcamera/stream.h\n> > index 3e8e83a2ff245879..445b80de66217934 100644\n> > --- a/include/libcamera/stream.h\n> > +++ b/include/libcamera/stream.h\n> > @@ -35,7 +35,46 @@ private:\n> >  \tStreamConfiguration configuration_;\n> >  };\n> >\n> > +class StreamHint\n> > +{\n> > +public:\n> > +\tenum Type {\n> > +\t\tViewfinder,\n> > +\t\tVideo,\n> > +\t\tStill,\n> \n> I would use all capitals, and lengthen 'video' and 'still' as\n> STILL_CAPTURE and VIDEO_CAPTURE\n\nI don't agree I think it's better as is :-) As this is bike shedding \nterritory I will yield to popular opinion. What to the rest of you \nthink?\n\n> \n> > +\t};\n> >\n> > +\tType type() const { return type_; }\n> \n> const Type &\n\nThanks.\n\n> \n> > +\n> > +protected:\n> > +\tStreamHint(Type type);\n> > +\tStreamHint(Type type, StreamConfiguration hints);\n> \n> &hints\n\nThanks, will make this a const &.\n\n> \n> > +\n> > +private:\n> > +\tType type_;\n> > +\tStreamConfiguration hints_;\n> \n> I would call the configuration descriptor of an hint 'config_' not\n> 'hints_'.\n\nI tried that at first but it gave me a bad feeling as it's in fact not a \nconfiguration it's a hint of the configuration the user wish to use. I \nwill keep this as hints_ for now.\n\nI'm not even sure the type should be StreamConfiguration or if we should \ninline the variables we judge to be useful as hints. As we have no \npipelines yet to experiment with making use of the hints I picked \nsomething to store the user provided hints in. Also note that there is \ncurrently no way for a pipeline handler to get hold of the content of \nhints_. This is by design to force me to do something here when we join \nthis work with the stream properties :-)\n\n> \n> > +};\n> > +\n> > +class Viewfinder : public StreamHint\n> > +{\n> > +public:\n> > +\tViewfinder(unsigned int width, unsigned int height);\n> > +\n> > +private:\n> > +\tstatic StreamConfiguration initHints(unsigned int width, unsigned int height);\n> > +};\n> > +\n> > +class Video : public StreamHint\n> > +{\n> > +public:\n> > +\tVideo();\n> > +};\n> > +\n> > +class Still : public StreamHint\n> > +{\n> > +public:\n> > +\tStill();\n> > +};\n> \n> I would question if these hierarchy brings any benefit or it just\n> makes more complex adding new use cases.\n\nI don't think we will add use cases all that much. The main reason I \nwent with this design is to make it easier for applications to use the \ninterface.\n\n    foo->streamConfiguration({ Viewfinder(640,480), Still() });\n\nIs quiet nice to use instead of having to create raw StreamHint objects \nand configure them. It also gives us a bit more of control, with this \ndesign we can force any hint for a Viewfinder to supply a hint for the \nresolution while if we allowed raw StreamHint creation pipeline handers \nwould need to be prepared to handle them both with and without that \ninformation.\n\nI expect his area will change a lot as we move forward, both based on \nneeds from applications and implementations in pipeline handlers. In \nthis RFC I have only parameterized the viewfinder hint as it's quiet \nclear dimensions would be part of its hints. I expect Video and Still to \nbe parameterized in the near future.\n\n> \n> As I immagined this, use case hints might just be an enumeration with\n> a configuration associated, ie. I don't think only viewfinder should\n> have associated sizes, but it should still be possible to specify a\n> max sizes for the other streams to make sure the selected streams\n> could provide that resolution. Furthermore the base class has a\n> configuration field, but it is only accessible for the viewfinder use\n> case, why that?\n> \n> >\n> >  } /* namespace libcamera */\n> >\n> > diff --git a/src/libcamera/stream.cpp b/src/libcamera/stream.cpp\n> > index c4943c91b2e6ce13..32f26a1f8e6adb2c 100644\n> > --- a/src/libcamera/stream.cpp\n> > +++ b/src/libcamera/stream.cpp\n> > @@ -102,4 +102,88 @@ Stream::Stream()\n> >   * \\return The active configuration of the stream\n> >   */\n> >\n> > +/**\n> > + * \\class StreamHint\n> > + * \\brief Stream usage hint information\n> > + *\n> > + * The StreamHint class carries information about stream usage hints from the\n> > + * application to a specific pipeline handler implementation. The pipeline\n> > + * handler shall take the usage hints into account when select which stream\n> > + * to use for the desired operation.\n> \n> I would mention Camera not pipeline handlers here, as the interface\n> for applications using hints will be the Camera class.\n\nThe Camera don't make use of the hints it only forwards them to the \npipeline handler. I think it's correct to describe that here, that the \nexpectation is that the pipeline handler is responsible to make good use \nof the hints.\n\n> \n> \n> > + */\n> > +\n> > +/**\n> > + * \\enum StreamHint::Type\n> > + * \\brief List of types of usage hints\n> > + */\n> > +\n> > +/**\n> > + * \\fn StreamHint::type()\n> > + * \\brief Retrieve the usage hint type\n> \n> Don't we usually insert a blank line between \\brief and \\return?\n\nWe do, will fix for next version. Thanks.\n\n> \n> > + * \\return The hint type\n> > + */\n> > +\n> > +/**\n> > + * \\brief Create a stream hint\n> > + * \\param[in] type Stream hint type\n> > + */\n> > +StreamHint::StreamHint(Type type)\n> > +\t: type_(type), hints_()\n> > +{\n> > +}\n> > +\n> > +/**\n> > + * \\brief Create a stream hint with parameters\n> > + * \\param[in] type Stream hint type\n> > + * \\param[in] hints Stream hint parameters\n> > + */\n> > +StreamHint::StreamHint(Type type, StreamConfiguration hints)\n> > +\t: type_(type), hints_(hints)\n> > +{\n> > +}\n> > +\n> > +/**\n> > + * \\class Viewfinder\n> > + * \\brief Stream usage hint for viewfinder\n> > + */\n> > +\n> > +/**\n> > + * \\brief Create a viewfinder stream hint\n> > + * \\param[in] width Desired view finder width\n> \n> viewfinder\n\nThanks.\n\n> \n> > + * \\param[in] height Desired view finder height\n> > + */\n> > +Viewfinder::Viewfinder(unsigned int width, unsigned int height)\n> > +\t: StreamHint(Type::Viewfinder, initHints(width, height))\n> > +{\n> > +}\n> > +\n> > +StreamConfiguration Viewfinder::initHints(unsigned int width,\n> > +\t\t\t\t\t  unsigned int height)\n> > +{\n> > +\tStreamConfiguration hints = {};\n> > +\n> > +\thints.width = width;\n> > +\thints.height = height;\n> > +\n> > +\treturn hints;\n> > +}\n> \n> Is this necessary? Couldn't you just pass width and height to the base\n> class constructor and let it assign hints_.widht and hints_.height\n> without going through copies? Or you think they would be elided by\n> RVO everywhere here?\n\nI'm not concerned about the var being copied anywhere. My rational for \nusing this is as we move forward I think these static initializer \nfunctions to be moved to StreamHints and used by other stream usage \nhint implementations.\n\n> \n> > +\n> > +/**\n> > + * \\class Video\n> > + * \\brief Stream usage hint for video\n> > + */\n> > +Video::Video()\n> > +\t: StreamHint(Type::Video)\n> > +{\n> > +}\n> > +\n> > +/**\n> > + * \\class Still\n> > + * \\brief Stream usage hint for still images\n> > + */\n> > +Still::Still()\n> > +\t: StreamHint(Type::Still)\n> > +{\n> > +}\n> > +\n> >  } /* namespace libcamera */\n> > --\n> > 2.21.0\n> >\n> > _______________________________________________\n> > libcamera-devel mailing list\n> > libcamera-devel@lists.libcamera.org\n> > https://lists.libcamera.org/listinfo/libcamera-devel","headers":{"Return-Path":"<niklas.soderlund@ragnatech.se>","Received":["from mail-lf1-x133.google.com (mail-lf1-x133.google.com\n\t[IPv6:2a00:1450:4864:20::133])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id D85EA60DB3\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue,  2 Apr 2019 14:02:16 +0200 (CEST)","by mail-lf1-x133.google.com with SMTP id u2so4282261lfd.4\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue, 02 Apr 2019 05:02:16 -0700 (PDT)","from localhost (89-233-230-99.cust.bredband2.com. [89.233.230.99])\n\tby smtp.gmail.com with ESMTPSA id\n\tr2sm2726110ljd.16.2019.04.02.05.02.15\n\t(version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256);\n\tTue, 02 Apr 2019 05:02:15 -0700 (PDT)"],"DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=ragnatech-se.20150623.gappssmtp.com; s=20150623;\n\th=date:from:to:cc:subject:message-id:references:mime-version\n\t:content-disposition:content-transfer-encoding:in-reply-to\n\t:user-agent; bh=ver5yJEM5QrtCULLnC3gKW/p1GPtEWTNSGOAeLMocnU=;\n\tb=0QX4oWiH/ooldKXL5DH1EuggCImt9V6GPLN0kyt6ZZ+TOIBcGh8sXvuPeVQzW37wWs\n\t3cL1IXOKMqU9FAQf3vB3fmQxk9xUrw5lCbuCTmJLGwBZaqTISZ0Pje89wUnnXSqWrOCo\n\tKyHnbxgGSIZKIz7oTojZG9hM8yr6JocddFKwtZpjQr5wu7wH6Czcxl+eTL00gkbNsqMm\n\tObfrgLriRGLRliy0eO34hQBqf8vQip5GRQU17XbI4syuQ2q6qZu6mQouTOu/M75e4tbI\n\taUCbY+ALcu0gnWRYjh/+dvCE6fiu15CQSIGnN+xa5gOV79ZvoiCCScMaNqw1AAt5pFYG\n\t8jZw==","X-Google-DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=1e100.net; s=20161025;\n\th=x-gm-message-state:date:from:to:cc:subject:message-id:references\n\t:mime-version:content-disposition:content-transfer-encoding\n\t:in-reply-to:user-agent;\n\tbh=ver5yJEM5QrtCULLnC3gKW/p1GPtEWTNSGOAeLMocnU=;\n\tb=clsoNphT8QMh1dQssH6l+BNUNpdPCMDG/E8ewgxmLfOVeP2zTeuBnmeMU8RW8PxtaV\n\trdwIJi5MK/kYJNEmEac+4DY4rwGN0kAko0uP3V5r9BGExOwfgYL1/uMCI0q7uXS77drd\n\t69l96ivj3Hy15c04ulwBRoKjCeiDwOIw4S2P35si2I4zfoeNYsvdcubFBIccGrwYXsIs\n\tYJEDpMZZrOCdWvktrqy/0cnlKjH+bLI/h01j0TzAUgsqt5+gEHElFOxnJnV2FQanlEjX\n\tZbeSPzS0qj7/uqfZsWmvhYFttag1L+yZX4JP7cBD3CrdrGZbKsTfw6ZdITG7H96DYYic\n\t2h2Q==","X-Gm-Message-State":"APjAAAWjRHVCXpKVrek9h4t29QbGMNc1Nxd0ZilCZoouN6+x0n1T5PCB\n\tg531fi1zR6ecA1/FqP3QDHHSwA==","X-Google-Smtp-Source":"APXvYqzXGE9vazJkJx0/q1sQ2Ce4QBE6xrmPx9Z/jSWXGY7V+uCFGpm6BBAmafEbcGdsgL8mEB5xHQ==","X-Received":"by 2002:ac2:51aa:: with SMTP id\n\tf10mr14669594lfk.82.1554206536246; \n\tTue, 02 Apr 2019 05:02:16 -0700 (PDT)","Date":"Tue, 2 Apr 2019 14:02:14 +0200","From":"Niklas =?iso-8859-1?q?S=F6derlund?= <niklas.soderlund@ragnatech.se>","To":"Jacopo Mondi <jacopo@jmondi.org>","Cc":"libcamera-devel@lists.libcamera.org","Message-ID":"<20190402120214.GW23466@bigcity.dyn.berto.se>","References":"<20190402005332.25018-1-niklas.soderlund@ragnatech.se>\n\t<20190402005332.25018-5-niklas.soderlund@ragnatech.se>\n\t<20190402075927.ekwz2rhzekdwdls3@uno.localdomain>","MIME-Version":"1.0","Content-Type":"text/plain; charset=iso-8859-1","Content-Disposition":"inline","Content-Transfer-Encoding":"8bit","In-Reply-To":"<20190402075927.ekwz2rhzekdwdls3@uno.localdomain>","User-Agent":"Mutt/1.11.3 (2019-02-01)","Subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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":"Tue, 02 Apr 2019 12:02:17 -0000"}},{"id":1208,"web_url":"https://patchwork.libcamera.org/comment/1208/","msgid":"<20190402143547.GC4805@pendragon.ideasonboard.com>","date":"2019-04-02T14:35:47","subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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 Tue, Apr 02, 2019 at 02:53:31AM +0200, Niklas Söderlund wrote:\n> In preparation of reworking how a default configuration is retrieved\n> from a camera add stream usage hints. The hints will be used by\n> applications to describe how it intends to use a camera and replace the\n> Stream IDs role when retrieving default configuration from the camera\n> using streamConfiguration().\n> \n> Signed-off-by: Niklas Söderlund <niklas.soderlund@ragnatech.se>\n> ---\n>  include/libcamera/stream.h | 39 ++++++++++++++++++\n>  src/libcamera/stream.cpp   | 84 ++++++++++++++++++++++++++++++++++++++\n>  2 files changed, 123 insertions(+)\n> \n> diff --git a/include/libcamera/stream.h b/include/libcamera/stream.h\n> index 3e8e83a2ff245879..445b80de66217934 100644\n> --- a/include/libcamera/stream.h\n> +++ b/include/libcamera/stream.h\n> @@ -35,7 +35,46 @@ private:\n>  \tStreamConfiguration configuration_;\n>  };\n>  \n> +class StreamHint\n\nShould we name this StreamUsage instead ? I'm not sure the word \"hint\"\nis a really good fit for the API, as these are more than hints. In any\ncase it would be usage hints, so I think StreamUsage is better than\nStreamHint, and StreamUsageHint seems a bit too long.\n\n> +{\n> +public:\n> +\tenum Type {\n\nMaybe Role instead or Type ?\n\n> +\t\tViewfinder,\n> +\t\tVideo,\n> +\t\tStill,\n\nYou could go for VideoRecording and StillCapture, to be a bit more\ndescriptive.\n\n> +\t};\n>  \n> +\tType type() const { return type_; }\n> +\n> +protected:\n> +\tStreamHint(Type type);\n> +\tStreamHint(Type type, StreamConfiguration hints);\n\nDoesn't this abuse the StreamConfiguration class a bit, shouldn't we use\na size (or possibly format) class ?\n\n> +\n> +private:\n> +\tType type_;\n> +\tStreamConfiguration hints_;\n> +};\n> +\n> +class Viewfinder : public StreamHint\n> +{\n> +public:\n> +\tViewfinder(unsigned int width, unsigned int height);\n> +\n> +private:\n> +\tstatic StreamConfiguration initHints(unsigned int width, unsigned int height);\n\nA bit overkill in my opinion, I don't think we need this helper.\n\n> +};\n> +\n> +class Video : public StreamHint\n> +{\n> +public:\n> +\tVideo();\n> +};\n> +\n> +class Still : public StreamHint\n> +{\n> +public:\n> +\tStill();\n> +};\n\nThose are very generic names, and may lead to namespace clashes. You\ncould isolate them in a separate namespace (possibly moving them to the\nStream class), or rename them to StreamUsageViewfinder,\nStreamUsageVideoRecording and StreamUsageStillCapture.\n\nI like this overall, but I wonder if it's really worth subclassing\nStreamHint.\n\n>  \n>  } /* namespace libcamera */\n>  \n> diff --git a/src/libcamera/stream.cpp b/src/libcamera/stream.cpp\n> index c4943c91b2e6ce13..32f26a1f8e6adb2c 100644\n> --- a/src/libcamera/stream.cpp\n> +++ b/src/libcamera/stream.cpp\n> @@ -102,4 +102,88 @@ Stream::Stream()\n>   * \\return The active configuration of the stream\n>   */\n>  \n> +/**\n> + * \\class StreamHint\n> + * \\brief Stream usage hint information\n> + *\n> + * The StreamHint class carries information about stream usage hints from the\n> + * application to a specific pipeline handler implementation. The pipeline\n> + * handler shall take the usage hints into account when select which stream\n> + * to use for the desired operation.\n> + */\n> +\n> +/**\n> + * \\enum StreamHint::Type\n> + * \\brief List of types of usage hints\n> + */\n> +\n> +/**\n> + * \\fn StreamHint::type()\n> + * \\brief Retrieve the usage hint type\n> + * \\return The hint type\n> + */\n> +\n> +/**\n> + * \\brief Create a stream hint\n> + * \\param[in] type Stream hint type\n> + */\n> +StreamHint::StreamHint(Type type)\n> +\t: type_(type), hints_()\n> +{\n> +}\n> +\n> +/**\n> + * \\brief Create a stream hint with parameters\n> + * \\param[in] type Stream hint type\n> + * \\param[in] hints Stream hint parameters\n> + */\n> +StreamHint::StreamHint(Type type, StreamConfiguration hints)\n> +\t: type_(type), hints_(hints)\n> +{\n> +}\n> +\n> +/**\n> + * \\class Viewfinder\n> + * \\brief Stream usage hint for viewfinder\n> + */\n> +\n> +/**\n> + * \\brief Create a viewfinder stream hint\n> + * \\param[in] width Desired view finder width\n> + * \\param[in] height Desired view finder height\n> + */\n> +Viewfinder::Viewfinder(unsigned int width, unsigned int height)\n> +\t: StreamHint(Type::Viewfinder, initHints(width, height))\n> +{\n> +}\n> +\n> +StreamConfiguration Viewfinder::initHints(unsigned int width,\n> +\t\t\t\t\t  unsigned int height)\n> +{\n> +\tStreamConfiguration hints = {};\n> +\n> +\thints.width = width;\n> +\thints.height = height;\n> +\n> +\treturn hints;\n> +}\n> +\n> +/**\n> + * \\class Video\n> + * \\brief Stream usage hint for video\n> + */\n> +Video::Video()\n> +\t: StreamHint(Type::Video)\n> +{\n> +}\n> +\n> +/**\n> + * \\class Still\n> + * \\brief Stream usage hint for still images\n> + */\n> +Still::Still()\n> +\t: StreamHint(Type::Still)\n> +{\n> +}\n> +\n>  } /* namespace libcamera */","headers":{"Return-Path":"<laurent.pinchart@ideasonboard.com>","Received":["from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 6B450600FB\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue,  2 Apr 2019 16:35:59 +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 D30152F9;\n\tTue,  2 Apr 2019 16:35:58 +0200 (CEST)"],"DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1554215759;\n\tbh=CW9sUR+eZrWWWa2PmrDmjtNSE+iCpg3lry+CxdnA5hI=;\n\th=Date:From:To:Cc:Subject:References:In-Reply-To:From;\n\tb=AtjFVxT6Ha0kzh9K70vwFGWYHZZy1v60hxZFr6flxcs9rkl01SdJcZy0mIkhooxuu\n\tPhlNV4tAwMfhXxte4CDByADF5cgLZF2fyCk+8wsL1XrAyFS9P/FPIRMVo63Iju5RcN\n\tyzJff9FyNSF/yRKZUN45nNaiD/rDn+SRnWlF7pK4=","Date":"Tue, 2 Apr 2019 17:35:47 +0300","From":"Laurent Pinchart <laurent.pinchart@ideasonboard.com>","To":"Niklas =?utf-8?q?S=C3=B6derlund?= <niklas.soderlund@ragnatech.se>","Cc":"libcamera-devel@lists.libcamera.org","Message-ID":"<20190402143547.GC4805@pendragon.ideasonboard.com>","References":"<20190402005332.25018-1-niklas.soderlund@ragnatech.se>\n\t<20190402005332.25018-5-niklas.soderlund@ragnatech.se>","MIME-Version":"1.0","Content-Type":"text/plain; charset=utf-8","Content-Disposition":"inline","Content-Transfer-Encoding":"8bit","In-Reply-To":"<20190402005332.25018-5-niklas.soderlund@ragnatech.se>","User-Agent":"Mutt/1.10.1 (2018-07-13)","Subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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":"Tue, 02 Apr 2019 14:35:59 -0000"}},{"id":1209,"web_url":"https://patchwork.libcamera.org/comment/1209/","msgid":"<20190402144205.GD4805@pendragon.ideasonboard.com>","date":"2019-04-02T14:42:05","subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","submitter":{"id":2,"url":"https://patchwork.libcamera.org/api/people/2/","name":"Laurent Pinchart","email":"laurent.pinchart@ideasonboard.com"},"content":"Hello,\n\nOn Tue, Apr 02, 2019 at 02:02:14PM +0200, Niklas Söderlund wrote:\n> On 2019-04-02 09:59:27 +0200, Jacopo Mondi wrote:\n> > On Tue, Apr 02, 2019 at 02:53:31AM +0200, Niklas Söderlund wrote:\n> >> In preparation of reworking how a default configuration is retrieved\n> >> from a camera add stream usage hints. The hints will be used by\n> >> applications to describe how it intends to use a camera and replace the\n> >> Stream IDs role when retrieving default configuration from the camera\n> >> using streamConfiguration().\n> >>\n> >> Signed-off-by: Niklas Söderlund <niklas.soderlund@ragnatech.se>\n> >> ---\n> >>  include/libcamera/stream.h | 39 ++++++++++++++++++\n> >>  src/libcamera/stream.cpp   | 84 ++++++++++++++++++++++++++++++++++++++\n> >>  2 files changed, 123 insertions(+)\n> >>\n> >> diff --git a/include/libcamera/stream.h b/include/libcamera/stream.h\n> >> index 3e8e83a2ff245879..445b80de66217934 100644\n> >> --- a/include/libcamera/stream.h\n> >> +++ b/include/libcamera/stream.h\n> >> @@ -35,7 +35,46 @@ private:\n> >>  \tStreamConfiguration configuration_;\n> >>  };\n> >>\n> >> +class StreamHint\n> >> +{\n> >> +public:\n> >> +\tenum Type {\n> >> +\t\tViewfinder,\n> >> +\t\tVideo,\n> >> +\t\tStill,\n> > \n> > I would use all capitals, and lengthen 'video' and 'still' as\n> > STILL_CAPTURE and VIDEO_CAPTURE\n> \n> I don't agree I think it's better as is :-) As this is bike shedding \n> territory I will yield to popular opinion. What to the rest of you \n> think?\n\nAll our enums use CamelCase.\n\n> > \n> >> +\t};\n> >>\n> >> +\tType type() const { return type_; }\n> > \n> > const Type &\n> \n> Thanks.\n\nA bit overkill as Type is just an integer...\n\n> >> +\n> >> +protected:\n> >> +\tStreamHint(Type type);\n> >> +\tStreamHint(Type type, StreamConfiguration hints);\n> > \n> > &hints\n> \n> Thanks, will make this a const &.\n\nNot overkill at all :-)\n\n> >> +\n> >> +private:\n> >> +\tType type_;\n> >> +\tStreamConfiguration hints_;\n> > \n> > I would call the configuration descriptor of an hint 'config_' not\n> > 'hints_'.\n> \n> I tried that at first but it gave me a bad feeling as it's in fact not a \n> configuration it's a hint of the configuration the user wish to use. I \n> will keep this as hints_ for now.\n> \n> I'm not even sure the type should be StreamConfiguration or if we should \n> inline the variables we judge to be useful as hints. As we have no \n> pipelines yet to experiment with making use of the hints I picked \n> something to store the user provided hints in. Also note that there is \n> currently no way for a pipeline handler to get hold of the content of \n> hints_. This is by design to force me to do something here when we join \n> this work with the stream properties :-)\n> \n> >> +};\n> >> +\n> >> +class Viewfinder : public StreamHint\n> >> +{\n> >> +public:\n> >> +\tViewfinder(unsigned int width, unsigned int height);\n> >> +\n> >> +private:\n> >> +\tstatic StreamConfiguration initHints(unsigned int width, unsigned int height);\n> >> +};\n> >> +\n> >> +class Video : public StreamHint\n> >> +{\n> >> +public:\n> >> +\tVideo();\n> >> +};\n> >> +\n> >> +class Still : public StreamHint\n> >> +{\n> >> +public:\n> >> +\tStill();\n> >> +};\n> > \n> > I would question if these hierarchy brings any benefit or it just\n> > makes more complex adding new use cases.\n> \n> I don't think we will add use cases all that much. The main reason I \n> went with this design is to make it easier for applications to use the \n> interface.\n> \n>     foo->streamConfiguration({ Viewfinder(640,480), Still() });\n\nI pondered the same as Jacopo, but reading this feels quite nice...\n\n> Is quiet nice to use instead of having to create raw StreamHint objects \n> and configure them. It also gives us a bit more of control, with this \n> design we can force any hint for a Viewfinder to supply a hint for the \n> resolution while if we allowed raw StreamHint creation pipeline handers \n> would need to be prepared to handle them both with and without that \n> information.\n\nYou're right, in the end the API is less error-prone. We may end up\nreconsidering this though, if the stream usages require more flexibility\nthan what could easily be handled through parameters to the\nconstructors.\n\n> I expect his area will change a lot as we move forward, both based on \n> needs from applications and implementations in pipeline handlers. In \n> this RFC I have only parameterized the viewfinder hint as it's quiet \n> clear dimensions would be part of its hints. I expect Video and Still to \n> be parameterized in the near future.\n> \n> > As I immagined this, use case hints might just be an enumeration with\n> > a configuration associated, ie. I don't think only viewfinder should\n> > have associated sizes, but it should still be possible to specify a\n> > max sizes for the other streams to make sure the selected streams\n> > could provide that resolution. Furthermore the base class has a\n> > configuration field, but it is only accessible for the viewfinder use\n> > case, why that?\n> > \n> >>\n> >>  } /* namespace libcamera */\n> >>\n> >> diff --git a/src/libcamera/stream.cpp b/src/libcamera/stream.cpp\n> >> index c4943c91b2e6ce13..32f26a1f8e6adb2c 100644\n> >> --- a/src/libcamera/stream.cpp\n> >> +++ b/src/libcamera/stream.cpp\n> >> @@ -102,4 +102,88 @@ Stream::Stream()\n> >>   * \\return The active configuration of the stream\n> >>   */\n> >>\n> >> +/**\n> >> + * \\class StreamHint\n> >> + * \\brief Stream usage hint information\n> >> + *\n> >> + * The StreamHint class carries information about stream usage hints from the\n> >> + * application to a specific pipeline handler implementation. The pipeline\n> >> + * handler shall take the usage hints into account when select which stream\n> >> + * to use for the desired operation.\n> > \n> > I would mention Camera not pipeline handlers here, as the interface\n> > for applications using hints will be the Camera class.\n> \n> The Camera don't make use of the hints it only forwards them to the \n> pipeline handler. I think it's correct to describe that here, that the \n> expectation is that the pipeline handler is responsible to make good use \n> of the hints.\n\nNote that usage hints are public API, while pipeline handlers are purely\ninternal. I'm with Jacopo on this one, I wouldn't mention pipeline\nhandlers in the documentation of public classes.\n\n> >> + */\n> >> +\n> >> +/**\n> >> + * \\enum StreamHint::Type\n> >> + * \\brief List of types of usage hints\n> >> + */\n> >> +\n> >> +/**\n> >> + * \\fn StreamHint::type()\n> >> + * \\brief Retrieve the usage hint type\n> > \n> > Don't we usually insert a blank line between \\brief and \\return?\n> \n> We do, will fix for next version. Thanks.\n> \n> >> + * \\return The hint type\n> >> + */\n> >> +\n> >> +/**\n> >> + * \\brief Create a stream hint\n> >> + * \\param[in] type Stream hint type\n> >> + */\n> >> +StreamHint::StreamHint(Type type)\n> >> +\t: type_(type), hints_()\n> >> +{\n> >> +}\n> >> +\n> >> +/**\n> >> + * \\brief Create a stream hint with parameters\n> >> + * \\param[in] type Stream hint type\n> >> + * \\param[in] hints Stream hint parameters\n> >> + */\n> >> +StreamHint::StreamHint(Type type, StreamConfiguration hints)\n> >> +\t: type_(type), hints_(hints)\n> >> +{\n> >> +}\n> >> +\n> >> +/**\n> >> + * \\class Viewfinder\n> >> + * \\brief Stream usage hint for viewfinder\n> >> + */\n> >> +\n> >> +/**\n> >> + * \\brief Create a viewfinder stream hint\n> >> + * \\param[in] width Desired view finder width\n> > \n> > viewfinder\n> \n> Thanks.\n> \n> >> + * \\param[in] height Desired view finder height\n> >> + */\n> >> +Viewfinder::Viewfinder(unsigned int width, unsigned int height)\n> >> +\t: StreamHint(Type::Viewfinder, initHints(width, height))\n> >> +{\n> >> +}\n> >> +\n> >> +StreamConfiguration Viewfinder::initHints(unsigned int width,\n> >> +\t\t\t\t\t  unsigned int height)\n> >> +{\n> >> +\tStreamConfiguration hints = {};\n> >> +\n> >> +\thints.width = width;\n> >> +\thints.height = height;\n> >> +\n> >> +\treturn hints;\n> >> +}\n> > \n> > Is this necessary? Couldn't you just pass width and height to the base\n> > class constructor and let it assign hints_.widht and hints_.height\n> > without going through copies? Or you think they would be elided by\n> > RVO everywhere here?\n> \n> I'm not concerned about the var being copied anywhere. My rational for \n> using this is as we move forward I think these static initializer \n> functions to be moved to StreamHints and used by other stream usage \n> hint implementations.\n> \n> >> +\n> >> +/**\n> >> + * \\class Video\n> >> + * \\brief Stream usage hint for video\n> >> + */\n> >> +Video::Video()\n> >> +\t: StreamHint(Type::Video)\n> >> +{\n> >> +}\n> >> +\n> >> +/**\n> >> + * \\class Still\n> >> + * \\brief Stream usage hint for still images\n> >> + */\n> >> +Still::Still()\n> >> +\t: StreamHint(Type::Still)\n> >> +{\n> >> +}\n> >> +\n> >>  } /* namespace libcamera */","headers":{"Return-Path":"<laurent.pinchart@ideasonboard.com>","Received":["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 2F9D3600FB\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue,  2 Apr 2019 16:42:16 +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 928822F9;\n\tTue,  2 Apr 2019 16:42:15 +0200 (CEST)"],"DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1554216135;\n\tbh=w56fYV7z7t8RwOJouvi4eeTjA7ZqzFbQpoOnwODf2us=;\n\th=Date:From:To:Cc:Subject:References:In-Reply-To:From;\n\tb=LQqx9mheWOLyRrKMBiLQqI2okPFi4mIwgJLOevCh8V2SP3nUrWD4VnQUlZqUJGbtj\n\tGO52ghVMF8YoXuXhf30PEfMP9C3eq4houMVfXVCOwdtE60RCnmhqDsUx4q0VNLIWgv\n\tZOAOvDMmoKRBiUf5sIevW+KPpEms5BX48NW0TRfs=","Date":"Tue, 2 Apr 2019 17:42:05 +0300","From":"Laurent Pinchart <laurent.pinchart@ideasonboard.com>","To":"Niklas =?utf-8?q?S=C3=B6derlund?= <niklas.soderlund@ragnatech.se>","Cc":"Jacopo Mondi <jacopo@jmondi.org>, libcamera-devel@lists.libcamera.org","Message-ID":"<20190402144205.GD4805@pendragon.ideasonboard.com>","References":"<20190402005332.25018-1-niklas.soderlund@ragnatech.se>\n\t<20190402005332.25018-5-niklas.soderlund@ragnatech.se>\n\t<20190402075927.ekwz2rhzekdwdls3@uno.localdomain>\n\t<20190402120214.GW23466@bigcity.dyn.berto.se>","MIME-Version":"1.0","Content-Type":"text/plain; charset=utf-8","Content-Disposition":"inline","Content-Transfer-Encoding":"8bit","In-Reply-To":"<20190402120214.GW23466@bigcity.dyn.berto.se>","User-Agent":"Mutt/1.10.1 (2018-07-13)","Subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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":"Tue, 02 Apr 2019 14:42:16 -0000"}},{"id":1232,"web_url":"https://patchwork.libcamera.org/comment/1232/","msgid":"<20190402234015.GA3588@bigcity.dyn.berto.se>","date":"2019-04-02T23:40:15","subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","submitter":{"id":5,"url":"https://patchwork.libcamera.org/api/people/5/","name":"Niklas Söderlund","email":"niklas.soderlund@ragnatech.se"},"content":"Hi Laurent,\n\nThanks for your feedback.\n\nOn 2019-04-02 17:35:47 +0300, Laurent Pinchart wrote:\n> > +};\n> > +\n> > +class Video : public StreamHint\n> > +{\n> > +public:\n> > +\tVideo();\n> > +};\n> > +\n> > +class Still : public StreamHint\n> > +{\n> > +public:\n> > +\tStill();\n> > +};\n> \n> Those are very generic names, and may lead to namespace clashes. You\n> could isolate them in a separate namespace (possibly moving them to the\n> Stream class), or rename them to StreamUsageViewfinder,\n> StreamUsageVideoRecording and StreamUsageStillCapture.\n\nI wrestled a lot with how to best handle this, for next version I went \nwith moving the subclasses inside Stream class as it seems create then \nnicest interface for applications to use. Lets see how it works out.","headers":{"Return-Path":"<niklas.soderlund@ragnatech.se>","Received":["from mail-lf1-x12b.google.com (mail-lf1-x12b.google.com\n\t[IPv6:2a00:1450:4864:20::12b])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id 119AF610B3\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tWed,  3 Apr 2019 01:40:18 +0200 (CEST)","by mail-lf1-x12b.google.com with SMTP id y18so10296673lfe.1\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tTue, 02 Apr 2019 16:40:17 -0700 (PDT)","from localhost (89-233-230-99.cust.bredband2.com. [89.233.230.99])\n\tby smtp.gmail.com with ESMTPSA id\n\tm1sm2902528lfh.36.2019.04.02.16.40.15\n\t(version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256);\n\tTue, 02 Apr 2019 16:40:16 -0700 (PDT)"],"DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=ragnatech-se.20150623.gappssmtp.com; s=20150623;\n\th=date:from:to:cc:subject:message-id:references:mime-version\n\t:content-disposition:content-transfer-encoding:in-reply-to\n\t:user-agent; bh=+C9waErxGXNxvFu0ONOmbZpoihVXibfEWlOmG4zh/pU=;\n\tb=N+kC6H4ra5BhTYMfAog4oos84kxgcGHSCIX1z1Tu0Lf/hYnoNLXPkIE8TI5psy1HcQ\n\tMVsphDhrAqzMFo+1vx54JxKfMqAwvCtv4pMoHdcZOCEojN/eZSJ75c9+2yD/2qHy3XPz\n\tEvm93TaAh8r4krK6ZLOi40EHS1AEqQAOOvG3WJ7JYt9Cww+5njt8eFCQ5cfQbg1bwtVB\n\t2CVDwnEmumKwzmtqT4wUtgGps/XOX4DjkUmUmTNrAMxjKTPDM+ngoTYrHGsQWOov8FX0\n\tok0Et/u/MJe3DZ45Zu0a1KtIpSiSeykBWU27GgSTMBvYiG8CKjevKV6yc33XDInKeo5H\n\tTUsA==","X-Google-DKIM-Signature":"v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=1e100.net; s=20161025;\n\th=x-gm-message-state:date:from:to:cc:subject:message-id:references\n\t:mime-version:content-disposition:content-transfer-encoding\n\t:in-reply-to:user-agent;\n\tbh=+C9waErxGXNxvFu0ONOmbZpoihVXibfEWlOmG4zh/pU=;\n\tb=nH979FUtjMiMJxRUQG3NL4zMGCLv+cJWc/W+osL9WW1kpwnm1txQc2xE8qw+kus+Wm\n\tUyoM21cIaJngo0Mot0W/YcnrGQjKI4dY2P1tCa2wR8563BZ6wXa+SfH5L/h9IcXxG72M\n\tddESkFaGD/476yOZZOvhJsGOeaq3xtllY2yPZvp7n+cW9gchr1A5FV8coUwOccalHcCe\n\tiaKOIC2ZxPIQ74Qs85qXzZ2jCTAyzrTATXNLj7FTL1JLPsHG1KmwH/7mnJgjenS76sms\n\tF2TAMnWtBZZYYzpQMGYnDjt78G/BQXLJOpJfgTwvjnIeBVkyiSB67nZkOsw3ZCmimPV3\n\tZMVg==","X-Gm-Message-State":"APjAAAW0gKJeDbtV7KL/UgZwh3Ei99MeLneVX1VOJ6vStrzopKc9RMAh\n\tYeXW6B2z8dwZFMV63GuTskahHg==","X-Google-Smtp-Source":"APXvYqz48WS8JkpCqBTJsP5V9GNjyDVooleOhI2FEtAkEtaNn/W+OB9VqnYXV1/7aoZzjvCWX/bkRA==","X-Received":"by 2002:a19:ca02:: with SMTP id a2mr37391096lfg.88.1554248417319;\n\tTue, 02 Apr 2019 16:40:17 -0700 (PDT)","Date":"Wed, 3 Apr 2019 01:40:15 +0200","From":"Niklas =?iso-8859-1?q?S=F6derlund?= <niklas.soderlund@ragnatech.se>","To":"Laurent Pinchart <laurent.pinchart@ideasonboard.com>","Cc":"libcamera-devel@lists.libcamera.org","Message-ID":"<20190402234015.GA3588@bigcity.dyn.berto.se>","References":"<20190402005332.25018-1-niklas.soderlund@ragnatech.se>\n\t<20190402005332.25018-5-niklas.soderlund@ragnatech.se>\n\t<20190402143547.GC4805@pendragon.ideasonboard.com>","MIME-Version":"1.0","Content-Type":"text/plain; charset=iso-8859-1","Content-Disposition":"inline","Content-Transfer-Encoding":"8bit","In-Reply-To":"<20190402143547.GC4805@pendragon.ideasonboard.com>","User-Agent":"Mutt/1.11.3 (2019-02-01)","Subject":"Re: [libcamera-devel] [RFC 4/5] libcamera: stream: Add basic stream\n\tusage hints definitions","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":"Tue, 02 Apr 2019 23:40:18 -0000"}}]