@@ -90,27 +90,25 @@ int CameraSensor::init()
return ret;
/* Enumerate and cache media bus codes and sizes. */
- const FormatEnum formats = subdev_->formats(0);
- if (formats.empty()) {
+ const ImageFormats formats = subdev_->formats(0);
+ if (formats.isEmpty()) {
LOG(CameraSensor, Error) << "No image format found";
return -EINVAL;
}
- std::transform(formats.begin(), formats.end(),
- std::back_inserter(mbusCodes_),
- [](decltype(*formats.begin()) f) { return f.first; });
+ mbusCodes_ = formats.formats();
/*
* Extract the supported sizes from the first format as we only support
* sensors that offer the same frame sizes for all media bus codes.
* Verify this assumption and reject the sensor if it isn't true.
*/
- const std::vector<SizeRange> &sizes = formats.begin()->second;
+ const std::vector<SizeRange> &sizes = formats.sizes(mbusCodes_[0]);
std::transform(sizes.begin(), sizes.end(), std::back_inserter(sizes_),
[](const SizeRange &range) { return range.max; });
- for (auto it = ++formats.begin(); it != formats.end(); ++it) {
- if (it->second != sizes) {
+ for (unsigned int code : mbusCodes_) {
+ if (formats.sizes(code) != sizes) {
LOG(CameraSensor, Error)
<< "Frame sizes differ between media bus codes";
return -EINVAL;
@@ -14,16 +14,6 @@
namespace libcamera {
-/**
- * \typedef FormatEnum
- * \brief Type definition for the map of image formats and sizes
- *
- * Type definition used to enumerate the supported pixel formats and image
- * frame sizes. The type associates in a map a pixel format (for memory
- * formats) or a media bus code (for bus formats), to a vector of image
- * resolutions represented by SizeRange items.
- */
-
/**
* \class ImageFormats
* \brief Describe V4L2Device and V4L2SubDevice image formats
@@ -15,8 +15,6 @@
namespace libcamera {
-typedef std::map<unsigned int, std::vector<SizeRange>> FormatEnum;
-
class ImageFormats
{
public:
@@ -45,7 +45,7 @@ public:
int setCrop(unsigned int pad, Rectangle *rect);
int setCompose(unsigned int pad, Rectangle *rect);
- FormatEnum formats(unsigned int pad);
+ ImageFormats formats(unsigned int pad);
int getFormat(unsigned int pad, V4L2SubdeviceFormat *format);
int setFormat(unsigned int pad, V4L2SubdeviceFormat *format);
@@ -187,22 +187,17 @@ int V4L2Subdevice::setCompose(unsigned int pad, Rectangle *rect)
}
/**
- * \brief List the sub-device image resolutions and formats on \a pad
+ * \brief Enumerate all media bus codes and frame sizes on a \a pad
* \param[in] pad The 0-indexed pad number to enumerate formats on
*
- * Retrieve a list of image formats and sizes on the \a pad of a video
- * subdevice. Subdevices can report either a list of discrete sizes they
- * support or a list of intervals expressed as a [min-max] sizes range.
+ * Enumerate all media bus codes and frame sizes supported by the subdevice on
+ * a \a pad.
*
- * Each image size list is associated with a media bus pixel code for which
- * the reported resolutions are supported.
- *
- * \return A map of image formats associated with a list of image sizes, or
- * an empty map on error or if the pad does not exist
+ * \return A list of the supported device formats
*/
-FormatEnum V4L2Subdevice::formats(unsigned int pad)
+ImageFormats V4L2Subdevice::formats(unsigned int pad)
{
- FormatEnum formatMap = {};
+ ImageFormats formats;
if (pad >= entity_->pads().size()) {
LOG(V4L2Subdev, Error) << "Invalid pad: " << pad;
@@ -214,10 +209,15 @@ FormatEnum V4L2Subdevice::formats(unsigned int pad)
if (sizes.empty())
return {};
- formatMap[code] = sizes;
+ if (formats.addFormat(code, sizes)) {
+ LOG(V4L2Subdev, Error)
+ << "Could not add sizes for media bus code "
+ << code << " on pad " << pad;
+ return {};
+ }
}
- return formatMap;
+ return formats;
}
/**
@@ -47,29 +47,29 @@ void ListFormatsTest::printFormats(unsigned int pad,
int ListFormatsTest::run()
{
/* List all formats available on existing "Scaler" pads. */
- std::map<unsigned int, std::vector<SizeRange>> formats;
+ ImageFormats formats;
formats = scaler_->formats(0);
- if (formats.empty()) {
+ if (formats.isEmpty()) {
cerr << "Failed to list formats on pad 0 of subdevice "
<< scaler_->entity()->name() << endl;
return TestFail;
}
- for (auto it = formats.begin(); it != formats.end(); ++it)
- printFormats(0, it->first, it->second);
+ for (unsigned int code : formats.formats())
+ printFormats(0, code, formats.sizes(code));
formats = scaler_->formats(1);
- if (formats.empty()) {
+ if (formats.isEmpty()) {
cerr << "Failed to list formats on pad 1 of subdevice "
<< scaler_->entity()->name() << endl;
return TestFail;
}
- for (auto it = formats.begin(); it != formats.end(); ++it)
- printFormats(1, it->first, it->second);
+ for (unsigned int code : formats.formats())
+ printFormats(1, code, formats.sizes(code));
/* List format on a non-existing pad, format vector shall be empty. */
formats = scaler_->formats(2);
- if (!formats.empty()) {
+ if (!formats.isEmpty()) {
cerr << "Listing formats on non-existing pad 2 of subdevice "
<< scaler_->entity()->name()
<< " should return an empty format list" << endl;