[libcamera-devel] [PATCH v3 7/8] libcamera: camera_sensor: Initialize frame durations
Jacopo Mondi
jacopo at jmondi.org
Fri Jun 5 16:10:01 CEST 2020
Calculate the camera minimum and maximum frame durations, and register
the corresponding FrameDurationLimits property with those values.
Signed-off-by: Jacopo Mondi <jacopo at jmondi.org>
---
src/libcamera/camera_sensor.cpp | 74 +++++++++++++++++++++++++++++++++
1 file changed, 74 insertions(+)
diff --git a/src/libcamera/camera_sensor.cpp b/src/libcamera/camera_sensor.cpp
index b9428175c55e..b144940f047d 100644
--- a/src/libcamera/camera_sensor.cpp
+++ b/src/libcamera/camera_sensor.cpp
@@ -283,6 +283,80 @@ int CameraSensor::initProperties()
propertyValue = 0;
properties_.set(properties::Rotation, propertyValue);
+ /* Frame durations. */
+ std::map<uint32_t, const ControlInfo *> controlLimits;
+ std::array<uint32_t, 3> controlIds = {
+ V4L2_CID_VBLANK,
+ V4L2_CID_HBLANK,
+ V4L2_CID_PIXEL_RATE
+ };
+ for (uint32_t controlId : controlIds) {
+ /*
+ * Make sure the subdevice reports VBLANK, HBLANK and PIXEL_RATE
+ * controls and collect the control information.
+ */
+ auto it = controls.find(controlId);
+ if (it == controls.end()) {
+ LOG(CameraSensor, Error)
+ << "Camera sensor does not support control "
+ << controlId;
+ return -EINVAL;
+ }
+
+ controlLimits[controlId] = &it->second;
+ }
+
+ /*
+ * While the maximum line and frame sizes can be calculated by adding
+ * each control's maximum supported value to the current configuration,
+ * the minimum sizes shall be calculated by using the minimum available
+ * resolution. Get the current and smalles available size then calculate
+ * the frame durations.
+ */
+ V4L2SubdeviceFormat fmt{};
+ int ret = subdev_->getFormat(0, &fmt);
+ if (ret)
+ return ret;
+ const Size ¤tSize = fmt.size;
+ const Size &minSize = *sizes_.begin();
+
+ std::vector<int32_t> durations;
+ int32_t duration;
+
+ /*
+ * Pixel rate is reported in Hz while frame duration is expressed in
+ * nanoseconds. Adjust it and calculate the minimum and maximum
+ * durations.
+ */
+ int64_t pixelRate = controlLimits[V4L2_CID_PIXEL_RATE]->max().get<int64_t>();
+ float rate = static_cast<float>(pixelRate) / 1e9F;
+
+ /* Minimum frame duration: higher frame rate. */
+ duration = (minSize.width +
+ controlLimits[V4L2_CID_HBLANK]->min().get<int32_t>())
+ * (minSize.height +
+ controlLimits[V4L2_CID_VBLANK]->min().get<int32_t>());
+ duration = static_cast<int32_t>(static_cast<float>(duration) / rate);
+ durations.push_back(duration);
+
+ pixelRate = controlLimits[V4L2_CID_PIXEL_RATE]->min().get<int64_t>();
+ rate = static_cast<float>(pixelRate) / 1e9F;
+
+ /* Maximum frame duration: lower frame rate. */
+ duration = (currentSize.width +
+ controlLimits[V4L2_CID_HBLANK]->max().get<int32_t>())
+ * (currentSize.height +
+ controlLimits[V4L2_CID_VBLANK]->max().get<int32_t>());
+ duration = static_cast<int32_t>(static_cast<float>(duration) / rate);
+ durations.push_back(duration);
+
+ properties_.set(properties::FrameDurationLimits, durations);
+
+ LOG(CameraSensor, Debug) << "Frame durations interval = ["
+ << durations[0] << " - "
+ << durations[1] << "]";
+
+ return 0;
}
/**
--
2.27.0
More information about the libcamera-devel
mailing list