{"id":17614,"url":"https://patchwork.libcamera.org/api/patches/17614/?format=json","web_url":"https://patchwork.libcamera.org/patch/17614/","project":{"id":1,"url":"https://patchwork.libcamera.org/api/projects/1/?format=json","name":"libcamera","link_name":"libcamera","list_id":"libcamera_core","list_email":"libcamera-devel@lists.libcamera.org","web_url":"","scm_url":"","webscm_url":""},"msgid":"<20221017171741.3803909-3-paul.elder@ideasonboard.com>","date":"2022-10-17T17:17:40","name":"[libcamera-devel,2/3] cam: file_sink: Add support for DNG output","commit_ref":null,"pull_url":null,"state":"accepted","archived":false,"hash":"68dfb329c0d1b70e8b9f2983fae9c9b34b9a3781","submitter":{"id":17,"url":"https://patchwork.libcamera.org/api/people/17/?format=json","name":"Paul Elder","email":"paul.elder@ideasonboard.com"},"delegate":null,"mbox":"https://patchwork.libcamera.org/patch/17614/mbox/","series":[{"id":3559,"url":"https://patchwork.libcamera.org/api/series/3559/?format=json","web_url":"https://patchwork.libcamera.org/project/libcamera/list/?series=3559","date":"2022-10-17T17:17:38","name":"cam: Add DNG support","version":1,"mbox":"https://patchwork.libcamera.org/series/3559/mbox/"}],"comments":"https://patchwork.libcamera.org/api/patches/17614/comments/","check":"pending","checks":"https://patchwork.libcamera.org/api/patches/17614/checks/","tags":{},"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 C8B11BD16B\n\tfor <parsemail@patchwork.libcamera.org>;\n\tMon, 17 Oct 2022 17:18:01 +0000 (UTC)","from lancelot.ideasonboard.com (localhost [IPv6:::1])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTP id 7BE2262E0B;\n\tMon, 17 Oct 2022 19:18:01 +0200 (CEST)","from perceval.ideasonboard.com (perceval.ideasonboard.com\n\t[213.167.242.64])\n\tby lancelot.ideasonboard.com (Postfix) with ESMTPS id AAEF562DEE\n\tfor <libcamera-devel@lists.libcamera.org>;\n\tMon, 17 Oct 2022 19:17:57 +0200 (CEST)","from pyrite.rasen.tech (h175-177-042-159.catv02.itscom.jp\n\t[175.177.42.159])\n\tby perceval.ideasonboard.com (Postfix) with ESMTPSA id 3BF0BCCF;\n\tMon, 17 Oct 2022 19:17:55 +0200 (CEST)"],"DKIM-Signature":["v=1; a=rsa-sha256; c=relaxed/simple; d=libcamera.org;\n\ts=mail; t=1666027081;\n\tbh=OB8Nx/5WhI+4P+Q7brDY0+UAXS+POsdPKzTcvVI9/kU=;\n\th=To:Date:In-Reply-To:References:Subject:List-Id:List-Unsubscribe:\n\tList-Archive:List-Post:List-Help:List-Subscribe:From:Reply-To:\n\tFrom;\n\tb=2HuRobIt27rBsyCtBfedcP3YLYJBIN/NN4XxqzkVPwP4NC7AnmOy0pCBdyzL9DjeW\n\tqRJjmKYyfR+K76FRPLH8S7rb3pm0MOu1EvLE7XX226pe/VipNXsKD2xxSxXcKYu8aa\n\tYkaf5Db1xnGtEhyCNjE/rVuTXRRyWd5jQYRaAjunvr1j0p5nzVEWVvez28QwkzdLNC\n\tjVo/5tfaLlozcWLltZXtKSDC2Dzj+Sbt5Rvb2n63V5lhMxsofEfJ8mjfSAw3uGbmMK\n\tB/zcGzpgsyIzpmmaSGgbeVljqZNU5ieESTn8l+0biDfnD0ldai3NKBKkKZtaK4AooG\n\tI3YeILQGlpMJA==","v=1; a=rsa-sha256; c=relaxed/simple; d=ideasonboard.com;\n\ts=mail; t=1666027077;\n\tbh=OB8Nx/5WhI+4P+Q7brDY0+UAXS+POsdPKzTcvVI9/kU=;\n\th=From:To:Cc:Subject:Date:In-Reply-To:References:From;\n\tb=Xi7dNPm54MDa/00mYhyKkQnGxUSQjy1J3X+v6qOHwPGbyXEwH+lJArSyyHxMeN5XV\n\tL4JlzUZKoHHdWp0Qpo/0An+GngE2s2KCI/3rWHp8QHTG3vluyYVByPKLtsTu+/1YAY\n\tGlUusnFIF4MmJz0Lo2d8HJW59zB4gOCsCWl+zJSs="],"Authentication-Results":"lancelot.ideasonboard.com; dkim=pass (1024-bit key; \n\tunprotected) header.d=ideasonboard.com\n\theader.i=@ideasonboard.com\n\theader.b=\"Xi7dNPm5\"; dkim-atps=neutral","To":"libcamera-devel@lists.libcamera.org","Date":"Tue, 18 Oct 2022 02:17:40 +0900","Message-Id":"<20221017171741.3803909-3-paul.elder@ideasonboard.com>","X-Mailer":"git-send-email 2.30.2","In-Reply-To":"<20221017171741.3803909-1-paul.elder@ideasonboard.com>","References":"<20221017171741.3803909-1-paul.elder@ideasonboard.com>","MIME-Version":"1.0","Content-Transfer-Encoding":"8bit","Subject":"[libcamera-devel] [PATCH 2/3] cam: file_sink: Add support for DNG\n\toutput","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>","From":"Paul Elder via libcamera-devel <libcamera-devel@lists.libcamera.org>","Reply-To":"Paul Elder <paul.elder@ideasonboard.com>","Errors-To":"libcamera-devel-bounces@lists.libcamera.org","Sender":"\"libcamera-devel\" <libcamera-devel-bounces@lists.libcamera.org>"},"content":"Add support for outputting buffers in DNG format. It reuses the DNG\nwriter that we had previously in qcam.\n\nSigned-off-by: Paul Elder <paul.elder@ideasonboard.com>\n---\n src/cam/camera_session.cpp |  3 ++-\n src/cam/file_sink.cpp      | 31 +++++++++++++++++++++++++------\n src/cam/file_sink.h        |  7 +++++--\n 3 files changed, 32 insertions(+), 9 deletions(-)","diff":"diff --git a/src/cam/camera_session.cpp b/src/cam/camera_session.cpp\nindex 238186a3..2557f32d 100644\n--- a/src/cam/camera_session.cpp\n+++ b/src/cam/camera_session.cpp\n@@ -208,7 +208,8 @@ int CameraSession::start()\n \tif (options_.isSet(OptFile)) {\n \t\tif (!options_[OptFile].toString().empty())\n \t\t\tsink_ = std::make_unique<FileSink>(streamNames_,\n-\t\t\t\t\t\t\t   options_[OptFile]);\n+\t\t\t\t\t\t\t   options_[OptFile],\n+\t\t\t\t\t\t\t   camera_.get());\n \t\telse\n \t\t\tsink_ = std::make_unique<FileSink>(streamNames_);\n \t}\ndiff --git a/src/cam/file_sink.cpp b/src/cam/file_sink.cpp\nindex 45213d4a..fabf163c 100644\n--- a/src/cam/file_sink.cpp\n+++ b/src/cam/file_sink.cpp\n@@ -15,14 +15,15 @@\n \n #include <libcamera/camera.h>\n \n+#include \"dng_writer.h\"\n #include \"file_sink.h\"\n #include \"image.h\"\n \n using namespace libcamera;\n \n FileSink::FileSink(const std::map<const libcamera::Stream *, std::string> &streamNames,\n-\t\t   const std::string &pattern)\n-\t: streamNames_(streamNames), pattern_(pattern)\n+\t\t   const std::string &pattern, const libcamera::Camera *camera)\n+\t: streamNames_(streamNames), pattern_(pattern), camera_(camera)\n {\n }\n \n@@ -51,12 +52,13 @@ void FileSink::mapBuffer(FrameBuffer *buffer)\n bool FileSink::processRequest(Request *request)\n {\n \tfor (auto [stream, buffer] : request->buffers())\n-\t\twriteBuffer(stream, buffer);\n+\t\twriteBuffer(stream, buffer, request->metadata());\n \n \treturn true;\n }\n \n-void FileSink::writeBuffer(const Stream *stream, FrameBuffer *buffer)\n+void FileSink::writeBuffer(const Stream *stream, FrameBuffer *buffer,\n+\t\t\t   [[maybe_unused]] const ControlList &metadata)\n {\n \tstd::string filename;\n \tsize_t pos;\n@@ -65,6 +67,10 @@ void FileSink::writeBuffer(const Stream *stream, FrameBuffer *buffer)\n \tif (!pattern_.empty())\n \t\tfilename = pattern_;\n \n+#ifdef HAVE_TIFF\n+\tbool dng = filename.find(\".dng\", filename.size() - 4) != std::string::npos;\n+#endif /* HAVE_TIFF */\n+\n \tif (filename.empty() || filename.back() == '/')\n \t\tfilename += \"frame-#.bin\";\n \n@@ -76,6 +82,21 @@ void FileSink::writeBuffer(const Stream *stream, FrameBuffer *buffer)\n \t\tfilename.replace(pos, 1, ss.str());\n \t}\n \n+\tImage *image = mappedBuffers_[buffer].get();\n+\n+#ifdef HAVE_TIFF\n+\tif (dng) {\n+\t\tret = DNGWriter::write(filename.c_str(), camera_,\n+\t\t\t\t       stream->configuration(), metadata,\n+\t\t\t\t       buffer, image->data(0).data());\n+\t\tif (ret < 0)\n+\t\t\tstd::cerr << \"failed to write DNG \" << filename\n+\t\t\t\t  << std::endl;\n+\n+\t\treturn;\n+\t}\n+#endif /* HAVE_TIFF */\n+\n \tfd = open(filename.c_str(), O_CREAT | O_WRONLY |\n \t\t  (pos == std::string::npos ? O_APPEND : O_TRUNC),\n \t\t  S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH | S_IWOTH);\n@@ -86,8 +107,6 @@ void FileSink::writeBuffer(const Stream *stream, FrameBuffer *buffer)\n \t\treturn;\n \t}\n \n-\tImage *image = mappedBuffers_[buffer].get();\n-\n \tfor (unsigned int i = 0; i < buffer->planes().size(); ++i) {\n \t\tconst FrameMetadata::Plane &meta = buffer->metadata().planes()[i];\n \ndiff --git a/src/cam/file_sink.h b/src/cam/file_sink.h\nindex 067736f5..e4838b37 100644\n--- a/src/cam/file_sink.h\n+++ b/src/cam/file_sink.h\n@@ -21,7 +21,7 @@ class FileSink : public FrameSink\n {\n public:\n \tFileSink(const std::map<const libcamera::Stream *, std::string> &streamNames,\n-\t\t const std::string &pattern = \"\");\n+\t\t const std::string &pattern = \"\", const libcamera::Camera *camera = nullptr);\n \t~FileSink();\n \n \tint configure(const libcamera::CameraConfiguration &config) override;\n@@ -32,9 +32,12 @@ public:\n \n private:\n \tvoid writeBuffer(const libcamera::Stream *stream,\n-\t\t\t libcamera::FrameBuffer *buffer);\n+\t\t\t libcamera::FrameBuffer *buffer,\n+\t\t\t const libcamera::ControlList &metadata);\n \n \tstd::map<const libcamera::Stream *, std::string> streamNames_;\n \tstd::string pattern_;\n \tstd::map<libcamera::FrameBuffer *, std::unique_ptr<Image>> mappedBuffers_;\n+\n+\tconst libcamera::Camera *camera_;\n };\n","prefixes":["libcamera-devel","2/3"]}