Device: Add Coremini script upload function

pull/56/head
Yasser Yassine 2023-03-08 18:58:38 +00:00
parent 9b46d486cb
commit bf6a059820
42 changed files with 363 additions and 55 deletions

View File

@ -113,6 +113,8 @@ static constexpr const char* ATOMIC_OPERATION_COMPLETED_NONATOMICALLY = "An idea
static constexpr const char* WIVI_STACK_REFRESH_FAILED = "The Wireless neoVI stack encountered a communication error."; static constexpr const char* WIVI_STACK_REFRESH_FAILED = "The Wireless neoVI stack encountered a communication error.";
static constexpr const char* WIVI_UPLOAD_STACK_OVERFLOW = "The Wireless neoVI upload stack has encountered an overflow condition."; static constexpr const char* WIVI_UPLOAD_STACK_OVERFLOW = "The Wireless neoVI upload stack has encountered an overflow condition.";
static constexpr const char* A2B_MESSAGE_INCOMPLETE_FRAME = "At least one of the frames of the A2B message does not contain samples for each channel and stream."; static constexpr const char* A2B_MESSAGE_INCOMPLETE_FRAME = "At least one of the frames of the A2B message does not contain samples for each channel and stream.";
static constexpr const char* COREMINI_UPLOAD_VERSION_MISMATCH = "The version of the coremini engine on the device and the script uploaded are not the same.";
static constexpr const char* DISK_NOT_CONNECTED = "The program tried to access a disk that is not connected.";
// Transport Errors // Transport Errors
static constexpr const char* FAILED_TO_READ = "A read operation failed."; static constexpr const char* FAILED_TO_READ = "A read operation failed.";
@ -249,7 +251,10 @@ const char* APIEvent::DescriptionForType(Type type) {
return WIVI_UPLOAD_STACK_OVERFLOW; return WIVI_UPLOAD_STACK_OVERFLOW;
case Type::A2BMessageIncompleteFrame: case Type::A2BMessageIncompleteFrame:
return A2B_MESSAGE_INCOMPLETE_FRAME; return A2B_MESSAGE_INCOMPLETE_FRAME;
case Type::CoreminiUploadVersionMismatch:
return COREMINI_UPLOAD_VERSION_MISMATCH;
case Type::DiskNotConnected:
return DISK_NOT_CONNECTED;
// Transport Errors // Transport Errors
case Type::FailedToRead: case Type::FailedToRead:
return FAILED_TO_READ; return FAILED_TO_READ;

View File

@ -445,7 +445,7 @@ int8_t Device::prepareScriptLoad() {
return retVal; return retVal;
} }
bool Device::startScript() bool Device::startScript(Disk::MemoryType memType)
{ {
if(!isOpen()) { if(!isOpen()) {
report(APIEvent::Type::DeviceCurrentlyClosed, APIEvent::Severity::Error); report(APIEvent::Type::DeviceCurrentlyClosed, APIEvent::Severity::Error);
@ -454,8 +454,8 @@ bool Device::startScript()
std::lock_guard<std::mutex> lg(diskLock); std::lock_guard<std::mutex> lg(diskLock);
uint8_t LocationSdCard = 1; //Only support starting a coremini in an SDCard uint8_t location = static_cast<uint8_t>(memType);
auto generic = com->sendCommand(Command::LoadCoreMini, LocationSdCard); auto generic = com->sendCommand(Command::LoadCoreMini, location);
if(!generic) if(!generic)
{ {
@ -486,6 +486,68 @@ bool Device::stopScript()
return true; return true;
} }
bool Device::uploadCoremini(std::unique_ptr<std::istream>&& stream, Disk::MemoryType memType) {
auto startAddress = getCoreminiStartAddress(memType);
if(!startAddress) {
return false;
}
auto connected = isLogicalDiskConnected();
if(!connected) {
return false; // Already added an API error
}
if(!(*connected)) {
report(APIEvent::Type::DiskNotConnected, APIEvent::Severity::Error);
return false;
}
if(!stopScript()) {
return false;
}
if(!stream || stream->bad()) {
report(APIEvent::Type::RequiredParameterNull, APIEvent::Severity::Error);
return false;
}
std::vector<char> bin(std::istreambuf_iterator<char>(*stream), {}); // Read the whole stream
if(bin.size() < 4) {
report(APIEvent::Type::BufferInsufficient, APIEvent::Severity::Error);
return false;
}
uint16_t scriptVersion = *(uint16_t*)(&bin[2]); // Third and fourth byte are version number stored in little endian
auto scriptStatus = getScriptStatus();
if(!scriptStatus) {
return false; // Already added an API error
}
if(scriptStatus->coreminiVersion != scriptVersion) {
// Version on device and script are not the same
report(APIEvent::Type::CoreminiUploadVersionMismatch, APIEvent::Severity::Error);
return false;
}
auto numWritten = writeLogicalDisk(*startAddress, (uint8_t*)bin.data(), static_cast<uint64_t>(bin.size()), std::chrono::milliseconds(2000), memType);
if(!numWritten) {
return false; // Already added an API error
}
if(*numWritten == 0) {
report(APIEvent::Type::FailedToWrite, APIEvent::Severity::Error);
return false; // Failed to write
}
return true;
}
bool Device::clearScript() bool Device::clearScript()
{ {
if(!stopScript()) if(!stopScript())
@ -564,7 +626,8 @@ Network Device::getNetworkByNumber(Network::Type type, size_t index) const {
return Network::NetID::Invalid; return Network::NetID::Invalid;
} }
std::optional<uint64_t> Device::readLogicalDisk(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) {
std::optional<uint64_t> Device::readLogicalDisk(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, Disk::MemoryType memType) {
if(!into || timeout <= std::chrono::milliseconds(0)) { if(!into || timeout <= std::chrono::milliseconds(0)) {
report(APIEvent::Type::RequiredParameterNull, APIEvent::Severity::Error); report(APIEvent::Type::RequiredParameterNull, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
@ -579,9 +642,9 @@ std::optional<uint64_t> Device::readLogicalDisk(uint64_t pos, uint8_t* into, uin
if(diskReadDriver->getAccess() == Disk::Access::EntireCard && diskWriteDriver->getAccess() == Disk::Access::VSA) { if(diskReadDriver->getAccess() == Disk::Access::EntireCard && diskWriteDriver->getAccess() == Disk::Access::VSA) {
// We have mismatched drivers, we need to add an offset to the diskReadDriver // We have mismatched drivers, we need to add an offset to the diskReadDriver
const auto offset = Disk::FindVSAInFAT([this, &timeout](uint64_t pos, uint8_t *into, uint64_t amount) { const auto offset = Disk::FindVSAInFAT([this, &timeout, &memType](uint64_t pos, uint8_t *into, uint64_t amount) {
const auto start = std::chrono::steady_clock::now(); const auto start = std::chrono::steady_clock::now();
auto ret = diskReadDriver->readLogicalDisk(*com, report, pos, into, amount, timeout); auto ret = diskReadDriver->readLogicalDisk(*com, report, pos, into, amount, timeout, memType);
timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::steady_clock::now() - start); timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::steady_clock::now() - start);
return ret; return ret;
}); });
@ -593,10 +656,10 @@ std::optional<uint64_t> Device::readLogicalDisk(uint64_t pos, uint8_t* into, uin
// This is needed for certain read drivers which take over the communication stream // This is needed for certain read drivers which take over the communication stream
const auto lifetime = suppressDisconnects(); const auto lifetime = suppressDisconnects();
return diskReadDriver->readLogicalDisk(*com, report, pos, into, amount, timeout); return diskReadDriver->readLogicalDisk(*com, report, pos, into, amount, timeout, memType);
} }
std::optional<uint64_t> Device::writeLogicalDisk(uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) { std::optional<uint64_t> Device::writeLogicalDisk(uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, Disk::MemoryType memType) {
if(!from || timeout <= std::chrono::milliseconds(0)) { if(!from || timeout <= std::chrono::milliseconds(0)) {
report(APIEvent::Type::RequiredParameterNull, APIEvent::Severity::Error); report(APIEvent::Type::RequiredParameterNull, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
@ -608,7 +671,7 @@ std::optional<uint64_t> Device::writeLogicalDisk(uint64_t pos, const uint8_t* fr
} }
std::lock_guard<std::mutex> lk(diskLock); std::lock_guard<std::mutex> lk(diskLock);
return diskWriteDriver->writeLogicalDisk(*com, report, *diskReadDriver, pos, from, amount, timeout); return diskWriteDriver->writeLogicalDisk(*com, report, *diskReadDriver, pos, from, amount, timeout, memType);
} }
std::optional<bool> Device::isLogicalDiskConnected() { std::optional<bool> Device::isLogicalDiskConnected() {

View File

@ -5,7 +5,11 @@ using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> ReadDriver::readLogicalDisk(Communication& com, device_eventhandler_t report, std::optional<uint64_t> ReadDriver::readLogicalDisk(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, Disk::MemoryType memType) {
std::vector<uint8_t>& cache = memType == Disk::MemoryType::SD ? cacheSD : cacheEEPROM;
uint64_t& cachePos = memType == Disk::MemoryType::SD ? cachePosSD : cachePosEEPROM;
if(amount == 0) if(amount == 0)
return 0; return 0;
@ -57,7 +61,7 @@ std::optional<uint64_t> ReadDriver::readLogicalDisk(Communication& com, device_e
auto start = std::chrono::high_resolution_clock::now(); auto start = std::chrono::high_resolution_clock::now();
auto readAmount = readLogicalDiskAligned(com, report, currentBlock * idealBlockSize, auto readAmount = readLogicalDiskAligned(com, report, currentBlock * idealBlockSize,
useAlignedReadBuffer ? alignedReadBuffer.data() : (into + intoOffset), idealBlockSize, timeout); useAlignedReadBuffer ? alignedReadBuffer.data() : (into + intoOffset), idealBlockSize, timeout, memType);
timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start); timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start);
if(!readAmount.has_value() || *readAmount < curAmt) { if(!readAmount.has_value() || *readAmount < curAmt) {
@ -94,12 +98,19 @@ std::optional<uint64_t> ReadDriver::readLogicalDisk(Communication& com, device_e
return ret; return ret;
} }
void ReadDriver::invalidateCache(uint64_t pos, uint64_t amount) { void ReadDriver::invalidateCache(uint64_t pos, uint64_t amount, MemoryType memType) {
std::vector<uint8_t>& cache = memType == Disk::MemoryType::SD ? cacheSD : cacheEEPROM;
uint64_t cachePos = memType == Disk::MemoryType::SD ? cachePosSD : cachePosEEPROM;
if(pos <= cachePos + cache.size() && pos + amount >= cachePos) if(pos <= cachePos + cache.size() && pos + amount >= cachePos)
cache.clear(); cache.clear();
} }
std::optional<uint64_t> ReadDriver::readFromCache(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds staleAfter) { std::optional<uint64_t> ReadDriver::readFromCache(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds staleAfter, MemoryType memType) {
std::vector<uint8_t>& cache = memType == Disk::MemoryType::SD ? cacheSD : cacheEEPROM;
uint64_t cachePos = memType == Disk::MemoryType::SD ? cachePosSD : cachePosEEPROM;
if(cache.empty()) if(cache.empty())
return std::nullopt; // Nothing in the cache return std::nullopt; // Nothing in the cache

View File

@ -5,7 +5,7 @@ using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> WriteDriver::writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver, std::optional<uint64_t> WriteDriver::writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType) {
if(amount == 0) if(amount == 0)
return 0; return 0;
@ -51,7 +51,7 @@ std::optional<uint64_t> WriteDriver::writeLogicalDisk(Communication& com, device
const bool useAlignedWriteBuffer = (posWithinCurrentBlock != 0 || curAmt != idealBlockSize); const bool useAlignedWriteBuffer = (posWithinCurrentBlock != 0 || curAmt != idealBlockSize);
if(useAlignedWriteBuffer) { if(useAlignedWriteBuffer) {
auto read = readDriver.readLogicalDisk(com, reportFromRead, currentBlock * idealBlockSize, auto read = readDriver.readLogicalDisk(com, reportFromRead, currentBlock * idealBlockSize,
alignedWriteBuffer.data(), idealBlockSize, timeout); alignedWriteBuffer.data(), idealBlockSize, timeout, memType);
timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start); timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start);
if(read != idealBlockSize) if(read != idealBlockSize)
@ -62,7 +62,7 @@ std::optional<uint64_t> WriteDriver::writeLogicalDisk(Communication& com, device
start = std::chrono::high_resolution_clock::now(); start = std::chrono::high_resolution_clock::now();
auto bytesTransferred = writeLogicalDiskAligned(com, report, currentBlock * idealBlockSize, auto bytesTransferred = writeLogicalDiskAligned(com, report, currentBlock * idealBlockSize,
useAlignedWriteBuffer ? alignedWriteBuffer.data() : (from + fromOffset), idealBlockSize, timeout); useAlignedWriteBuffer ? alignedWriteBuffer.data() : (from + fromOffset), idealBlockSize, timeout, memType);
timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start); timeout -= std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::high_resolution_clock::now() - start);
if(!bytesTransferred.has_value() || *bytesTransferred < curAmt) { if(!bytesTransferred.has_value() || *bytesTransferred < curAmt) {
@ -83,6 +83,6 @@ std::optional<uint64_t> WriteDriver::writeLogicalDisk(Communication& com, device
// No matter how much succeeded, to be safe, we'll invalidate anything // No matter how much succeeded, to be safe, we'll invalidate anything
// we may have even tried to write, since it may have succeeded without // we may have even tried to write, since it may have succeeded without
// notifying, etc. // notifying, etc.
readDriver.invalidateCache(pos, amount); readDriver.invalidateCache(pos, amount, memType);
return ret; return ret;
} }

View File

@ -13,7 +13,7 @@ using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> ExtExtractorDiskReadDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> ExtExtractorDiskReadDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType) {
if(amount > getBlockSizeBounds().second) if(amount > getBlockSizeBounds().second)
return std::nullopt; return std::nullopt;
@ -28,7 +28,7 @@ std::optional<uint64_t> ExtExtractorDiskReadDriver::readLogicalDiskAligned(Commu
unsigned int attempts = 4; unsigned int attempts = 4;
while (attempts-- > 0) while (attempts-- > 0)
{ {
ret = attemptReadLogicalDiskAligned(com, report, pos, into, amount, timeout); ret = attemptReadLogicalDiskAligned(com, report, pos, into, amount, timeout, memType);
if (ret.has_value()) if (ret.has_value())
break; break;
} }
@ -36,7 +36,7 @@ std::optional<uint64_t> ExtExtractorDiskReadDriver::readLogicalDiskAligned(Commu
} }
std::optional<uint64_t> ExtExtractorDiskReadDriver::attemptReadLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> ExtExtractorDiskReadDriver::attemptReadLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType) {
static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead); static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead);
uint64_t sector = pos / SectorSize; uint64_t sector = pos / SectorSize;

View File

@ -1,12 +1,13 @@
#include "icsneo/disk/neomemorydiskdriver.h" #include "icsneo/disk/neomemorydiskdriver.h"
#include "icsneo/communication/message/neoreadmemorysdmessage.h" #include "icsneo/communication/message/neoreadmemorysdmessage.h"
#include <cstring> #include <cstring>
#include <iostream>
using namespace icsneo; using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> NeoMemoryDiskDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> NeoMemoryDiskDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType) {
static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead); static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead);
if(pos % SectorSize != 0) if(pos % SectorSize != 0)
@ -16,9 +17,11 @@ std::optional<uint64_t> NeoMemoryDiskDriver::readLogicalDiskAligned(Communicatio
return std::nullopt; return std::nullopt;
const uint64_t currentSector = pos / SectorSize; const uint64_t currentSector = pos / SectorSize;
auto msg = com.waitForMessageSync([&currentSector, &com] { const uint8_t memLocation = (uint8_t)memType;
auto msg = com.waitForMessageSync([&currentSector, &memLocation, &com] {
return com.sendCommand(Command::NeoReadMemory, { return com.sendCommand(Command::NeoReadMemory, {
MemoryTypeSD, memLocation,
uint8_t(currentSector & 0xFF), uint8_t(currentSector & 0xFF),
uint8_t((currentSector >> 8) & 0xFF), uint8_t((currentSector >> 8) & 0xFF),
uint8_t((currentSector >> 16) & 0xFF), uint8_t((currentSector >> 16) & 0xFF),
@ -44,7 +47,7 @@ std::optional<uint64_t> NeoMemoryDiskDriver::readLogicalDiskAligned(Communicatio
} }
std::optional<uint64_t> NeoMemoryDiskDriver::writeLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> NeoMemoryDiskDriver::writeLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType) {
static std::shared_ptr<MessageFilter> NeoMemoryDone = std::make_shared<MessageFilter>(Network::NetID::NeoMemoryWriteDone); static std::shared_ptr<MessageFilter> NeoMemoryDone = std::make_shared<MessageFilter>(Network::NetID::NeoMemoryWriteDone);
@ -55,9 +58,11 @@ std::optional<uint64_t> NeoMemoryDiskDriver::writeLogicalDiskAligned(Communicati
return std::nullopt; return std::nullopt;
const uint64_t currentSector = pos / SectorSize; const uint64_t currentSector = pos / SectorSize;
auto msg = com.waitForMessageSync([&currentSector, &com, from, amount] { const uint8_t memLocation = (uint8_t)memType;
auto msg = com.waitForMessageSync([&currentSector, &memLocation, &com, from, amount] {
std::vector<uint8_t> command = { std::vector<uint8_t> command = {
MemoryTypeSD, memLocation,
uint8_t(currentSector & 0xFF), uint8_t(currentSector & 0xFF),
uint8_t((currentSector >> 8) & 0xFF), uint8_t((currentSector >> 8) & 0xFF),
uint8_t((currentSector >> 16) & 0xFF), uint8_t((currentSector >> 16) & 0xFF),

View File

@ -4,25 +4,25 @@ using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> NullDriver::readLogicalDisk(Communication&, device_eventhandler_t report, std::optional<uint64_t> NullDriver::readLogicalDisk(Communication&, device_eventhandler_t report,
uint64_t, uint8_t*, uint64_t, std::chrono::milliseconds) { uint64_t, uint8_t*, uint64_t, std::chrono::milliseconds, MemoryType) {
report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error); report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
} }
std::optional<uint64_t> NullDriver::readLogicalDiskAligned(Communication&, device_eventhandler_t report, std::optional<uint64_t> NullDriver::readLogicalDiskAligned(Communication&, device_eventhandler_t report,
uint64_t, uint8_t*, uint64_t, std::chrono::milliseconds) { uint64_t, uint8_t*, uint64_t, std::chrono::milliseconds, MemoryType) {
report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error); report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
} }
std::optional<uint64_t> NullDriver::writeLogicalDisk(Communication&, device_eventhandler_t report, ReadDriver&, std::optional<uint64_t> NullDriver::writeLogicalDisk(Communication&, device_eventhandler_t report, ReadDriver&,
uint64_t, const uint8_t*, uint64_t, std::chrono::milliseconds) { uint64_t, const uint8_t*, uint64_t, std::chrono::milliseconds, MemoryType) {
report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error); report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
} }
std::optional<uint64_t> NullDriver::writeLogicalDiskAligned(Communication&, device_eventhandler_t report, std::optional<uint64_t> NullDriver::writeLogicalDiskAligned(Communication&, device_eventhandler_t report,
uint64_t, const uint8_t*, uint64_t, std::chrono::milliseconds) { uint64_t, const uint8_t*, uint64_t, std::chrono::milliseconds, MemoryType) {
report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error); report(APIEvent::Type::DiskNotSupported, APIEvent::Severity::Error);
return std::nullopt; return std::nullopt;
} }

View File

@ -7,7 +7,7 @@ using namespace icsneo;
using namespace icsneo::Disk; using namespace icsneo::Disk;
std::optional<uint64_t> PlasionDiskReadDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> PlasionDiskReadDriver::readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType) {
static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead); static std::shared_ptr<MessageFilter> NeoMemorySDRead = std::make_shared<MessageFilter>(Network::NetID::NeoMemorySDRead);
if(amount > getBlockSizeBounds().second) if(amount > getBlockSizeBounds().second)

View File

@ -91,6 +91,8 @@ public:
WiVIUploadStackOverflow = 0x2037, WiVIUploadStackOverflow = 0x2037,
I2CMessageExceedsMaxLength = 0x2038, I2CMessageExceedsMaxLength = 0x2038,
A2BMessageIncompleteFrame = 0x2039, A2BMessageIncompleteFrame = 0x2039,
CoreminiUploadVersionMismatch = 0x2040,
DiskNotConnected = 0x2041,
// Transport Events // Transport Events
FailedToRead = 0x3000, FailedToRead = 0x3000,

View File

@ -55,6 +55,8 @@ namespace icsneo {
class DeviceExtension; class DeviceExtension;
typedef uint64_t MemoryAddress;
class Device { class Device {
public: public:
virtual ~Device(); virtual ~Device();
@ -135,10 +137,34 @@ public:
NoScript, NoScript,
}; };
int8_t prepareScriptLoad(); int8_t prepareScriptLoad();
bool startScript(); bool startScript(Disk::MemoryType memType = Disk::MemoryType::SD);
bool stopScript(); bool stopScript();
bool clearScript(); bool clearScript();
bool uploadCoremini(std::unique_ptr<std::istream>&& stream, Disk::MemoryType memType = Disk::MemoryType::SD);
virtual std::optional<MemoryAddress> getCoreminiStartAddressFlash() const {
return std::nullopt;
}
virtual std::optional<MemoryAddress> getCoreminiStartAddressSD() const {
return std::nullopt;
}
std::optional<MemoryAddress> getCoreminiStartAddress(Disk::MemoryType memType) const {
switch(memType) {
case Disk::MemoryType::Flash:
return getCoreminiStartAddressFlash();
case Disk::MemoryType::SD:
return getCoreminiStartAddressSD();
default:
break;
}
return std::nullopt;
}
// Message polling related functions // Message polling related functions
bool enableMessagePolling(); bool enableMessagePolling();
@ -173,6 +199,8 @@ public:
virtual size_t getNetworkCountByType(Network::Type) const; virtual size_t getNetworkCountByType(Network::Type) const;
virtual Network getNetworkByNumber(Network::Type, size_t) const; virtual Network getNetworkByNumber(Network::Type, size_t) const;
/** /**
* Read from the logical disk in this device, starting from byte `pos` * Read from the logical disk in this device, starting from byte `pos`
* and reading up to `amount` bytes. * and reading up to `amount` bytes.
@ -188,7 +216,7 @@ public:
* set in icsneo::GetLastError(). * set in icsneo::GetLastError().
*/ */
std::optional<uint64_t> readLogicalDisk(uint64_t pos, uint8_t* into, uint64_t amount, std::optional<uint64_t> readLogicalDisk(uint64_t pos, uint8_t* into, uint64_t amount,
std::chrono::milliseconds timeout = Disk::DefaultTimeout); std::chrono::milliseconds timeout = Disk::DefaultTimeout, Disk::MemoryType memType = Disk::MemoryType::SD);
/** /**
* Write to the logical disk in this device, starting from byte `pos` * Write to the logical disk in this device, starting from byte `pos`
@ -205,7 +233,7 @@ public:
* set in icsneo::GetLastError(). * set in icsneo::GetLastError().
*/ */
std::optional<uint64_t> writeLogicalDisk(uint64_t pos, const uint8_t* from, uint64_t amount, std::optional<uint64_t> writeLogicalDisk(uint64_t pos, const uint8_t* from, uint64_t amount,
std::chrono::milliseconds timeout = Disk::DefaultTimeout); std::chrono::milliseconds timeout = Disk::DefaultTimeout, Disk::MemoryType memType = Disk::MemoryType::SD);
/** /**
* Check if the logical disk is connected. This means the disk is inserted, * Check if the logical disk is connected. This means the disk is inserted,

View File

@ -45,6 +45,15 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 2048 * 512;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -36,6 +36,14 @@ private:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 2048 * 512;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -36,6 +36,14 @@ private:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 2048 * 512;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -69,6 +69,14 @@ private:
// The supported TX networks are the same as the supported RX networks for this device // The supported TX networks are the same as the supported RX networks for this device
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 4 * 512;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -129,6 +129,14 @@ protected:
ethActivationStatus = status->ethernetActivationLineEnabled; ethActivationStatus = status->ethernetActivationLineEnabled;
usbHostPowerStatus = status->usbHostPowerEnabled; usbHostPowerStatus = status->usbHostPowerEnabled;
} }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 4608 * 512;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -74,6 +74,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool supportsWiVI() const override { return true; } bool supportsWiVI() const override { return true; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 33*1024*1024;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -76,6 +76,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool supportsWiVI() const override { return true; } bool supportsWiVI() const override { return true; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -59,6 +59,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool supportsWiVI() const override { return true; } bool supportsWiVI() const override { return true; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 33*1024*1024;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -35,6 +35,10 @@ private:
1 // 2 1 // 2
); );
} }
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -33,6 +33,10 @@ private:
1 // 3 1 // 3
); );
} }
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -7,6 +7,7 @@
#include "icsneo/device/devicetype.h" #include "icsneo/device/devicetype.h"
#include "icsneo/communication/packetizer.h" #include "icsneo/communication/packetizer.h"
#include "icsneo/communication/decoder.h" #include "icsneo/communication/decoder.h"
#include "icsneo/disk/neomemorydiskdriver.h"
#include "icsneo/device/tree/rada2b/rada2bsettings.h" #include "icsneo/device/tree/rada2b/rada2bsettings.h"
namespace icsneo { namespace icsneo {
@ -40,7 +41,7 @@ public:
protected: protected:
RADA2B(neodevice_t neodevice, const driver_factory_t& makeDriver) : Device(neodevice) { RADA2B(neodevice_t neodevice, const driver_factory_t& makeDriver) : Device(neodevice) {
initialize<RADA2BSettings>(makeDriver); initialize<RADA2BSettings, Disk::NeoMemoryDiskDriver, Disk::NeoMemoryDiskDriver>(makeDriver);
} }
void setupPacketizer(Packetizer& packetizer) override { void setupPacketizer(Packetizer& packetizer) override {
@ -66,6 +67,14 @@ protected:
// The supported TX networks are the same as the supported RX networks for this device // The supported TX networks are the same as the supported RX networks for this device
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 15*1024*1024;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -41,6 +41,14 @@ protected:
// The supported TX networks are the same as the supported RX networks for this device // The supported TX networks are the same as the supported RX networks for this device
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 14*1024*1024;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -89,6 +89,14 @@ protected:
const radgalaxy_status_t* status = reinterpret_cast<const radgalaxy_status_t*>(message->data.data()); const radgalaxy_status_t* status = reinterpret_cast<const radgalaxy_status_t*>(message->data.data());
ethActivationStatus = status->ethernetActivationLineEnabled; ethActivationStatus = status->ethernetActivationLineEnabled;
} }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -98,6 +98,14 @@ protected:
const radgigastar_status_t* status = reinterpret_cast<const radgigastar_status_t*>(message->data.data()); const radgigastar_status_t* status = reinterpret_cast<const radgigastar_status_t*>(message->data.data());
ethActivationStatus = status->ethernetActivationLineEnabled; ethActivationStatus = status->ethernetActivationLineEnabled;
} }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -49,6 +49,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*2048;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -86,6 +86,14 @@ protected:
const radmars_status_t* status = reinterpret_cast<const radmars_status_t*>(message->data.data()); const radmars_status_t* status = reinterpret_cast<const radmars_status_t*>(message->data.data());
ethActivationStatus = status->ethernetActivationLineEnabled; ethActivationStatus = status->ethernetActivationLineEnabled;
} }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -81,6 +81,14 @@ protected:
} }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -45,6 +45,13 @@ protected:
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*2048;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -54,6 +54,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*2048;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -57,6 +57,14 @@ protected:
// The supported TX networks are the same as the supported RX networks for this device // The supported TX networks are the same as the supported RX networks for this device
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -79,6 +79,14 @@ protected:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*4;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -36,6 +36,14 @@ private:
void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); } void setupSupportedTXNetworks(std::vector<Network>& txNetworks) override { setupSupportedRXNetworks(txNetworks); }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*2048;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -21,6 +21,14 @@ protected:
} }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*2048;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -33,6 +33,14 @@ protected:
} }
bool requiresVehiclePower() const override { return false; } bool requiresVehiclePower() const override { return false; }
std::optional<MemoryAddress> getCoreminiStartAddressFlash() const override {
return 512*128;
}
std::optional<MemoryAddress> getCoreminiStartAddressSD() const override {
return 0;
}
}; };
} }

View File

@ -19,6 +19,12 @@ enum class Access {
VSA VSA
}; };
enum class MemoryType : uint8_t
{
Flash = 0,
SD = 1
};
/** /**
* Interface for drivers which work with block data on devices * Interface for drivers which work with block data on devices
*/ */

View File

@ -20,10 +20,10 @@ namespace Disk {
class ReadDriver : public virtual Driver { class ReadDriver : public virtual Driver {
public: public:
virtual std::optional<uint64_t> readLogicalDisk(Communication& com, device_eventhandler_t report, virtual std::optional<uint64_t> readLogicalDisk(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout); uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout, MemoryType memType = MemoryType::SD);
void invalidateCache(uint64_t pos = 0, void invalidateCache(uint64_t pos = 0,
uint64_t amount = std::numeric_limits<uint32_t>::max() /* large value, but avoid overflow */); uint64_t amount = std::numeric_limits<uint32_t>::max() /* large value, but avoid overflow */, MemoryType memType = MemoryType::SD);
protected: protected:
/** /**
@ -33,16 +33,19 @@ protected:
* within the block size bounds provided by the driver. * within the block size bounds provided by the driver.
*/ */
virtual std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report, virtual std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) = 0; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) = 0;
private: private:
std::vector<uint8_t> cache; std::vector<uint8_t> cacheSD;
uint64_t cachePos = 0; std::vector<uint8_t> cacheEEPROM;
uint64_t cachePosSD = 0;
uint64_t cachePosEEPROM = 0;
std::chrono::time_point<std::chrono::steady_clock> cachedAt; std::chrono::time_point<std::chrono::steady_clock> cachedAt;
static constexpr const std::chrono::milliseconds CacheTime = std::chrono::milliseconds(1000); static constexpr const std::chrono::milliseconds CacheTime = std::chrono::milliseconds(1000);
std::optional<uint64_t> readFromCache(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds staleAfter = CacheTime); std::optional<uint64_t> readFromCache(uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds staleAfter = CacheTime, MemoryType memType = MemoryType::SD);
}; };
} // namespace Disk } // namespace Disk

View File

@ -20,7 +20,7 @@ namespace Disk {
class WriteDriver : public virtual Driver { class WriteDriver : public virtual Driver {
public: public:
virtual std::optional<uint64_t> writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver, virtual std::optional<uint64_t> writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout); uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout, MemoryType memType = MemoryType::SD);
protected: protected:
/** /**
@ -30,7 +30,7 @@ protected:
* within the block size bounds provided by the driver. * within the block size bounds provided by the driver.
*/ */
virtual std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report, virtual std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) = 0; uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) = 0;
}; };
} // namespace Disk } // namespace Disk

View File

@ -29,10 +29,10 @@ private:
Access getPossibleAccess() const override { return Access::EntireCard; } Access getPossibleAccess() const override { return Access::EntireCard; }
std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
std::optional<uint64_t> attemptReadLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> attemptReadLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout); uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD);
}; };
} // namespace Disk } // namespace Disk

View File

@ -31,10 +31,10 @@ private:
Access getPossibleAccess() const override { return Access::VSA; } Access getPossibleAccess() const override { return Access::VSA; }
std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
}; };
} // namespace Disk } // namespace Disk

View File

@ -19,9 +19,9 @@ namespace Disk {
class NullDriver : public ReadDriver, public WriteDriver { class NullDriver : public ReadDriver, public WriteDriver {
public: public:
std::optional<uint64_t> readLogicalDisk(Communication& com, device_eventhandler_t report, std::optional<uint64_t> readLogicalDisk(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout) override; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout, MemoryType memType = MemoryType::SD) override;
std::optional<uint64_t> writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver, std::optional<uint64_t> writeLogicalDisk(Communication& com, device_eventhandler_t report, ReadDriver& readDriver,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout) override; uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout = DefaultTimeout, MemoryType memType = MemoryType::SD) override;
std::pair<uint32_t, uint32_t> getBlockSizeBounds() const override { std::pair<uint32_t, uint32_t> getBlockSizeBounds() const override {
static_assert(SectorSize <= std::numeric_limits<uint32_t>::max(), "Incorrect sector size"); static_assert(SectorSize <= std::numeric_limits<uint32_t>::max(), "Incorrect sector size");
static_assert(SectorSize >= std::numeric_limits<uint32_t>::min(), "Incorrect sector size"); static_assert(SectorSize >= std::numeric_limits<uint32_t>::min(), "Incorrect sector size");
@ -32,9 +32,9 @@ private:
Access getPossibleAccess() const override { return Access::None; } Access getPossibleAccess() const override { return Access::None; }
std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> writeLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, const uint8_t* from, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
}; };
} // namespace Disk } // namespace Disk

View File

@ -28,7 +28,7 @@ private:
Access getPossibleAccess() const override { return Access::EntireCard; } Access getPossibleAccess() const override { return Access::EntireCard; }
std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report, std::optional<uint64_t> readLogicalDiskAligned(Communication& com, device_eventhandler_t report,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout) override; uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds timeout, MemoryType memType = MemoryType::SD) override;
}; };
} // namespace Disk } // namespace Disk

View File

@ -18,7 +18,7 @@ public:
std::pair<uint32_t, uint32_t> getBlockSizeBounds() const override { return { 8, 256 }; } std::pair<uint32_t, uint32_t> getBlockSizeBounds() const override { return { 8, 256 }; }
std::optional<uint64_t> readLogicalDiskAligned(Communication&, device_eventhandler_t, std::optional<uint64_t> readLogicalDiskAligned(Communication&, device_eventhandler_t,
uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds) override { uint64_t pos, uint8_t* into, uint64_t amount, std::chrono::milliseconds, Disk::MemoryType) override {
readCalls++; readCalls++;
EXPECT_EQ(pos % getBlockSizeBounds().first, 0); // Ensure the alignment rules are respected EXPECT_EQ(pos % getBlockSizeBounds().first, 0); // Ensure the alignment rules are respected
@ -40,7 +40,7 @@ public:
} }
std::optional<uint64_t> writeLogicalDiskAligned(Communication&, device_eventhandler_t report, uint64_t pos, std::optional<uint64_t> writeLogicalDiskAligned(Communication&, device_eventhandler_t report, uint64_t pos,
const uint8_t* from, uint64_t amount, std::chrono::milliseconds) override { const uint8_t* from, uint64_t amount, std::chrono::milliseconds, Disk::MemoryType) override {
writeCalls++; writeCalls++;
EXPECT_EQ(pos % getBlockSizeBounds().first, 0); // Ensure the alignment rules are respected EXPECT_EQ(pos % getBlockSizeBounds().first, 0); // Ensure the alignment rules are respected