diff options
author | Naushir Patuck <naush@raspberrypi.com> | 2023-01-27 15:43:14 +0000 |
---|---|---|
committer | Kieran Bingham <kieran.bingham@ideasonboard.com> | 2023-01-31 16:54:36 +0000 |
commit | 8c53b2498bbebde229920e7994feab76a0018c2b (patch) | |
tree | ceac6dda68b68cddd8bfba0d81574f6eac2c9565 | |
parent | 8b267c24a017e0fd81cd3fd1b9d439d76373d096 (diff) |
pipeline: raspberrypi: Read config parameters from a file
Add the ability to read the platform configuration parameters from a
config file provided by the user through the LIBCAMERA_RPI_CONFIG_FILE
environment variable. Use the PipelineHandler::configurationFile()
helper to determine the full path of the file.
Provide an example configuration file named example.yaml. Currently two
parameters are available through the json file:
"min_unicam_buffers" The minimum number of internal Unicam buffers to
allocate.
"min_total_unicam_buffers" The minimum number of internal + external
Unicam buffers that must be allocated.
Signed-off-by: Naushir Patuck <naush@raspberrypi.com>
Reviewed-by: David Plowman <david.plowman@raspberrypi.com>
Signed-off-by: Kieran Bingham <kieran.bingham@ideasonboard.com>
-rw-r--r-- | Documentation/environment_variables.rst | 5 | ||||
-rw-r--r-- | src/libcamera/pipeline/raspberrypi/data/example.yaml | 32 | ||||
-rw-r--r-- | src/libcamera/pipeline/raspberrypi/data/meson.build | 8 | ||||
-rw-r--r-- | src/libcamera/pipeline/raspberrypi/meson.build | 2 | ||||
-rw-r--r-- | src/libcamera/pipeline/raspberrypi/raspberrypi.cpp | 45 |
5 files changed, 92 insertions, 0 deletions
diff --git a/Documentation/environment_variables.rst b/Documentation/environment_variables.rst index f092cbbd..ceeb251a 100644 --- a/Documentation/environment_variables.rst +++ b/Documentation/environment_variables.rst @@ -37,6 +37,11 @@ LIBCAMERA_IPA_MODULE_PATH Example value: ``${HOME}/.libcamera/lib:/opt/libcamera/vendor/lib`` +LIBCAMERA_RPI_CONFIG_FILE + Define a custom configuration file to use in the Raspberry Pi pipeline handler. + + Example value: ``/usr/local/share/libcamera/pipeline/raspberrypi/minimal_mem.yaml`` + Further details --------------- diff --git a/src/libcamera/pipeline/raspberrypi/data/example.yaml b/src/libcamera/pipeline/raspberrypi/data/example.yaml new file mode 100644 index 00000000..4662136e --- /dev/null +++ b/src/libcamera/pipeline/raspberrypi/data/example.yaml @@ -0,0 +1,32 @@ +{ + "version": 1.0, + "target": "bcm2835", + + "pipeline_handler": + { + # The minimum number of internal buffers to be allocated for + # Unicam. This value must be greater than 0, but less than or + # equal to min_total_unicam_buffers. + # + # A larger number of internal buffers can reduce the occurrence + # of frame drops during high CPU loads, but might also cause + # additional latency in the system. + # + # Note that the pipeline handler might override this value and + # not allocate any internal buffers if it knows they will never + # be used. For example if the RAW stream is marked as mandatory + # and there are no dropped frames signalled for algorithm + # convergence. + # + # "min_unicam_buffers": 2, + + # The minimum total (internal + external) buffer count used for + # Unicam. The number of internal buffers allocated for Unicam is + # given by: + # + # internal buffer count = max(min_unicam_buffers, + # min_total_unicam_buffers - external buffer count) + # + # "min_total_unicam_buffers": 4 + } +} diff --git a/src/libcamera/pipeline/raspberrypi/data/meson.build b/src/libcamera/pipeline/raspberrypi/data/meson.build new file mode 100644 index 00000000..1c70433b --- /dev/null +++ b/src/libcamera/pipeline/raspberrypi/data/meson.build @@ -0,0 +1,8 @@ +# SPDX-License-Identifier: CC0-1.0 + +conf_files = files([ + 'example.yaml', +]) + +install_data(conf_files, + install_dir : pipeline_data_dir / 'raspberrypi') diff --git a/src/libcamera/pipeline/raspberrypi/meson.build b/src/libcamera/pipeline/raspberrypi/meson.build index 6064a3f0..59e8fb18 100644 --- a/src/libcamera/pipeline/raspberrypi/meson.build +++ b/src/libcamera/pipeline/raspberrypi/meson.build @@ -6,3 +6,5 @@ libcamera_sources += files([ 'raspberrypi.cpp', 'rpi_stream.cpp', ]) + +subdir('data') diff --git a/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp b/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp index 0a9ef66f..a140ff73 100644 --- a/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp +++ b/src/libcamera/pipeline/raspberrypi/raspberrypi.cpp @@ -14,6 +14,7 @@ #include <unordered_set> #include <utility> +#include <libcamera/base/file.h> #include <libcamera/base/shared_fd.h> #include <libcamera/base/utils.h> @@ -40,6 +41,7 @@ #include "libcamera/internal/media_device.h" #include "libcamera/internal/pipeline_handler.h" #include "libcamera/internal/v4l2_videodevice.h" +#include "libcamera/internal/yaml_parser.h" #include "delayed_controls.h" #include "dma_heaps.h" @@ -1214,6 +1216,7 @@ int PipelineHandlerRPi::queueRequestDevice(Camera *camera, Request *request) */ stream->setExternalBuffer(buffer); } + /* * If no buffer is provided by the request for this stream, we * queue a nullptr to the stream to signify that it must use an @@ -1718,6 +1721,48 @@ int RPiCameraData::loadPipelineConfiguration() .minTotalUnicamBuffers = 4, }; + char const *configFromEnv = utils::secure_getenv("LIBCAMERA_RPI_CONFIG_FILE"); + if (!configFromEnv || *configFromEnv == '\0') + return 0; + + std::string filename = std::string(configFromEnv); + File file(filename); + + if (!file.open(File::OpenModeFlag::ReadOnly)) { + LOG(RPI, Error) << "Failed to open configuration file '" << filename << "'"; + return -EIO; + } + + LOG(RPI, Info) << "Using configuration file '" << filename << "'"; + + std::unique_ptr<YamlObject> root = YamlParser::parse(file); + if (!root) { + LOG(RPI, Warning) << "Failed to parse configuration file, using defaults"; + return 0; + } + + std::optional<double> ver = (*root)["version"].get<double>(); + if (!ver || *ver != 1.0) { + LOG(RPI, Error) << "Unexpected configuration file version reported"; + return -EINVAL; + } + + const YamlObject &phConfig = (*root)["pipeline_handler"]; + config_.minUnicamBuffers = + phConfig["min_unicam_buffers"].get<unsigned int>(config_.minUnicamBuffers); + config_.minTotalUnicamBuffers = + phConfig["min_total_unicam_buffers"].get<unsigned int>(config_.minTotalUnicamBuffers); + + if (config_.minTotalUnicamBuffers < config_.minUnicamBuffers) { + LOG(RPI, Error) << "Invalid configuration: min_total_unicam_buffers must be >= min_unicam_buffers"; + return -EINVAL; + } + + if (config_.minTotalUnicamBuffers < 1) { + LOG(RPI, Error) << "Invalid configuration: min_total_unicam_buffers must be >= 1"; + return -EINVAL; + } + return 0; } |