@@ -16,6 +16,8 @@
using namespace libcamera;
+namespace {
+
const std::vector<int> NUMREQUESTS = { 1, 2, 3, 5, 8, 13, 21, 34, 55, 89 };
const std::vector<std::vector<StreamRole>> ROLES = {
{ StreamRole::Raw },
@@ -24,6 +26,22 @@ const std::vector<std::vector<StreamRole>> ROLES = {
{ StreamRole::Viewfinder },
};
+const std::vector<std::array<StreamRole, 2>> MULTIROLES = {
+ { StreamRole::Raw, StreamRole::StillCapture },
+ { StreamRole::Raw, StreamRole::VideoRecording },
+ { StreamRole::StillCapture, StreamRole::VideoRecording },
+ { StreamRole::VideoRecording, StreamRole::VideoRecording },
+};
+
+std::map<StreamRole, std::string> rolesMap = {
+ { StreamRole::Raw, "Raw" },
+ { StreamRole::StillCapture, "StillCapture" },
+ { StreamRole::VideoRecording, "VideoRecording" },
+ { StreamRole::Viewfinder, "Viewfinder" }
+};
+
+} /* namespace */
+
class SingleStream : public testing::TestWithParam<std::tuple<std::vector<StreamRole>, int>>
{
public:
@@ -60,13 +78,6 @@ void SingleStream::TearDown()
std::string SingleStream::nameParameters(const testing::TestParamInfo<SingleStream::ParamType> &info)
{
- std::map<StreamRole, std::string> rolesMap = {
- { StreamRole::Raw, "Raw" },
- { StreamRole::StillCapture, "StillCapture" },
- { StreamRole::VideoRecording, "VideoRecording" },
- { StreamRole::Viewfinder, "Viewfinder" }
- };
-
std::string roleName = rolesMap[std::get<0>(info.param)[0]];
std::string numRequestsName = std::to_string(std::get<1>(info.param));
@@ -134,3 +145,70 @@ INSTANTIATE_TEST_SUITE_P(CaptureTests,
testing::Combine(testing::ValuesIn(ROLES),
testing::ValuesIn(NUMREQUESTS)),
SingleStream::nameParameters);
+
+class MultiStream : public testing::TestWithParam<std::tuple<std::array<StreamRole, 2>, int>>
+{
+public:
+ static std::string nameParameters(const testing::TestParamInfo<MultiStream::ParamType> &info);
+
+protected:
+ void SetUp() override;
+ void TearDown() override;
+
+ std::shared_ptr<Camera> camera_;
+};
+
+/*
+ * We use gtest's SetUp() and TearDown() instead of constructor and destructor
+ * in order to be able to assert on them.
+ */
+void MultiStream::SetUp()
+{
+ Environment *env = Environment::get();
+
+ camera_ = env->cm()->get(env->cameraId());
+
+ ASSERT_EQ(camera_->acquire(), 0);
+}
+
+void MultiStream::TearDown()
+{
+ if (!camera_)
+ return;
+
+ camera_->release();
+ camera_.reset();
+}
+
+std::string MultiStream::nameParameters(const testing::TestParamInfo<MultiStream::ParamType> &info)
+{
+ std::string roleName = rolesMap[std::get<0>(info.param)[0]] + "_" +
+ rolesMap[std::get<0>(info.param)[1]];
+ std::string numRequestsName = std::to_string(std::get<1>(info.param));
+
+ return roleName + "_" + numRequestsName;
+}
+
+/*
+ * Test multi-stream capture cycles
+ *
+ * Makes sure the camera completes the exact number of requests queued. Example
+ * failure is a camera that completes less requests than the number of requests
+ * queued.
+ */
+TEST_P(MultiStream, Capture)
+{
+ const auto [roles, numRequests] = GetParam();
+
+ CaptureBalanced capture(camera_);
+
+ capture.configure(Span<const StreamRole>{ roles });
+
+ capture.capture(numRequests);
+}
+
+INSTANTIATE_TEST_SUITE_P(MultiCaptureTests,
+ MultiStream,
+ testing::Combine(testing::ValuesIn(MULTIROLES),
+ testing::ValuesIn(NUMREQUESTS)),
+ MultiStream::nameParameters);