2021-09-03 01:49:56 +00:00
|
|
|
// Copyright 2021, Collabora, Ltd.
|
|
|
|
// SPDX-License-Identifier: BSL-1.0
|
|
|
|
/*!
|
|
|
|
* @file
|
2021-09-15 07:11:10 +00:00
|
|
|
* @brief Ringbuffer implementation for keeping track of the past state of things
|
2021-09-03 01:49:56 +00:00
|
|
|
* @author Moses Turner <moses@collabora.com>
|
|
|
|
* @ingroup drv_ht
|
|
|
|
*/
|
|
|
|
|
|
|
|
#pragma once
|
|
|
|
|
2021-09-15 07:11:10 +00:00
|
|
|
#include <algorithm>
|
2021-09-03 01:49:56 +00:00
|
|
|
#include <assert.h>
|
|
|
|
|
|
|
|
|
|
|
|
//| -4 | -3 | -2 | -1 | Top | Garbage |
|
|
|
|
// OR
|
|
|
|
//| -4 | -3 | -2 | -1 | Top | -7 | -6 | -5 |
|
|
|
|
|
2021-09-15 07:11:10 +00:00
|
|
|
namespace xrt::auxiliary::util {
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
template <typename T, int maxSize> class HistoryBuffer
|
2021-09-03 01:49:56 +00:00
|
|
|
{
|
2021-09-20 09:54:04 +00:00
|
|
|
private:
|
2021-09-03 01:49:56 +00:00
|
|
|
T internalBuffer[maxSize];
|
2021-09-20 09:54:04 +00:00
|
|
|
int mTopIdx = 0;
|
|
|
|
int mLength = 0;
|
2021-09-03 01:49:56 +00:00
|
|
|
|
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
public:
|
|
|
|
// clang-format off
|
2021-12-10 15:59:18 +00:00
|
|
|
int topIdx() const noexcept { return mTopIdx; }
|
|
|
|
int length() const noexcept { return mLength; }
|
2021-09-20 09:54:04 +00:00
|
|
|
// clang-format on
|
2021-09-15 07:11:10 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
/* Put something at the top, overwrite whatever was at the back*/
|
|
|
|
void
|
|
|
|
push(const T inElement)
|
|
|
|
{
|
|
|
|
mTopIdx++;
|
|
|
|
if (mTopIdx == maxSize) {
|
|
|
|
mTopIdx = 0;
|
|
|
|
}
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
memcpy(&internalBuffer[mTopIdx], &inElement, sizeof(T));
|
|
|
|
mLength++;
|
|
|
|
mLength = std::min(mLength, maxSize);
|
2021-09-03 01:49:56 +00:00
|
|
|
}
|
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
T * // Hack comment to fix clang-format
|
|
|
|
operator[](int inIndex)
|
|
|
|
{
|
|
|
|
if (mLength == 0) {
|
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
assert(inIndex <= maxSize);
|
|
|
|
assert(inIndex >= 0);
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
int index = mTopIdx - inIndex;
|
|
|
|
if (index < 0) {
|
|
|
|
index = maxSize + index;
|
|
|
|
}
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
assert(index >= 0);
|
|
|
|
if (index > maxSize) {
|
|
|
|
assert(false);
|
|
|
|
}
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
return &internalBuffer[index];
|
2021-09-03 01:49:56 +00:00
|
|
|
}
|
2021-09-20 09:54:04 +00:00
|
|
|
};
|
2021-09-03 01:49:56 +00:00
|
|
|
|
2021-09-20 09:54:04 +00:00
|
|
|
} // namespace xrt::auxiliary::util
|