From 5c5e752ab71e2525e92864d8ee243800a62fff86 Mon Sep 17 00:00:00 2001
From: Sebastian Hahta <joseha@utu.fi>
Date: Thu, 29 Aug 2019 17:18:22 +0300
Subject: [PATCH] small adjustments and documentation

---
 .../include/ftl/rgbd/detail/source.hpp        |  4 ++
 .../rgbd-sources/include/ftl/rgbd/frame.hpp   | 71 +++++++++++++------
 2 files changed, 53 insertions(+), 22 deletions(-)

diff --git a/components/rgbd-sources/include/ftl/rgbd/detail/source.hpp b/components/rgbd-sources/include/ftl/rgbd/detail/source.hpp
index 25e19e396..a75fb1879 100644
--- a/components/rgbd-sources/include/ftl/rgbd/detail/source.hpp
+++ b/components/rgbd-sources/include/ftl/rgbd/detail/source.hpp
@@ -10,6 +10,10 @@ namespace rgbd {
 
 class Source;
 
+// TODO:	frame.hpp has to know the exact amount of channels
+//			(remove hardcoded value by providing exact value elsewhere).
+//			Possibly move channels to frame.hpp?
+
 typedef unsigned int channel_t;
 
 static const channel_t kChanNone = 0;
diff --git a/components/rgbd-sources/include/ftl/rgbd/frame.hpp b/components/rgbd-sources/include/ftl/rgbd/frame.hpp
index 41eb75095..a97a1f17b 100644
--- a/components/rgbd-sources/include/ftl/rgbd/frame.hpp
+++ b/components/rgbd-sources/include/ftl/rgbd/frame.hpp
@@ -4,24 +4,6 @@
 #include <ftl/configuration.hpp>
 #include <opencv2/core.hpp>
 
-// https://stackoverflow.com/a/31718095/
-static uint32_t msbDeBruijn32(uint32_t v)
-{
-	static const int MultiplyDeBruijnBitPosition[32] =
-	{
-		0, 9, 1, 10, 13, 21, 2, 29, 11, 14, 16, 18, 22, 25, 3, 30,
-		8, 12, 20, 28, 15, 17, 24, 7, 19, 27, 23, 6, 26, 5, 4, 31
-	};
-
-	v |= v >> 1; // first round down to one less than a power of 2
-	v |= v >> 2;
-	v |= v >> 4;
-	v |= v >> 8;
-	v |= v >> 16;
-
-	return MultiplyDeBruijnBitPosition[(uint32_t)(v * 0x07C4ACDDU) >> 27];
-}
-
 namespace ftl {
 namespace rgbd {
 
@@ -38,21 +20,66 @@ public:
 		std::fill(available_.begin(), available_.end(), false);
 	}
 
-	/* @brief	Is there valid data in channel
+	/* @brief	Is there valid data in channel. Must be checked if user
+	 *			is not providing the data and it is uncertain that valid data is
+	 * 			available.
 	 */
 	bool hasChannel(const ftl::rgbd::channel_t& channel)
 	{
-		return available_[msbDeBruijn32(channel)];
+		return available_[_channelIdx(channel)];
 	}
 
-	/* @brief	Get reference to the channel GpuMat
+	/* @brief	Get reference to the channel GpuMat and marks it valid.
+	 *			If hasChannel() was false, user of this method must set
+	 *			valid data to the returned reference.
 	 */
 	cv::cuda::GpuMat& getChannel(const ftl::rgbd::channel_t& channel)
 	{
-		return channels_[msbDeBruijn32(channel)];
+		auto idx = _channelIdx(channel);
+		available_[idx] = true;
+		return channels_[idx];
 	}
 
 private:
+
+	static size_t _channelIdx(const ftl::rgbd::channel_t& channel)
+	{
+		switch(channel)
+		{
+			case kChanNone:				return 0;
+			case kChanLeft:				return 1;
+			case kChanDepth:			return 2;
+			case kChanRight:			return 3;
+			case kChanDisparity:		return 4;
+			case kChanDeviation:		return 5;
+			case kChanNormals:			return 6;
+			case kChanConfidence:		return 7;
+			case kChanFlow:				return 8;
+			case kChanEnergy:			return 9;
+			default:					return 0; // should not happen
+		}
+	}
+
+	// https://stackoverflow.com/a/31718095/
+	// Indices for channels, requirs channels to have bitmask format
+	// (values are power of 2 and no missing values/gaps).
+	static uint32_t _msbDeBruijn32(uint32_t v)
+	{
+		static const int MultiplyDeBruijnBitPosition[32] =
+		{
+			0, 9, 1, 10, 13, 21, 2, 29, 11, 14, 16, 18, 22, 25, 3, 30,
+			8, 12, 20, 28, 15, 17, 24, 7, 19, 27, 23, 6, 26, 5, 4, 31
+		};
+
+		v |= v >> 1; // first round down to one less than a power of 2
+		v |= v >> 2;
+		v |= v >> 4;
+		v |= v >> 8;
+		v |= v >> 16;
+
+		return MultiplyDeBruijnBitPosition[(uint32_t)(v * 0x07C4ACDDU) >> 27];
+	}
+
 	std::vector<cv::cuda::GpuMat> channels_;
 	std::vector<bool> available_;
 };
-- 
GitLab