Skip to content

Commit e754fc1

Browse files
committed
[cru] Update CRU DMA engine control
1 parent 48af6bf commit e754fc1

File tree

5 files changed

+52
-33
lines changed

5 files changed

+52
-33
lines changed

src/CommandLineUtilities/ProgramDmaBench.cxx

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -346,6 +346,8 @@ class ProgramDmaBench : public Program
346346

347347
std::cout << "\n\n";
348348
mChannel->stopDma();
349+
int numPopped = freeExcessPages(10ms);
350+
getLogger() << "Popped " << numPopped << " remaining superpages" << endm;
349351

350352
outputErrors();
351353
outputStats();
@@ -548,6 +550,39 @@ class ProgramDmaBench : public Program
548550
lowPriorityFuture.get();
549551
}
550552

553+
/// Free the pages that remain after stopping DMA (these may not be filled)
554+
int freeExcessPages(std::chrono::milliseconds timeout)
555+
{
556+
auto start = std::chrono::steady_clock::now();
557+
int popped = 0;
558+
while ((std::chrono::steady_clock::now() - start) < timeout) {
559+
auto size = mChannel->getReadyQueueSize();
560+
for (int i = 0; i < size; ++i) {
561+
auto superpage = mChannel->popSuperpage();
562+
fetchAddSuperpagesReadOut();
563+
if ((mDataSource == DataSource::Fee) || (mDataSource == DataSource::Ddg)) {
564+
auto superpageAddress = mBufferBaseAddress + superpage.getOffset();
565+
size_t readoutBytes = 0;
566+
bool atStartOfSuperpage = true;
567+
while ((readoutBytes < superpage.getReceived())) { // At least one more dma page fits in the superpage
568+
auto pageAddress = superpageAddress + readoutBytes;
569+
auto readoutCount = fetchAddDmaPagesReadOut();
570+
size_t pageSize = readoutPage(pageAddress, readoutCount, atStartOfSuperpage);
571+
atStartOfSuperpage = false; // Update the boolean value as soon as we move...
572+
readoutBytes += pageSize;
573+
}
574+
575+
if (readoutBytes > mSuperpageSize) {
576+
BOOST_THROW_EXCEPTION(Exception() << ErrorInfo::Message("RDH reports cumulative dma page sizes that exceed the superpage size"));
577+
}
578+
}
579+
std::cout << "[popped superpage " << i << " ], size= " << superpage.getSize() << " received= " << superpage.getReceived() << " isFilled=" << superpage.isFilled() << " isReady=" << superpage.isReady() << std::endl;
580+
}
581+
popped += size;
582+
}
583+
return popped;
584+
}
585+
551586
uint32_t getDataGeneratorCounterFromPage(uintptr_t pageAddress, size_t headerSize)
552587
{
553588
auto payload = reinterpret_cast<const volatile uint32_t*>(pageAddress + headerSize);

src/Cru/CruBar.cxx

Lines changed: 12 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -152,14 +152,19 @@ uint32_t CruBar::getSuperpageSize(uint32_t link)
152152
return superpageSize;
153153
}
154154

155-
/// Enables the data emulator
156-
/// \param enabled true for enabled
157-
void CruBar::setDataEmulatorEnabled(bool enabled)
155+
/// Signals the CRU DMA engine to start
156+
void CruBar::startDmaEngine()
158157
{
159-
writeRegister(Cru::Registers::DMA_CONTROL.index, enabled ? 0x1 : 0x0);
160-
uint32_t bits = readRegister(Cru::Registers::DATA_GENERATOR_CONTROL.index);
161-
setDataGeneratorEnableBits(bits, enabled);
162-
writeRegister(Cru::Registers::DATA_GENERATOR_CONTROL.index, bits);
158+
writeRegister(Cru::Registers::DMA_CONTROL.index, 0x11); // send DMA start (bit #0)
159+
// dyn offset enabled (bit #4)
160+
modifyRegister(Cru::Registers::DATA_GENERATOR_CONTROL.index, 0, 1, 0x1); // enable data generator
161+
}
162+
163+
/// Signals the CRU DMA engine to stop
164+
void CruBar::stopDmaEngine()
165+
{
166+
modifyRegister(Cru::Registers::DMA_CONTROL.index, 8, 1, 0x1); // send DMA flush to the CRU
167+
modifyRegister(Cru::Registers::DATA_GENERATOR_CONTROL.index, 0, 1, 0x0); // disable data generator
163168
}
164169

165170
/// Resets the data generator counter
@@ -387,14 +392,6 @@ FirmwareFeatures CruBar::convertToFirmwareFeatures(uint32_t reg)
387392
return features;
388393
}
389394

390-
/// Sets the bits for the data generator enabled in the given integer
391-
/// \param bits Integer with bits to set
392-
/// \param enabled Generator enabled or not
393-
void CruBar::setDataGeneratorEnableBits(uint32_t& bits, bool enabled)
394-
{
395-
Utilities::setBit(bits, 0, enabled);
396-
}
397-
398395
/// Reports the CRU status
399396
Cru::ReportInfo CruBar::report()
400397
{

src/Cru/CruBar.h

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,8 @@ class CruBar final : public BarInterfaceBase
6666
void pushSuperpageDescriptor(uint32_t link, uint32_t pages, uintptr_t busAddress);
6767
uint32_t getSuperpageCount(uint32_t link);
6868
uint32_t getSuperpageSize(uint32_t link);
69-
void setDataEmulatorEnabled(bool enabled);
69+
void startDmaEngine();
70+
void stopDmaEngine();
7071
void resetDataGeneratorCounter();
7172
void resetCard();
7273
void dataGeneratorInjectError();
@@ -75,9 +76,6 @@ class CruBar final : public BarInterfaceBase
7576

7677
static FirmwareFeatures convertToFirmwareFeatures(uint32_t reg);
7778

78-
static void setDataGeneratorEnableBits(uint32_t& bits, bool enabled);
79-
static void setDataGeneratorRandomSizeBits(uint32_t& bits, bool enabled);
80-
8179
void setWrapperCount();
8280
void configure() override;
8381
void reconfigure() override;

src/Cru/CruDmaChannel.cxx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -147,14 +147,14 @@ void CruDmaChannel::deviceStartDma()
147147
/// Set buffer to ready
148148
void CruDmaChannel::setBufferReady()
149149
{
150-
getBar()->setDataEmulatorEnabled(true);
150+
getBar()->startDmaEngine();
151151
std::this_thread::sleep_for(10ms);
152152
}
153153

154154
/// Set buffer to non-ready
155155
void CruDmaChannel::setBufferNonReady()
156156
{
157-
getBar()->setDataEmulatorEnabled(false);
157+
getBar()->stopDmaEngine();
158158
}
159159

160160
void CruDmaChannel::deviceStopDma()
@@ -171,7 +171,7 @@ void CruDmaChannel::deviceStopDma()
171171
break;
172172
}
173173

174-
if (!link.queue.empty()) { // care for the extra filled superpage
174+
if (!link.queue.empty()) { // care for the extra filled superpage
175175
transferSuperpageFromLinkToReady(link);
176176
moved++;
177177
}

test/TestCruBar.cxx

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -50,14 +50,3 @@ BOOST_AUTO_TEST_CASE(TestFirmwareFeatures)
5050
BOOST_CHECK(!CruBar::convertToFirmwareFeatures(0x40005AFE + (1 << 19)).firmwareInfo);
5151
}
5252
}
53-
54-
BOOST_AUTO_TEST_CASE(TestDataGeneratorConfiguration)
55-
{
56-
{
57-
uint32_t bits = 0;
58-
CruBar::setDataGeneratorEnableBits(bits, true);
59-
BOOST_CHECK(bits == 0x1);
60-
CruBar::setDataGeneratorEnableBits(bits, false);
61-
BOOST_CHECK(bits == 0x0);
62-
}
63-
}

0 commit comments

Comments
 (0)