28 jassert (bufferSize > 0);
36 auto vs = validStart.
get();
37 auto ve = validEnd.
get();
38 return ve >= vs ? (ve - vs) : (bufferSize - (vs - ve));
49 jassert (newSize > 0);
56 int& startIndex2,
int& blockSize2)
const noexcept
58 auto vs = validStart.get();
59 auto ve = validEnd.get();
61 auto freeSpace = ve >= vs ? (bufferSize - (ve - vs)) : (vs - ve);
62 numToWrite = jmin (numToWrite, freeSpace - 1);
75 blockSize1 = jmin (bufferSize - ve, numToWrite);
76 numToWrite -= blockSize1;
77 blockSize2 = numToWrite <= 0 ? 0 : jmin (numToWrite, vs);
83 jassert (numWritten >= 0 && numWritten < bufferSize);
85 auto newEnd = validEnd.get() + numWritten;
87 if (newEnd >= bufferSize)
94 int& startIndex2,
int& blockSize2)
const noexcept
96 auto vs = validStart.get();
97 auto ve = validEnd.get();
99 auto numReady = ve >= vs ? (ve - vs) : (bufferSize - (vs - ve));
100 numWanted = jmin (numWanted, numReady);
113 blockSize1 = jmin (bufferSize - vs, numWanted);
114 numWanted -= blockSize1;
115 blockSize2 = numWanted <= 0 ? 0 : jmin (numWanted, ve);
121 jassert (numRead >= 0 && numRead <= bufferSize);
123 auto newStart = validStart.get() + numRead;
125 if (newStart >= bufferSize)
126 newStart -= bufferSize;
128 validStart = newStart;
132template <AbstractFifo::ReadOrWrite mode>
134 : startIndex1 (other.startIndex1),
135 blockSize1 (other.blockSize1),
136 startIndex2 (other.startIndex2),
137 blockSize2 (other.blockSize2)
142template <AbstractFifo::ReadOrWrite mode>
143AbstractFifo::ScopedReadWrite<mode>&
144AbstractFifo::ScopedReadWrite<mode>::operator= (ScopedReadWrite&& other)
noexcept
150template <AbstractFifo::ReadOrWrite mode>
151void AbstractFifo::ScopedReadWrite<mode>::swap (ScopedReadWrite& other)
noexcept
153 std::swap (other.fifo, fifo);
154 std::swap (other.startIndex1, startIndex1);
155 std::swap (other.blockSize1, blockSize1);
156 std::swap (other.startIndex2, startIndex2);
157 std::swap (other.blockSize2, blockSize2);
160template class AbstractFifo::ScopedReadWrite<AbstractFifo::ReadOrWrite::read>;
161template class AbstractFifo::ScopedReadWrite<AbstractFifo::ReadOrWrite::write>;
171class AbstractFifoTests final :
public UnitTest
175 :
UnitTest (
"Abstract Fifo", UnitTestCategories::containers)
178 struct WriteThread final :
public Thread
180 WriteThread (AbstractFifo& f,
int* b, Random rng)
181 : Thread (
"fifo writer"), fifo (f), buffer (b), random (rng)
186 ~WriteThread()
override
195 while (! threadShouldExit())
197 int num = random.nextInt (2000) + 1;
199 auto writer = fifo.write (num);
201 jassert (writer.blockSize1 >= 0 && writer.blockSize2 >= 0);
202 jassert (writer.blockSize1 == 0
203 || (writer.startIndex1 >= 0 && writer.startIndex1 < fifo.getTotalSize()));
204 jassert (writer.blockSize2 == 0
205 || (writer.startIndex2 >= 0 && writer.startIndex2 < fifo.getTotalSize()));
207 writer.forEach ([
this, &n] (
int index) { this->buffer[index] = n++; });
216 JUCE_BEGIN_IGNORE_WARNINGS_MSVC (6262)
218 void runTest()
override
220 beginTest (
"AbstractFifo");
223 AbstractFifo fifo (numElementsInArray (buffer));
225 WriteThread writer (fifo, buffer, getRandom());
228 Random r = getRandom();
229 r.combineSeed (12345);
231 for (
int count = 100000; --count >= 0;)
233 int num = r.nextInt (6000) + 1;
235 auto reader = fifo.read (num);
237 if (! (reader.blockSize1 >= 0 && reader.blockSize2 >= 0)
238 && (reader.blockSize1 == 0
239 || (reader.startIndex1 >= 0 && reader.startIndex1 < fifo.getTotalSize()))
240 && (reader.blockSize2 == 0
241 || (reader.startIndex2 >= 0 && reader.startIndex2 < fifo.getTotalSize())))
243 expect (
false,
"prepareToRead returned -ve values");
249 reader.forEach ([&failed, &buffer, &n] (
int index)
251 failed = (buffer[index] != n++) || failed;
256 expect (
false,
"read values were incorrect");
262 JUCE_END_IGNORE_WARNINGS_MSVC
265static AbstractFifoTests fifoUnitTests;
ScopedReadWrite()=default
void prepareToWrite(int numToWrite, int &startIndex1, int &blockSize1, int &startIndex2, int &blockSize2) const noexcept
int getTotalSize() const noexcept
void prepareToRead(int numWanted, int &startIndex1, int &blockSize1, int &startIndex2, int &blockSize2) const noexcept
AbstractFifo(int capacity) noexcept
void finishedRead(int numRead) noexcept
int getFreeSpace() const noexcept
void finishedWrite(int numWritten) noexcept
int getNumReady() const noexcept
void setTotalSize(int newSize) noexcept
Type get() const noexcept