Memory management update, SonarCloud fixes, fix for issue #841 (#842)

- Memory management updates, more fixed Sonar issues
* Replaced macros, fixed other sonar issues
* Added const, replaced enum with a single value by constant
* Updated object initializations
* Fixed potential strncpy overflow reported by gcc 8.3
This commit is contained in:
Uwe Seimet 2022-09-15 23:01:10 +02:00 committed by GitHub
parent e64c2f7254
commit 241e739d3a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
51 changed files with 533 additions and 712 deletions

View File

@ -13,6 +13,7 @@
#include "phase_handler.h" #include "phase_handler.h"
#include <unordered_map> #include <unordered_map>
#include <memory>
using namespace std; using namespace std;
@ -57,7 +58,7 @@ public:
unordered_map<int, PrimaryDevice *> luns; unordered_map<int, PrimaryDevice *> luns;
}; };
AbstractController(BUS *bus, int target_id) : bus(bus), target_id(target_id) {} AbstractController(shared_ptr<BUS> bus, int target_id) : bus(bus), target_id(target_id) {}
~AbstractController() override = default; ~AbstractController() override = default;
AbstractController(AbstractController&) = delete; AbstractController(AbstractController&) = delete;
AbstractController& operator=(const AbstractController&) = delete; AbstractController& operator=(const AbstractController&) = delete;
@ -91,7 +92,7 @@ public:
protected: protected:
BUS *bus; shared_ptr<BUS> bus;
ctrl_t ctrl = {}; ctrl_t ctrl = {};

View File

@ -15,31 +15,24 @@
using namespace std; using namespace std;
unordered_map<int, AbstractController *> ControllerManager::controllers;
ControllerManager::~ControllerManager()
{
DeleteAllControllersAndDevices();
}
ControllerManager& ControllerManager::instance() ControllerManager& ControllerManager::instance()
{ {
static ControllerManager instance; static ControllerManager instance;
return instance; return instance;
} }
bool ControllerManager::CreateScsiController(BUS *bus, PrimaryDevice *device) bool ControllerManager::CreateScsiController(shared_ptr<BUS> bus, PrimaryDevice *device) const
{ {
AbstractController *controller = FindController(device->GetId()); shared_ptr<AbstractController> controller = FindController(device->GetId());
if (controller == nullptr) { if (controller == nullptr) {
controller = make_unique<ScsiController>(bus, device->GetId()).release(); controller = make_shared<ScsiController>(bus, device->GetId());
controllers[device->GetId()] = controller; controllers[device->GetId()] = controller;
} }
return controller->AddDevice(device); return controller->AddDevice(device);
} }
AbstractController *ControllerManager::IdentifyController(int data) const shared_ptr<AbstractController> ControllerManager::IdentifyController(int data) const
{ {
for (const auto& [id, controller] : controllers) { for (const auto& [id, controller] : controllers) {
if (data & (1 << controller->GetTargetId())) { if (data & (1 << controller->GetTargetId())) {
@ -50,26 +43,18 @@ AbstractController *ControllerManager::IdentifyController(int data) const
return nullptr; return nullptr;
} }
AbstractController *ControllerManager::FindController(int target_id) const shared_ptr<AbstractController> ControllerManager::FindController(int target_id) const
{ {
const auto& it = controllers.find(target_id); const auto& it = controllers.find(target_id);
return it == controllers.end() ? nullptr : it->second; return it == controllers.end() ? nullptr : it->second;
} }
void ControllerManager::DeleteAllControllersAndDevices() void ControllerManager::DeleteAllControllers() const
{ {
for (const auto& [id, controller] : controllers) {
delete controller;
}
controllers.clear(); controllers.clear();
DeviceFactory::instance().DeleteAllDevices();
FileSupport::UnreserveAll();
} }
void ControllerManager::ResetAllControllers() void ControllerManager::ResetAllControllers() const
{ {
for (const auto& [id, controller] : controllers) { for (const auto& [id, controller] : controllers) {
controller->Reset(); controller->Reset();

View File

@ -12,6 +12,9 @@
#pragma once #pragma once
#include <unordered_map> #include <unordered_map>
#include <memory>
using namespace std;
class BUS; class BUS;
class AbstractController; class AbstractController;
@ -20,7 +23,7 @@ class PrimaryDevice;
class ControllerManager class ControllerManager
{ {
ControllerManager() = default; ControllerManager() = default;
~ControllerManager(); ~ControllerManager() = default;
ControllerManager(ControllerManager&) = delete; ControllerManager(ControllerManager&) = delete;
ControllerManager& operator=(const ControllerManager&) = delete; ControllerManager& operator=(const ControllerManager&) = delete;
@ -30,12 +33,12 @@ public:
static ControllerManager& instance(); static ControllerManager& instance();
bool CreateScsiController(BUS *, PrimaryDevice *); bool CreateScsiController(shared_ptr<BUS>, PrimaryDevice *) const;
AbstractController *IdentifyController(int) const; shared_ptr<AbstractController> IdentifyController(int) const;
AbstractController *FindController(int) const; shared_ptr<AbstractController> FindController(int) const;
void DeleteAllControllersAndDevices(); void DeleteAllControllers() const;
void ResetAllControllers(); void ResetAllControllers() const;
PrimaryDevice *GetDeviceByIdAndLun(int, int) const; PrimaryDevice *GetDeviceByIdAndLun(int, int) const;
static std::unordered_map<int, AbstractController *> controllers; inline static unordered_map<int, shared_ptr<AbstractController>> controllers;
}; };

View File

@ -24,7 +24,7 @@
using namespace scsi_defs; using namespace scsi_defs;
ScsiController::ScsiController(BUS *bus, int target_id) : AbstractController(bus, target_id) ScsiController::ScsiController(shared_ptr<BUS> bus, int target_id) : AbstractController(bus, target_id)
{ {
// The initial buffer size will default to either the default buffer size OR // The initial buffer size will default to either the default buffer size OR
// the size of an Ethernet message, whichever is larger. // the size of an Ethernet message, whichever is larger.
@ -57,7 +57,7 @@ void ScsiController::Reset()
bytes_to_transfer = 0; bytes_to_transfer = 0;
// Reset all LUNs // Reset all LUNs
for (auto& [lun, device] : ctrl.luns) { for (const auto& [lun, device] : ctrl.luns) {
device->Reset(); device->Reset();
} }
} }
@ -564,12 +564,10 @@ void ScsiController::Send()
bool result = true; bool result = true;
// Processing after data collection (read/data-in only) // Processing after data collection (read/data-in only)
if (ctrl.phase == BUS::datain) { if (ctrl.phase == BUS::datain && ctrl.blocks != 0) {
if (ctrl.blocks != 0) { // set next buffer (set offset, length)
// set next buffer (set offset, length) result = XferIn(ctrl.buffer);
result = XferIn(ctrl.buffer); LOGTRACE("%s%s", __PRETTY_FUNCTION__, (" Processing after data collection. Blocks: " + to_string(ctrl.blocks)).c_str())
LOGTRACE("%s%s", __PRETTY_FUNCTION__, (" Processing after data collection. Blocks: " + to_string(ctrl.blocks)).c_str())
}
} }
// If result FALSE, move to status phase // If result FALSE, move to status phase

View File

@ -69,7 +69,7 @@ class ScsiController : public AbstractController
public: public:
ScsiController(BUS *, int); ScsiController(shared_ptr<BUS>, int);
~ScsiController() override; ~ScsiController() override;
ScsiController(ScsiController&) = delete; ScsiController(ScsiController&) = delete;
ScsiController& operator=(const ScsiController&) = delete; ScsiController& operator=(const ScsiController&) = delete;

View File

@ -202,17 +202,6 @@ void Human68k::namests_t::GetCopyFilename(BYTE* szFilename) const
// //
//=========================================================================== //===========================================================================
CHostDrv::CHostDrv()
{
m_bWriteProtect = FALSE;
m_bEnable = FALSE;
m_capCache.sectors = 0;
m_bVolumeCache = FALSE;
m_szVolumeCache[0] = _T('\0');
m_szBase[0] = _T('\0');
m_nRing = 0;
}
CHostDrv::~CHostDrv() CHostDrv::~CHostDrv()
{ {
CHostPath* p; CHostPath* p;
@ -248,6 +237,8 @@ void CHostDrv::Init(const TCHAR* szBase, DWORD nFlag)
ASSERT(m_cRing.Prev() == &m_cRing); ASSERT(m_cRing.Prev() == &m_cRing);
ASSERT(m_nRing == 0); ASSERT(m_nRing == 0);
m_capCache.sectors = 0;
// Receive parameters // Receive parameters
if (nFlag & FSFLAG_WRITE_PROTECT) if (nFlag & FSFLAG_WRITE_PROTECT)
m_bWriteProtect = TRUE; m_bWriteProtect = TRUE;
@ -726,7 +717,7 @@ BOOL CHostDrv::Find(CHostFiles* pFiles)
ASSERT(pFiles); ASSERT(pFiles);
// Get path name and build cache // Get path name and build cache
CHostPath* pPath = CopyCache(pFiles); const CHostPath* pPath = CopyCache(pFiles);
if (pPath == nullptr) { if (pPath == nullptr) {
pPath = MakeCache(pFiles); pPath = MakeCache(pFiles);
if (pPath == nullptr) { if (pPath == nullptr) {
@ -764,13 +755,6 @@ BOOL CHostDrv::Find(CHostFiles* pFiles)
// //
//=========================================================================== //===========================================================================
CHostFilename::CHostFilename()
{
m_bCorrect = FALSE;
m_pszHumanExt = FALSE;
m_pszHumanLast = FALSE;
}
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// //
/// Set host side name /// Set host side name
@ -861,8 +845,8 @@ void CHostFilename::ConvertHuman(int nCount)
// Char conversion // Char conversion
BYTE szHuman[FILEPATH_MAX]; BYTE szHuman[FILEPATH_MAX];
const BYTE* pFirst = szHuman; const BYTE* pFirst = szHuman;
const BYTE* pLast; BYTE* pLast;
const BYTE* pExt = nullptr; BYTE* pExt = nullptr;
{ {
strcpy(szHost, m_szHost); strcpy(szHost, m_szHost);
@ -934,15 +918,14 @@ void CHostFilename::ConvertHuman(int nCount)
// Delete spaces at the end // Delete spaces at the end
while (pExt < pLast - 1 && *(pLast - 1) == ' ') { while (pExt < pLast - 1 && *(pLast - 1) == ' ') {
pLast--; pLast--;
auto p = (BYTE*)pLast; auto p = pLast;
*p = '\0'; *p = '\0';
} }
// Delete if the file name disappeared after conversion // Delete if the file name disappeared after conversion
if (pExt + 1 >= pLast) { if (pExt + 1 >= pLast) {
pLast = pExt; pLast = pExt;
auto p = (BYTE*)pLast; *pLast = '\0'; // Just in case
*p = '\0'; // Just in case
} }
} else { } else {
pExt = pLast; pExt = pLast;
@ -1065,7 +1048,7 @@ void CHostFilename::CopyHuman(const BYTE* szHuman)
void CHostFilename::SetEntryName() void CHostFilename::SetEntryName()
{ {
// Set file name // Set file name
BYTE* p = m_szHuman; const BYTE* p = m_szHuman;
size_t i; size_t i;
for (i = 0; i < 8; i++) { for (i = 0; i < 8; i++) {
if (p < m_pszHumanExt) if (p < m_pszHumanExt)
@ -1098,7 +1081,7 @@ void CHostFilename::SetEntryName()
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostFilename::isReduce() const BOOL CHostFilename::isReduce() const
{ {
return strcmp((char *)m_szHost, (char*)m_szHuman) != 0; return strcmp((const char *)m_szHost, (const char*)m_szHuman) != 0;
} }
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
@ -1150,18 +1133,6 @@ const BYTE* CHostFilename::SeparateExt(const BYTE* szHuman) // static
DWORD CHostPath::g_nId; ///< Identifier creation counter DWORD CHostPath::g_nId; ///< Identifier creation counter
CHostPath::CHostPath()
{
m_bRefresh = TRUE;
m_nId = 0;
m_tBackup = FALSE;
#ifdef _DEBUG
// Initialization is not required because this value always gets updated (used for debugging or initialization operation)
m_nId = 0;
#endif // _DEBUG
}
CHostPath::~CHostPath() CHostPath::~CHostPath()
{ {
Clean(); Clean();
@ -1739,22 +1710,13 @@ void CHostPath::Release()
// //
//=========================================================================== //===========================================================================
CHostEntry::CHostEntry()
{
for (size_t n = 0; n < DriveMax; n++) {
m_pDrv[n] = nullptr;
}
m_nTimeout = 0;
}
CHostEntry::~CHostEntry() CHostEntry::~CHostEntry()
{ {
Clean(); Clean();
#ifdef _DEBUG #ifdef _DEBUG
// Confirm object // Confirm object
for (size_t n = 0; n < DriveMax; n++) { for (size_t n = 0; n < DRIVE_MAX; n++) {
ASSERT(m_pDrv[n] == nullptr); ASSERT(m_pDrv[n] == nullptr);
} }
#endif // _DEBUG #endif // _DEBUG
@ -1765,15 +1727,15 @@ CHostEntry::~CHostEntry()
/// Initialize (when the driver is installed) /// Initialize (when the driver is installed)
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::Init() void CHostEntry::Init() const
{ {
#ifdef _DEBUG #ifdef _DEBUG
// Confirm object // Confirm object
for (size_t n = 0; n < DriveMax; n++) { for (size_t n = 0; n < DRIVE_MAX; n++) {
ASSERT(m_pDrv[n] == nullptr); ASSERT(m_pDrv[n] == nullptr);
} }
#endif // _DEBUG #endif
} }
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
@ -1785,7 +1747,7 @@ void CHostEntry::Clean()
{ {
// Delete object // Delete object
for (size_t n = 0; n < DriveMax; n++) { for (size_t n = 0; n < DRIVE_MAX; n++) {
delete m_pDrv[n]; delete m_pDrv[n];
m_pDrv[n] = nullptr; m_pDrv[n] = nullptr;
} }
@ -1796,10 +1758,10 @@ void CHostEntry::Clean()
/// Update all cache /// Update all cache
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::CleanCache() void CHostEntry::CleanCache() const
{ {
for (size_t i = 0; i < DriveMax; i++) { for (size_t i = 0; i < DRIVE_MAX; i++) {
if (m_pDrv[i]) if (m_pDrv[i])
m_pDrv[i]->CleanCache(); m_pDrv[i]->CleanCache();
} }
@ -1812,9 +1774,9 @@ void CHostEntry::CleanCache()
/// Update the cache for the specified unit /// Update the cache for the specified unit
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::CleanCache(DWORD nUnit) void CHostEntry::CleanCache(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->CleanCache(); m_pDrv[nUnit]->CleanCache();
@ -1825,10 +1787,10 @@ void CHostEntry::CleanCache(DWORD nUnit)
/// Update the cache for the specified path /// Update the cache for the specified path
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::CleanCache(DWORD nUnit, const BYTE* szHumanPath) void CHostEntry::CleanCache(DWORD nUnit, const BYTE* szHumanPath) const
{ {
ASSERT(szHumanPath); ASSERT(szHumanPath);
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->CleanCache(szHumanPath); m_pDrv[nUnit]->CleanCache(szHumanPath);
@ -1839,10 +1801,10 @@ void CHostEntry::CleanCache(DWORD nUnit, const BYTE* szHumanPath)
/// Update all cache for the specified path and below /// Update all cache for the specified path and below
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::CleanCacheChild(DWORD nUnit, const BYTE* szHumanPath) void CHostEntry::CleanCacheChild(DWORD nUnit, const BYTE* szHumanPath) const
{ {
ASSERT(szHumanPath); ASSERT(szHumanPath);
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->CleanCacheChild(szHumanPath); m_pDrv[nUnit]->CleanCacheChild(szHumanPath);
@ -1853,10 +1815,10 @@ void CHostEntry::CleanCacheChild(DWORD nUnit, const BYTE* szHumanPath)
/// Delete cache for the specified path /// Delete cache for the specified path
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::DeleteCache(DWORD nUnit, const BYTE* szHumanPath) void CHostEntry::DeleteCache(DWORD nUnit, const BYTE* szHumanPath) const
{ {
ASSERT(szHumanPath); ASSERT(szHumanPath);
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->DeleteCache(szHumanPath); m_pDrv[nUnit]->DeleteCache(szHumanPath);
@ -1870,7 +1832,7 @@ void CHostEntry::DeleteCache(DWORD nUnit, const BYTE* szHumanPath)
BOOL CHostEntry::Find(DWORD nUnit, CHostFiles* pFiles) const BOOL CHostEntry::Find(DWORD nUnit, CHostFiles* pFiles) const
{ {
ASSERT(pFiles); ASSERT(pFiles);
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->Find(pFiles); return m_pDrv[nUnit]->Find(pFiles);
@ -1883,7 +1845,7 @@ BOOL CHostEntry::Find(DWORD nUnit, CHostFiles* pFiles) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::SetDrv(DWORD nUnit, CHostDrv* pDrv) void CHostEntry::SetDrv(DWORD nUnit, CHostDrv* pDrv)
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit] == nullptr); ASSERT(m_pDrv[nUnit] == nullptr);
m_pDrv[nUnit] = pDrv; m_pDrv[nUnit] = pDrv;
@ -1896,7 +1858,7 @@ void CHostEntry::SetDrv(DWORD nUnit, CHostDrv* pDrv)
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::isWriteProtect(DWORD nUnit) const BOOL CHostEntry::isWriteProtect(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->isWriteProtect(); return m_pDrv[nUnit]->isWriteProtect();
@ -1909,7 +1871,7 @@ BOOL CHostEntry::isWriteProtect(DWORD nUnit) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::isEnable(DWORD nUnit) const BOOL CHostEntry::isEnable(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->isEnable(); return m_pDrv[nUnit]->isEnable();
@ -1922,7 +1884,7 @@ BOOL CHostEntry::isEnable(DWORD nUnit) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::isMediaOffline(DWORD nUnit) const BOOL CHostEntry::isMediaOffline(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->isMediaOffline(); return m_pDrv[nUnit]->isMediaOffline();
@ -1935,7 +1897,7 @@ BOOL CHostEntry::isMediaOffline(DWORD nUnit) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BYTE CHostEntry::GetMediaByte(DWORD nUnit) const BYTE CHostEntry::GetMediaByte(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->GetMediaByte(); return m_pDrv[nUnit]->GetMediaByte();
@ -1948,7 +1910,7 @@ BYTE CHostEntry::GetMediaByte(DWORD nUnit) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
DWORD CHostEntry::GetStatus(DWORD nUnit) const DWORD CHostEntry::GetStatus(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->GetStatus(); return m_pDrv[nUnit]->GetStatus();
@ -1961,7 +1923,7 @@ DWORD CHostEntry::GetStatus(DWORD nUnit) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::CheckMedia(DWORD nUnit) const BOOL CHostEntry::CheckMedia(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->CheckMedia(); return m_pDrv[nUnit]->CheckMedia();
@ -1972,9 +1934,9 @@ BOOL CHostEntry::CheckMedia(DWORD nUnit) const
/// Eject /// Eject
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::Eject(DWORD nUnit) void CHostEntry::Eject(DWORD nUnit) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->Eject(); m_pDrv[nUnit]->Eject();
@ -1985,9 +1947,9 @@ void CHostEntry::Eject(DWORD nUnit)
/// Get volume label /// Get volume label
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostEntry::GetVolume(DWORD nUnit, TCHAR* szLabel) void CHostEntry::GetVolume(DWORD nUnit, TCHAR* szLabel) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
m_pDrv[nUnit]->GetVolume(szLabel); m_pDrv[nUnit]->GetVolume(szLabel);
@ -2000,7 +1962,7 @@ void CHostEntry::GetVolume(DWORD nUnit, TCHAR* szLabel)
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::GetVolumeCache(DWORD nUnit, TCHAR* szLabel) const BOOL CHostEntry::GetVolumeCache(DWORD nUnit, TCHAR* szLabel) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->GetVolumeCache(szLabel); return m_pDrv[nUnit]->GetVolumeCache(szLabel);
@ -2013,7 +1975,7 @@ BOOL CHostEntry::GetVolumeCache(DWORD nUnit, TCHAR* szLabel) const
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
DWORD CHostEntry::GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const DWORD CHostEntry::GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->GetCapacity(pCapacity); return m_pDrv[nUnit]->GetCapacity(pCapacity);
@ -2026,7 +1988,7 @@ DWORD CHostEntry::GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) cons
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostEntry::GetCapacityCache(DWORD nUnit, Human68k::capacity_t* pCapacity) const BOOL CHostEntry::GetCapacityCache(DWORD nUnit, Human68k::capacity_t* pCapacity) const
{ {
ASSERT(nUnit < DriveMax); ASSERT(nUnit < DRIVE_MAX);
ASSERT(m_pDrv[nUnit]); ASSERT(m_pDrv[nUnit]);
return m_pDrv[nUnit]->GetCapacityCache(pCapacity); return m_pDrv[nUnit]->GetCapacityCache(pCapacity);
@ -2108,7 +2070,7 @@ void CHostFiles::SetPath(const Human68k::namests_t* pNamests)
/// Find file on the Human68k side and create data on the host side /// Find file on the Human68k side and create data on the host side
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CHostFiles::Find(DWORD nUnit, CHostEntry* pEntry) BOOL CHostFiles::Find(DWORD nUnit, const CHostEntry* pEntry)
{ {
ASSERT(pEntry); ASSERT(pEntry);
@ -2120,7 +2082,7 @@ BOOL CHostFiles::Find(DWORD nUnit, CHostEntry* pEntry)
/// Find file name /// Find file name
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
const CHostFilename* CHostFiles::Find(CHostPath* pPath) const CHostFilename* CHostFiles::Find(const CHostPath* pPath)
{ {
ASSERT(pPath); ASSERT(pPath);
@ -2282,12 +2244,6 @@ void CHostFilesManager::Free(CHostFiles* pFiles)
// //
//=========================================================================== //===========================================================================
void CHostFcb::Init()
{
m_bUpdate = FALSE;
m_pFile = nullptr;
}
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// //
/// Set file open mode /// Set file open mode
@ -2557,7 +2513,6 @@ CHostFcbManager::~CHostFcbManager()
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostFcbManager::Init() void CHostFcbManager::Init()
{ {
// Confirm that the entity does not exist (just in case) // Confirm that the entity does not exist (just in case)
ASSERT(m_cRing.Next() == &m_cRing); ASSERT(m_cRing.Next() == &m_cRing);
ASSERT(m_cRing.Prev() == &m_cRing); ASSERT(m_cRing.Prev() == &m_cRing);
@ -2575,9 +2530,8 @@ void CHostFcbManager::Init()
// Clean (at startup/reset) // Clean (at startup/reset)
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CHostFcbManager::Clean() void CHostFcbManager::Clean() const
{ {
// Fast task killer // Fast task killer
CRing* p; CRing* p;
while ((p = m_cRing.Next()) != &m_cRing) { while ((p = m_cRing.Next()) != &m_cRing) {
@ -2646,31 +2600,6 @@ void CHostFcbManager::Free(CHostFcb* pFcb)
DWORD CFileSys::g_nOption; // File name conversion flag DWORD CFileSys::g_nOption; // File name conversion flag
CFileSys::CFileSys()
{
m_nHostSectorCount = 0;
// Config data initialization
m_nDrives = 0;
for (size_t n = 0; n < DriveMax; n++) {
m_nFlag[n] = 0;
m_szBase[n][0] = _T('\0');
}
// Initialize TwentyOne option monitoring
m_nKernel = 0;
m_nKernelSearch = 0;
// Initialize operational flags
m_nOptionDefault = 0;
m_nOption = 0;
ASSERT(g_nOption == 0);
// Number of registered drives are 0
m_nUnits = 0;
}
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// //
/// Reset (close all) /// Reset (close all)
@ -2678,7 +2607,6 @@ CFileSys::CFileSys()
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CFileSys::Reset() void CFileSys::Reset()
{ {
// Initialize virtual sectors // Initialize virtual sectors
m_nHostSectorCount = 0; m_nHostSectorCount = 0;
memset(m_nHostSectorBuffer, 0, sizeof(m_nHostSectorBuffer)); memset(m_nHostSectorBuffer, 0, sizeof(m_nHostSectorBuffer));
@ -2707,7 +2635,6 @@ void CFileSys::Reset()
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void CFileSys::Init() void CFileSys::Init()
{ {
// Initialize file search memory (device startup and load) // Initialize file search memory (device startup and load)
m_cFiles.Init(); m_cFiles.Init();
@ -2755,7 +2682,6 @@ void CFileSys::Init()
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
DWORD CFileSys::InitDevice(const Human68k::argument_t* pArgument) DWORD CFileSys::InitDevice(const Human68k::argument_t* pArgument)
{ {
InitOption(pArgument); InitOption(pArgument);
// File system initialization // File system initialization
@ -2769,12 +2695,12 @@ DWORD CFileSys::InitDevice(const Human68k::argument_t* pArgument)
/// $41 - Directory check /// $41 - Directory check
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::CheckDir(DWORD nUnit, const Human68k::namests_t* pNamests) int CFileSys::CheckDir(DWORD nUnit, const Human68k::namests_t* pNamests) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive
@ -2796,12 +2722,12 @@ int CFileSys::CheckDir(DWORD nUnit, const Human68k::namests_t* pNamests)
/// $42 - Create directory /// $42 - Create directory
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::MakeDir(DWORD nUnit, const Human68k::namests_t* pNamests) int CFileSys::MakeDir(DWORD nUnit, const Human68k::namests_t* pNamests) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -2838,12 +2764,12 @@ int CFileSys::MakeDir(DWORD nUnit, const Human68k::namests_t* pNamests)
/// $43 - Delete directory /// $43 - Delete directory
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::RemoveDir(DWORD nUnit, const Human68k::namests_t* pNamests) int CFileSys::RemoveDir(DWORD nUnit, const Human68k::namests_t* pNamests) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -2888,12 +2814,12 @@ int CFileSys::RemoveDir(DWORD nUnit, const Human68k::namests_t* pNamests)
/// $44 - Change file name /// $44 - Change file name
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::Rename(DWORD nUnit, const Human68k::namests_t* pNamests, const Human68k::namests_t* pNamestsNew) int CFileSys::Rename(DWORD nUnit, const Human68k::namests_t* pNamests, const Human68k::namests_t* pNamestsNew) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -2946,12 +2872,12 @@ int CFileSys::Rename(DWORD nUnit, const Human68k::namests_t* pNamests, const Hum
/// $45 - Delete file /// $45 - Delete file
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::Delete(DWORD nUnit, const Human68k::namests_t* pNamests) int CFileSys::Delete(DWORD nUnit, const Human68k::namests_t* pNamests) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -2986,12 +2912,12 @@ int CFileSys::Delete(DWORD nUnit, const Human68k::namests_t* pNamests)
/// $46 - Get/set file attribute /// $46 - Get/set file attribute
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::Attribute(DWORD nUnit, const Human68k::namests_t* pNamests, DWORD nHumanAttribute) int CFileSys::Attribute(DWORD nUnit, const Human68k::namests_t* pNamests, DWORD nHumanAttribute) const
{ {
ASSERT(pNamests); ASSERT(pNamests);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3020,9 +2946,8 @@ int CFileSys::Attribute(DWORD nUnit, const Human68k::namests_t* pNamests, DWORD
return FS_FATAL_WRITEPROTECT; return FS_FATAL_WRITEPROTECT;
// Generate attribute // Generate attribute
DWORD nAttribute = (nHumanAttribute & Human68k::AT_READONLY) | if (DWORD nAttribute = (nHumanAttribute & Human68k::AT_READONLY) | (f.GetAttribute() & ~Human68k::AT_READONLY);
(f.GetAttribute() & ~Human68k::AT_READONLY); f.GetAttribute() != nAttribute) {
if (f.GetAttribute() != nAttribute) {
struct stat sb; //NOSONAR Cannot be declared in a separate statement because struct keyword is required struct stat sb; //NOSONAR Cannot be declared in a separate statement because struct keyword is required
if (stat(S2U(f.GetPath()), &sb)) if (stat(S2U(f.GetPath()), &sb))
return FS_FILENOTFND; return FS_FILENOTFND;
@ -3065,7 +2990,7 @@ int CFileSys::Files(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests
} }
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3150,7 +3075,7 @@ int CFileSys::NFiles(DWORD nUnit, DWORD nKey, Human68k::files_t* pFiles)
ASSERT(pFiles); ASSERT(pFiles);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3195,7 +3120,7 @@ int CFileSys::Create(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamest
ASSERT(pFcb); ASSERT(pFcb);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -3263,7 +3188,7 @@ int CFileSys::Open(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests,
ASSERT(pFcb); ASSERT(pFcb);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3327,12 +3252,12 @@ int CFileSys::Open(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests,
/// $4B - File close /// $4B - File close
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::Close(DWORD nUnit, DWORD nKey, Human68k::fcb_t* /* pFcb */) int CFileSys::Close(DWORD nUnit, DWORD nKey, const Human68k::fcb_t* /* pFcb */)
{ {
ASSERT(nKey); ASSERT(nKey);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3508,7 +3433,7 @@ DWORD CFileSys::TimeStamp(DWORD nUnit, DWORD nKey, Human68k::fcb_t* pFcb, DWORD
return ((DWORD)pFcb->date << 16) | pFcb->time; return ((DWORD)pFcb->date << 16) | pFcb->time;
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -3551,7 +3476,7 @@ int CFileSys::GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const
ASSERT(pCapacity); ASSERT(pCapacity);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -3570,12 +3495,12 @@ int CFileSys::GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const
/// $51 - Inspect/control drive status /// $51 - Inspect/control drive status
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
int CFileSys::CtrlDrive(DWORD nUnit, Human68k::ctrldrive_t* pCtrlDrive) int CFileSys::CtrlDrive(DWORD nUnit, Human68k::ctrldrive_t* pCtrlDrive) const
{ {
ASSERT(pCtrlDrive); ASSERT(pCtrlDrive);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive
@ -3618,7 +3543,7 @@ int CFileSys::GetDPB(DWORD nUnit, Human68k::dpb_t* pDpb) const
ASSERT(pDpb); ASSERT(pDpb);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
Human68k::capacity_t cap; Human68k::capacity_t cap;
@ -3698,7 +3623,7 @@ int CFileSys::DiskRead(DWORD nUnit, BYTE* pBuffer, DWORD nSector, DWORD nSize)
ASSERT(pBuffer); ASSERT(pBuffer);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive return FS_FATAL_MEDIAOFFLINE; // This occurs when resuming with an invalid drive
@ -3778,7 +3703,7 @@ int CFileSys::DiskRead(DWORD nUnit, BYTE* pBuffer, DWORD nSector, DWORD nSize)
int CFileSys::DiskWrite(DWORD nUnit) const int CFileSys::DiskWrite(DWORD nUnit) const
{ {
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -3806,7 +3731,7 @@ int CFileSys::Ioctrl(DWORD nUnit, DWORD nFunction, Human68k::ioctrl_t* pIoctrl)
ASSERT(pIoctrl); ASSERT(pIoctrl);
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive
@ -3870,7 +3795,7 @@ int CFileSys::Flush(DWORD nUnit) const
{ {
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_INVALIDFUNC; // Avoid triggering a fatal error returning from a mint command when resuming with an invalid drive return FS_INVALIDFUNC; // Avoid triggering a fatal error returning from a mint command when resuming with an invalid drive
@ -3888,7 +3813,7 @@ int CFileSys::CheckMedia(DWORD nUnit) const
{ {
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive return FS_INVALIDFUNC; // Avoid triggering a fatal error in mint when resuming with an invalid drive
@ -3911,7 +3836,7 @@ int CFileSys::Lock(DWORD nUnit) const
{ {
// Unit check // Unit check
if (nUnit >= DriveMax) if (nUnit >= CHostEntry::DRIVE_MAX)
return FS_FATAL_INVALIDUNIT; return FS_FATAL_INVALIDUNIT;
ASSERT(nUnit < m_nUnits); ASSERT(nUnit < m_nUnits);
if (nUnit >= m_nUnits) if (nUnit >= m_nUnits)
@ -3971,7 +3896,7 @@ void CFileSys::InitOption(const Human68k::argument_t* pArgument)
nMode = 0; nMode = 0;
} else if (c == '/') { } else if (c == '/') {
// Specify default base path // Specify default base path
if (m_nDrives < DriveMax) { if (m_nDrives < CHostEntry::DRIVE_MAX) {
p--; p--;
strcpy(m_szBase[m_nDrives], (const char *)p); strcpy(m_szBase[m_nDrives], (const char *)p);
m_nDrives++; m_nDrives++;
@ -4032,7 +3957,7 @@ void CFileSys::InitOption(const Human68k::argument_t* pArgument)
/// Get volume label /// Get volume label
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
BOOL CFileSys::FilesVolume(DWORD nUnit, Human68k::files_t* pFiles) BOOL CFileSys::FilesVolume(DWORD nUnit, Human68k::files_t* pFiles) const
{ {
ASSERT(pFiles); ASSERT(pFiles);

View File

@ -18,47 +18,47 @@
// Status code definitions // Status code definitions
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
#define FS_INVALIDFUNC 0xFFFFFFFF ///< Executed an invalid function static const int FS_INVALIDFUNC = 0xFFFFFFFF; ///< Executed an invalid function
#define FS_FILENOTFND 0xFFFFFFFE ///< The selected file can not be found static const int FS_FILENOTFND = 0xFFFFFFFE; ///< The selected file can not be found
#define FS_DIRNOTFND 0xFFFFFFFD ///< The selected directory can not be found static const int FS_DIRNOTFND = 0xFFFFFFFD; ///< The selected directory can not be found
#define FS_OVEROPENED 0xFFFFFFFC ///< There are too many files open static const int FS_OVEROPENED = 0xFFFFFFFC; ///< There are too many files open
#define FS_CANTACCESS 0xFFFFFFFB ///< Can not access the direcory or volume static const int FS_CANTACCESS = 0xFFFFFFFB; ///< Can not access the direcory or volume
#define FS_NOTOPENED 0xFFFFFFFA ///< The selected handle is not opened static const int FS_NOTOPENED = 0xFFFFFFFA; ///< The selected handle is not opened
#define FS_INVALIDMEM 0xFFFFFFF9 ///< Memory management has been destroyed static const int FS_INVALIDMEM = 0xFFFFFFF9; ///< Memory management has been destroyed
#define FS_OUTOFMEM 0xFFFFFFF8 ///< Insufficient memory for execution static const int FS_OUTOFMEM = 0xFFFFFFF8; ///< Insufficient memory for execution
#define FS_INVALIDPTR 0xFFFFFFF7 ///< Selected an invalid memory management pointer static const int FS_INVALIDPTR = 0xFFFFFFF7; ///< Selected an invalid memory management pointer
#define FS_INVALIDENV 0xFFFFFFF6 ///< Selected an invalid environment static const int FS_INVALIDENV = 0xFFFFFFF6; ///< Selected an invalid environment
#define FS_ILLEGALFMT 0xFFFFFFF5 ///< The exeucted file is in an invalid format static const int FS_ILLEGALFMT = 0xFFFFFFF5; ///< The exeucted file is in an invalid format
#define FS_ILLEGALMOD 0xFFFFFFF4 ///< Invalid open access mode static const int FS_ILLEGALMOD = 0xFFFFFFF4; ///< Invalid open access mode
#define FS_INVALIDPATH 0xFFFFFFF3 ///< Mistake in selected file name static const int FS_INVALIDPATH = 0xFFFFFFF3; ///< Mistake in selected file name
#define FS_INVALIDPRM 0xFFFFFFF2 ///< Called with an invalid parameter static const int FS_INVALIDPRM = 0xFFFFFFF2; ///< Called with an invalid parameter
#define FS_INVALIDDRV 0xFFFFFFF1 ///< Mistake in selected drive static const int FS_INVALIDDRV = 0xFFFFFFF1; ///< Mistake in selected drive
#define FS_DELCURDIR 0xFFFFFFF0 ///< Unable to delete the current directory static const int FS_DELCURDIR = 0xFFFFFFF0; ///< Unable to delete the current directory
#define FS_NOTIOCTRL 0xFFFFFFEF ///< Unable to use IOCTRL with the device static const int FS_NOTIOCTRL = 0xFFFFFFEF; ///< Unable to use IOCTRL with the device
#define FS_LASTFILE 0xFFFFFFEE ///< Can not find any more files static const int FS_LASTFILE = 0xFFFFFFEE; ///< Can not find any more files
#define FS_CANTWRITE 0xFFFFFFED ///< Selected file can not be written static const int FS_CANTWRITE = 0xFFFFFFED; ///< Selected file can not be written
#define FS_DIRALREADY 0xFFFFFFEC ///< Selected directory is already registered static const int FS_DIRALREADY = 0xFFFFFFEC; ///< Selected directory is already registered
#define FS_CANTDELETE 0xFFFFFFEB ///< Can not delete because of a file static const int FS_CANTDELETE = 0xFFFFFFEB; ///< Can not delete because of a file
#define FS_CANTRENAME 0xFFFFFFEA ///< Can not rename because of a file static const int FS_CANTRENAME = 0xFFFFFFEA; ///< Can not rename because of a file
#define FS_DISKFULL 0xFFFFFFE9 ///< Can not create a file because the disk is full static const int FS_DISKFULL = 0xFFFFFFE9; ///< Can not create a file because the disk is full
#define FS_DIRFULL 0xFFFFFFE8 ///< Can not create a file because the directory is full static const int FS_DIRFULL = 0xFFFFFFE8; ///< Can not create a file because the directory is full
#define FS_CANTSEEK 0xFFFFFFE7 ///< Can not seek in the selected location static const int FS_CANTSEEK = 0xFFFFFFE7; ///< Can not seek in the selected location
#define FS_SUPERVISOR 0xFFFFFFE6 ///< Selected supervisor in supervisor mode static const int FS_SUPERVISOR = 0xFFFFFFE6; ///< Selected supervisor in supervisor mode
#define FS_THREADNAME 0xFFFFFFE5 ///< A thread with this name already exists static const int FS_THREADNAME = 0xFFFFFFE5; ///< A thread with this name already exists
#define FS_BUFWRITE 0xFFFFFFE4 ///< Writing to inter-process communication buffers is disallowed static const int FS_BUFWRITE = 0xFFFFFFE4; ///< Writing to inter-process communication buffers is disallowed
#define FS_BACKGROUND 0xFFFFFFE3 ///< Unable to start a background process static const int FS_BACKGROUND = 0xFFFFFFE3; ///< Unable to start a background process
#define FS_OUTOFLOCK 0xFFFFFFE0 ///< Insufficient lock space static const int FS_OUTOFLOCK = 0xFFFFFFE0; ///< Insufficient lock space
#define FS_LOCKED 0xFFFFFFDF ///< Can not access because it is locked static const int FS_LOCKED = 0xFFFFFFDF; ///< Can not access because it is locked
#define FS_DRIVEOPENED 0xFFFFFFDE ///< Selected drive has an open handler static const int FS_DRIVEOPENED = 0xFFFFFFDE; ///< Selected drive has an open handler
#define FS_LINKOVER 0xFFFFFFDD ///< The symbolic link is nested over 16 times static const int FS_LINKOVER = 0xFFFFFFDD; ///< The symbolic link is nested over 16 times
#define FS_FILEEXIST 0xFFFFFFB0 ///< The file exists static const int FS_FILEEXIST = 0xFFFFFFB0; ///< The file exists
#define FS_FATAL_MEDIAOFFLINE 0xFFFFFFA3 ///< No media inserted static const int FS_FATAL_MEDIAOFFLINE = 0xFFFFFFA3; ///< No media inserted
#define FS_FATAL_WRITEPROTECT 0xFFFFFFA2 ///< Write protected static const int FS_FATAL_WRITEPROTECT = 0xFFFFFFA2; ///< Write protected
#define FS_FATAL_INVALIDCOMMAND 0xFFFFFFA1 ///< Invalid command number static const int FS_FATAL_INVALIDCOMMAND = 0xFFFFFFA1; ///< Invalid command number
#define FS_FATAL_INVALIDUNIT 0xFFFFFFA0 ///< Invalid unit number static const int FS_FATAL_INVALIDUNIT = 0xFFFFFFA0; ///< Invalid unit number
#define HUMAN68K_PATH_MAX 96 ///< Longest path allowed in Human68k static const int HUMAN68K_PATH_MAX = 96; ///< Longest path allowed in Human68k
//=========================================================================== //===========================================================================
// //
@ -236,7 +236,7 @@ deeply in the system, which is why this value is set this high.
Default is 20 buffers. Default is 20 buffers.
*/ */
#define XM6_HOST_FILES_MAX 20 static const int XM6_HOST_FILES_MAX = 20;
/// Number of FCB buffers /// Number of FCB buffers
/** /**
@ -244,7 +244,7 @@ This decides how many files can be opened at the same time.
Default is 100 files. Default is 100 files.
*/ */
#define XM6_HOST_FCB_MAX 100 static const int XM6_HOST_FCB_MAX = 100;
/// Max number of virtual clusters and sectors /// Max number of virtual clusters and sectors
/** /**
@ -253,7 +253,7 @@ Allocating a generous amount to exceed the number of threads lzdsys uses for acc
Default is 10 sectors. Default is 10 sectors.
*/ */
#define XM6_HOST_PSEUDO_CLUSTER_MAX 10 static const int XM6_HOST_PSEUDO_CLUSTER_MAX = 10;
/// Number of caches for directory entries /// Number of caches for directory entries
/** /**
@ -264,7 +264,7 @@ and the host OS gets under a heavy load, so be careful.
Default is 16. Default is 16.
*/ */
#define XM6_HOST_DIRENTRY_CACHE_MAX 16 static const int XM6_HOST_DIRENTRY_CACHE_MAX = 16;
/// Max number of entries that can be stored per directory /// Max number of entries that can be stored per directory
/** /**
@ -276,7 +276,7 @@ file manager, the upper limit is 2560 files. This is one good example to use as
Default is around 60000 entries. (Upper limit of the FAT root directory) Default is around 60000 entries. (Upper limit of the FAT root directory)
*/ */
#define XM6_HOST_DIRENTRY_FILE_MAX 65535 static const int XM6_HOST_DIRENTRY_FILE_MAX = 65535;
/// Max number of patterns for file name deduplication /// Max number of patterns for file name deduplication
/** /**
@ -295,7 +295,7 @@ only the first entry will ever be accessed.
Default is 36 patterns. Default is 36 patterns.
*/ */
#define XM6_HOST_FILENAME_PATTERN_MAX 36 static const int XM6_HOST_FILENAME_PATTERN_MAX = 36;
/// Duplicate file identification mark /// Duplicate file identification mark
/** /**
@ -304,7 +304,7 @@ Do not use a command shell escape character, or similar protected symbol.
Default is '@'. Default is '@'.
*/ */
#define XM6_HOST_FILENAME_MARK '@' static const char XM6_HOST_FILENAME_MARK = '@';
/// WINDRV operational flags /// WINDRV operational flags
/** /**
@ -440,47 +440,51 @@ private:
//=========================================================================== //===========================================================================
class CHostFilename { class CHostFilename {
public: public:
CHostFilename(); CHostFilename() = default;
static size_t Offset() { return offsetof(CHostFilename, m_szHost); } ///< Get offset location ~CHostFilename() = default;
CHostFilename(CHostFilename&) = delete;
CHostFilename& operator=(const CHostFilename&) = delete;
void SetHost(const TCHAR* szHost); ///< Set the name of the host static size_t Offset() { return offsetof(CHostFilename, m_szHost); } ///< Get offset location
const TCHAR* GetHost() const { return m_szHost; } ///< Get the name of the host
void ConvertHuman(int nCount = -1); ///< Convert the Human68k name void SetHost(const TCHAR* szHost); ///< Set the name of the host
void CopyHuman(const BYTE* szHuman); ///< Copy the Human68k name const TCHAR* GetHost() const { return m_szHost; } ///< Get the name of the host
BOOL isReduce() const; ///< Inspect if the Human68k name is generated void ConvertHuman(int nCount = -1); ///< Convert the Human68k name
BOOL isCorrect() const { return m_bCorrect; } ///< Inspect if the Human68k file name adhers to naming rules void CopyHuman(const BYTE* szHuman); ///< Copy the Human68k name
const BYTE* GetHuman() const { return m_szHuman; } ///< Get Human68k file name BOOL isReduce() const; ///< Inspect if the Human68k name is generated
const BYTE* GetHumanLast() const BOOL isCorrect() const { return m_bCorrect; } ///< Inspect if the Human68k file name adhers to naming rules
const BYTE* GetHuman() const { return m_szHuman; } ///< Get Human68k file name
const BYTE* GetHumanLast() const
{ return m_pszHumanLast; } ///< Get Human68k file name { return m_pszHumanLast; } ///< Get Human68k file name
const BYTE* GetHumanExt() const { return m_pszHumanExt; }///< Get Human68k file name const BYTE* GetHumanExt() const { return m_pszHumanExt; }///< Get Human68k file name
void SetEntryName(); ///< Set Human68k directory entry void SetEntryName(); ///< Set Human68k directory entry
void SetEntryAttribute(BYTE nHumanAttribute) void SetEntryAttribute(BYTE nHumanAttribute)
{ m_dirHuman.attr = nHumanAttribute; } ///< Set Human68k directory entry { m_dirHuman.attr = nHumanAttribute; } ///< Set Human68k directory entry
void SetEntrySize(DWORD nHumanSize) void SetEntrySize(DWORD nHumanSize)
{ m_dirHuman.size = nHumanSize; } ///< Set Human68k directory entry { m_dirHuman.size = nHumanSize; } ///< Set Human68k directory entry
void SetEntryDate(WORD nHumanDate) void SetEntryDate(WORD nHumanDate)
{ m_dirHuman.date = nHumanDate; } ///< Set Human68k directory entry { m_dirHuman.date = nHumanDate; } ///< Set Human68k directory entry
void SetEntryTime(WORD nHumanTime) void SetEntryTime(WORD nHumanTime)
{ m_dirHuman.time = nHumanTime; } ///< Set Human68k directory entry { m_dirHuman.time = nHumanTime; } ///< Set Human68k directory entry
void SetEntryCluster(WORD nHumanCluster) void SetEntryCluster(WORD nHumanCluster)
{ m_dirHuman.cluster = nHumanCluster; } ///< Set Human68k directory entry { m_dirHuman.cluster = nHumanCluster; } ///< Set Human68k directory entry
const Human68k::dirent_t* GetEntry() const const Human68k::dirent_t* GetEntry() const
{ return &m_dirHuman; } ///< Get Human68k directory entry { return &m_dirHuman; } ///< Get Human68k directory entry
BOOL CheckAttribute(DWORD nHumanAttribute) const; ///< Determine Human68k directory entry attributes BOOL CheckAttribute(DWORD nHumanAttribute) const; ///< Determine Human68k directory entry attributes
BOOL isSameEntry(const Human68k::dirent_t* pdirHuman) const BOOL isSameEntry(const Human68k::dirent_t* pdirHuman) const
{ ASSERT(pdirHuman); return memcmp(&m_dirHuman, pdirHuman, sizeof(m_dirHuman)) == 0; } { ASSERT(pdirHuman); return memcmp(&m_dirHuman, pdirHuman, sizeof(m_dirHuman)) == 0; }
///< Determine Human68k directory entry match ///< Determine Human68k directory entry match
// Path name operations // Path name operations
static const BYTE* SeparateExt(const BYTE* szHuman); ///< Extract extension from Human68k file name static const BYTE* SeparateExt(const BYTE* szHuman); ///< Extract extension from Human68k file name
private: private:
static BYTE* CopyName(BYTE* pWrite, const BYTE* pFirst, const BYTE* pLast); static BYTE* CopyName(BYTE* pWrite, const BYTE* pFirst, const BYTE* pLast);
///< Copy Human68k file name elements ///< Copy Human68k file name elements
const BYTE* m_pszHumanLast; ///< Last position of the Human68k internal name of the relevant entry const BYTE* m_pszHumanLast = nullptr; ///< Last position of the Human68k internal name of the relevant entry
const BYTE* m_pszHumanExt; ///< Position of the extension of the Human68k internal name of the relevant entry const BYTE* m_pszHumanExt = nullptr; ///< Position of the extension of the Human68k internal name of the relevant entry
BOOL m_bCorrect; ///< TRUE if the relevant entry of the Human68k internal name is correct BOOL m_bCorrect = FALSE; ///< TRUE if the relevant entry of the Human68k internal name is correct
BYTE m_szHuman[24]; ///< Human68k internal name of the relevant entry BYTE m_szHuman[24]; ///< Human68k internal name of the relevant entry
Human68k::dirent_t m_dirHuman; ///< All information for the Human68k relevant entry Human68k::dirent_t m_dirHuman; ///< All information for the Human68k relevant entry
TCHAR m_szHost[FILEPATH_MAX]; ///< The host name of the relevant entry (variable length) TCHAR m_szHost[FILEPATH_MAX]; ///< The host name of the relevant entry (variable length)
@ -526,7 +530,7 @@ public:
void Clear() { count = 0; } ///< Initialize void Clear() { count = 0; } ///< Initialize
}; };
CHostPath(); CHostPath() = default;
~CHostPath(); ~CHostPath();
CHostPath(CHostPath&) = delete; CHostPath(CHostPath&) = delete;
CHostPath& operator=(const CHostPath&) = delete; CHostPath& operator=(const CHostPath&) = delete;
@ -558,9 +562,9 @@ private:
///< Compare string (with support for wildcards) ///< Compare string (with support for wildcards)
CRing m_cRing; ///< For CHostFilename linking CRing m_cRing; ///< For CHostFilename linking
time_t m_tBackup; ///< For time stamp restoration time_t m_tBackup = FALSE; ///< For time stamp restoration
BOOL m_bRefresh; ///< Refresh flag BOOL m_bRefresh = TRUE; ///< Refresh flag
DWORD m_nId; ///< Unique ID (When the value has changed, it means an update has been made) DWORD m_nId = 0; ///< Unique ID (When the value has changed, it means an update has been made)
BYTE m_szHuman[HUMAN68K_PATH_MAX]; ///< The internal Human68k name for the relevant entry BYTE m_szHuman[HUMAN68K_PATH_MAX]; ///< The internal Human68k name for the relevant entry
TCHAR m_szHost[FILEPATH_MAX]; ///< The host side name for the relevant entry TCHAR m_szHost[FILEPATH_MAX]; ///< The host side name for the relevant entry
@ -590,47 +594,50 @@ private:
//=========================================================================== //===========================================================================
class CHostFiles { class CHostFiles {
public: public:
CHostFiles() { SetKey(0); } CHostFiles() = default;
void Init(); ~CHostFiles() = default;
CHostFiles(CHostFiles&) = delete;
CHostFiles& operator=(const CHostFiles&) = delete;
void SetKey(DWORD nKey) { m_nKey = nKey; } ///< Set search key void Init();
BOOL isSameKey(DWORD nKey) const { return m_nKey == nKey; } ///< Compare search key
void SetPath(const Human68k::namests_t* pNamests); ///< Create path and file name internally
BOOL isRootPath() const { return m_szHumanPath[1] == '\0'; } ///< Check if root directory
void SetPathWildcard() { m_nHumanWildcard = 1; } ///< Enable file search using wildcards
void SetPathOnly() { m_nHumanWildcard = 0xFF; } ///< Enable only path names
BOOL isPathOnly() const { return m_nHumanWildcard == 0xFF; } ///< Check if set to only path names
void SetAttribute(DWORD nHumanAttribute) { m_nHumanAttribute = nHumanAttribute; } ///< Set search attribute
BOOL Find(DWORD nUnit, class CHostEntry* pEntry) ; ///< Find files on the Human68k side, generating data on the host side
const CHostFilename* Find(CHostPath* pPath); ///< Find file name
void SetEntry(const CHostFilename* pFilename); ///< Store search results on the Human68k side
void SetResult(const TCHAR* szPath); ///< Set names on the host side
void AddResult(const TCHAR* szPath); ///< Add file name to the name on the host side
void AddFilename(); ///< Add the new Human68k file name to the name on the host side
const TCHAR* GetPath() const { return m_szHostResult; } ///< Get the name on the host side void SetKey(DWORD nKey) { m_nKey = nKey; } ///< Set search key
BOOL isSameKey(DWORD nKey) const { return m_nKey == nKey; } ///< Compare search key
void SetPath(const Human68k::namests_t* pNamests); ///< Create path and file name internally
BOOL isRootPath() const { return m_szHumanPath[1] == '\0'; } ///< Check if root directory
void SetPathWildcard() { m_nHumanWildcard = 1; } ///< Enable file search using wildcards
void SetPathOnly() { m_nHumanWildcard = 0xFF; } ///< Enable only path names
BOOL isPathOnly() const { return m_nHumanWildcard == 0xFF; } ///< Check if set to only path names
void SetAttribute(DWORD nHumanAttribute) { m_nHumanAttribute = nHumanAttribute; } ///< Set search attribute
BOOL Find(DWORD nUnit, const class CHostEntry* pEntry); ///< Find files on the Human68k side, generating data on the host side
const CHostFilename* Find(const CHostPath* pPath); ///< Find file name
void SetEntry(const CHostFilename* pFilename); ///< Store search results on the Human68k side
void SetResult(const TCHAR* szPath); ///< Set names on the host side
void AddResult(const TCHAR* szPath); ///< Add file name to the name on the host side
void AddFilename(); ///< Add the new Human68k file name to the name on the host side
const Human68k::dirent_t* GetEntry() const { return &m_dirHuman; }///< Get Human68k directory entry const TCHAR* GetPath() const { return m_szHostResult; } ///< Get the name on the host side
DWORD GetAttribute() const { return m_dirHuman.attr; } ///< Get Human68k attribute const Human68k::dirent_t* GetEntry() const { return &m_dirHuman; }///< Get Human68k directory entry
WORD GetDate() const { return m_dirHuman.date; } ///< Get Human68k date
WORD GetTime() const { return m_dirHuman.time; } ///< Get Human68k time DWORD GetAttribute() const { return m_dirHuman.attr; } ///< Get Human68k attribute
DWORD GetSize() const { return m_dirHuman.size; } ///< Get Human68k file size WORD GetDate() const { return m_dirHuman.date; } ///< Get Human68k date
const BYTE* GetHumanFilename() const { return m_szHumanFilename; }///< Get Human68k file name WORD GetTime() const { return m_dirHuman.time; } ///< Get Human68k time
const BYTE* GetHumanResult() const { return m_szHumanResult; } ///< Get Human68k file name search results DWORD GetSize() const { return m_dirHuman.size; } ///< Get Human68k file size
const BYTE* GetHumanPath() const { return m_szHumanPath; } ///< Get Human68k path name const BYTE* GetHumanFilename() const { return m_szHumanFilename; }///< Get Human68k file name
const BYTE* GetHumanResult() const { return m_szHumanResult; } ///< Get Human68k file name search results
const BYTE* GetHumanPath() const { return m_szHumanPath; } ///< Get Human68k path name
private: private:
DWORD m_nKey; ///< FILES buffer address for Human68k; 0 is unused DWORD m_nKey = 0; ///< FILES buffer address for Human68k; 0 is unused
DWORD m_nHumanWildcard; ///< Human68k wildcard data DWORD m_nHumanWildcard = 0; ///< Human68k wildcard data
DWORD m_nHumanAttribute; ///< Human68k search attribute DWORD m_nHumanAttribute = 0; ///< Human68k search attribute
CHostPath::find_t m_findNext; ///< Next search location data CHostPath::find_t m_findNext = {}; ///< Next search location data
Human68k::dirent_t m_dirHuman; ///< Search results: Human68k file data Human68k::dirent_t m_dirHuman = {}; ///< Search results: Human68k file data
BYTE m_szHumanFilename[24]; ///< Human68k file name BYTE m_szHumanFilename[24] = {}; ///< Human68k file name
BYTE m_szHumanResult[24]; ///< Search results: Human68k file name BYTE m_szHumanResult[24] = {}; ///< Search results: Human68k file name
BYTE m_szHumanPath[HUMAN68K_PATH_MAX]; BYTE m_szHumanPath[HUMAN68K_PATH_MAX] = {}; ///< Human68k path name
///< Human68k path name TCHAR m_szHostResult[FILEPATH_MAX] = {}; ///< Search results: host's full path name
TCHAR m_szHostResult[FILEPATH_MAX]; ///< Search results: host's full path name
}; };
//=========================================================================== //===========================================================================
@ -666,41 +673,40 @@ private:
//=========================================================================== //===========================================================================
class CHostFcb { class CHostFcb {
public: public:
CHostFcb() { SetKey(0); Init(); } CHostFcb() = default;
~CHostFcb() { Close(); } ~CHostFcb() { Close(); }
CHostFcb(CHostFcb&) = delete; CHostFcb(CHostFcb&) = delete;
CHostFcb& operator=(const CHostFcb&) = delete; CHostFcb& operator=(const CHostFcb&) = delete;
void Init(); void Init();
void SetKey(DWORD nKey) { m_nKey = nKey; } ///< Set search key void SetKey(DWORD nKey) { m_nKey = nKey; } ///< Set search key
BOOL isSameKey(DWORD nKey) const { return m_nKey == nKey; } ///< Compare search key BOOL isSameKey(DWORD nKey) const { return m_nKey == nKey; } ///< Compare search key
void SetUpdate() { m_bUpdate = TRUE; } ///< Update void SetUpdate() { m_bUpdate = TRUE; } ///< Update
BOOL isUpdate() const { return m_bUpdate; } ///< Get update state BOOL isUpdate() const { return m_bUpdate; } ///< Get update state
BOOL SetMode(DWORD nHumanMode); ///< Set file open mode BOOL SetMode(DWORD nHumanMode); ///< Set file open mode
void SetFilename(const TCHAR* szFilename); ///< Set file name void SetFilename(const TCHAR* szFilename); ///< Set file name
void SetHumanPath(const BYTE* szHumanPath); ///< Set Human68k path name void SetHumanPath(const BYTE* szHumanPath); ///< Set Human68k path name
const BYTE* GetHumanPath() const { return m_szHumanPath; } ///< Get Human68k path name const BYTE* GetHumanPath() const { return m_szHumanPath; } ///< Get Human68k path name
BOOL Create(DWORD nHumanAttribute, BOOL bForce); ///< Create file BOOL Create(DWORD nHumanAttribute, BOOL bForce); ///< Create file
BOOL Open(); ///< Open file BOOL Open(); ///< Open file
BOOL Rewind(DWORD nOffset) const; ///< Seek file BOOL Rewind(DWORD nOffset) const; ///< Seek file
DWORD Read(BYTE* pBuffer, DWORD nSize); ///< Read file DWORD Read(BYTE* pBuffer, DWORD nSize); ///< Read file
DWORD Write(const BYTE* pBuffer, DWORD nSize); ///< Write file DWORD Write(const BYTE* pBuffer, DWORD nSize); ///< Write file
BOOL Truncate() const; ///< Truncate file BOOL Truncate() const; ///< Truncate file
DWORD Seek(DWORD nOffset, DWORD nHumanSeek); ///< Seek file DWORD Seek(DWORD nOffset, DWORD nHumanSeek); ///< Seek file
BOOL TimeStamp(DWORD nHumanTime) const; ///< Set file time stamp BOOL TimeStamp(DWORD nHumanTime) const; ///< Set file time stamp
BOOL Close(); ///< Close file BOOL Close(); ///< Close file
private: private:
DWORD m_nKey; ///< Human68k FCB buffer address (0 if unused) DWORD m_nKey = 0; ///< Human68k FCB buffer address (0 if unused)
BOOL m_bUpdate; ///< Update flag BOOL m_bUpdate = FALSE; ///< Update flag
FILE* m_pFile; ///< Host side file object FILE* m_pFile = nullptr; ///< Host side file object
const char* m_pszMode; ///< Host side file open mode const char* m_pszMode = nullptr; ///< Host side file open mode
bool m_bFlag; ///< Host side file open flag bool m_bFlag = false; ///< Host side file open flag
BYTE m_szHumanPath[HUMAN68K_PATH_MAX]; BYTE m_szHumanPath[HUMAN68K_PATH_MAX] = {}; ///< Human68k path name
///< Human68k path name TCHAR m_szFilename[FILEPATH_MAX] = {}; ///< Host side file name
TCHAR m_szFilename[FILEPATH_MAX]; ///< Host side file name
}; };
//=========================================================================== //===========================================================================
@ -714,7 +720,7 @@ public:
~CHostFcbManager(); ~CHostFcbManager();
#endif // _DEBUG #endif // _DEBUG
void Init(); ///< Initialization (when the driver is installed) void Init(); ///< Initialization (when the driver is installed)
void Clean(); ///< Release (when starting up or resetting) void Clean() const; ///< Release (when starting up or resetting)
CHostFcb* Alloc(DWORD nKey); CHostFcb* Alloc(DWORD nKey);
CHostFcb* Search(DWORD nKey); CHostFcb* Search(DWORD nKey);
@ -740,36 +746,36 @@ private:
class CHostDrv class CHostDrv
{ {
public: public:
CHostDrv(); CHostDrv() = default;
~CHostDrv(); ~CHostDrv();
CHostDrv(CHostDrv&) = delete; CHostDrv(CHostDrv&) = delete;
CHostDrv& operator=(const CHostDrv&) = delete; CHostDrv& operator=(const CHostDrv&) = delete;
void Init(const TCHAR* szBase, DWORD nFlag); ///< Initialization (device startup and load) void Init(const TCHAR* szBase, DWORD nFlag); ///< Initialization (device startup and load)
BOOL isWriteProtect() const { return m_bWriteProtect; } BOOL isWriteProtect() const { return m_bWriteProtect; }
BOOL isEnable() const { return m_bEnable; } ///< Is it accessible? BOOL isEnable() const { return m_bEnable; } ///< Is it accessible?
BOOL isMediaOffline() const; BOOL isMediaOffline() const;
BYTE GetMediaByte() const; BYTE GetMediaByte() const;
DWORD GetStatus() const; DWORD GetStatus() const;
void SetEnable(BOOL bEnable); ///< Set media status void SetEnable(BOOL bEnable); ///< Set media status
BOOL CheckMedia(); ///< Check if media was changed BOOL CheckMedia(); ///< Check if media was changed
void Update(); ///< Update media status void Update(); ///< Update media status
void Eject(); void Eject();
void GetVolume(TCHAR* szLabel); ///< Get volume label void GetVolume(TCHAR* szLabel); ///< Get volume label
BOOL GetVolumeCache(TCHAR* szLabel) const; ///< Get volume label from cache BOOL GetVolumeCache(TCHAR* szLabel) const; ///< Get volume label from cache
DWORD GetCapacity(Human68k::capacity_t* pCapacity); DWORD GetCapacity(Human68k::capacity_t* pCapacity);
BOOL GetCapacityCache(Human68k::capacity_t* pCapacity) const; ///< Get capacity from cache BOOL GetCapacityCache(Human68k::capacity_t* pCapacity) const; ///< Get capacity from cache
// Cache operations // Cache operations
void CleanCache() const; ///< Update all cache void CleanCache() const; ///< Update all cache
void CleanCache(const BYTE* szHumanPath); ///< Update cache for the specified path void CleanCache(const BYTE* szHumanPath); ///< Update cache for the specified path
void CleanCacheChild(const BYTE* szHumanPath) const; ///< Update all cache below the specified path void CleanCacheChild(const BYTE* szHumanPath) const; ///< Update all cache below the specified path
void DeleteCache(const BYTE* szHumanPath); ///< Delete the cache for the specified path void DeleteCache(const BYTE* szHumanPath); ///< Delete the cache for the specified path
CHostPath* FindCache(const BYTE* szHuman); ///< Inspect if the specified path is cached CHostPath* FindCache(const BYTE* szHuman); ///< Inspect if the specified path is cached
CHostPath* CopyCache(CHostFiles* pFiles); ///< Acquire the host side name on the basis of cache information CHostPath* CopyCache(CHostFiles* pFiles); ///< Acquire the host side name on the basis of cache information
CHostPath* MakeCache(CHostFiles* pFiles); ///< Get all required data to construct a host side name CHostPath* MakeCache(CHostFiles* pFiles); ///< Get all required data to construct a host side name
BOOL Find(CHostFiles* pFiles); ///< Find host side name (path + file name (can be abbreviated) + attribute) BOOL Find(CHostFiles* pFiles); ///< Find host side name (path + file name (can be abbreviated) + attribute)
private: private:
// Path name operations // Path name operations
@ -782,14 +788,14 @@ private:
CHostPath f; CHostPath f;
}; };
BOOL m_bWriteProtect; ///< TRUE if write-protected BOOL m_bWriteProtect = FALSE; ///< TRUE if write-protected
BOOL m_bEnable; ///< TRUE if media is usable BOOL m_bEnable = FALSE; ///< TRUE if media is usable
DWORD m_nRing; ///< Number of stored path names DWORD m_nRing = 0; ///< Number of stored path names
CRing m_cRing; ///< For attaching to CHostPath CRing m_cRing; ///< For attaching to CHostPath
Human68k::capacity_t m_capCache; ///< Sector data cache: if "sectors == 0" then not cached Human68k::capacity_t m_capCache; ///< Sector data cache: if "sectors == 0" then not cached
BOOL m_bVolumeCache; ///< TRUE if the volume label has been read BOOL m_bVolumeCache = FALSE; ///< TRUE if the volume label has been read
TCHAR m_szVolumeCache[24]; ///< Volume label cache TCHAR m_szVolumeCache[24] = {}; ///< Volume label cache
TCHAR m_szBase[FILEPATH_MAX]; ///< Base path TCHAR m_szBase[FILEPATH_MAX] = {}; ///< Base path
}; };
//=========================================================================== //===========================================================================
@ -798,46 +804,47 @@ private:
// //
//=========================================================================== //===========================================================================
class CHostEntry { class CHostEntry {
public: public:
CHostEntry();
/// Max number of drive candidates
static const int DRIVE_MAX = 10;
CHostEntry() = default;
~CHostEntry(); ~CHostEntry();
CHostEntry(CHostEntry&) = delete; CHostEntry(CHostEntry&) = delete;
CHostEntry& operator=(const CHostEntry&) = delete; CHostEntry& operator=(const CHostEntry&) = delete;
void Init(); ///< Initialization (when the driver is installed) void Init() const; ///< Initialization (when the driver is installed)
void Clean(); ///< Release (when starting up or resetting) void Clean(); ///< Release (when starting up or resetting)
// Cache operations // Cache operations
void CleanCache(); ///< Update all cache void CleanCache() const; ///< Update all cache
void CleanCache(DWORD nUnit); ///< Update cache for the specified unit void CleanCache(DWORD nUnit) const; ///< Update cache for the specified unit
void CleanCache(DWORD nUnit, const BYTE* szHumanPath); ///< Update cache for the specified path void CleanCache(DWORD nUnit, const BYTE* szHumanPath) const; ///< Update cache for the specified path
void CleanCacheChild(DWORD nUnit, const BYTE* szHumanPath); ///< Update cache below the specified path void CleanCacheChild(DWORD nUnit, const BYTE* szHumanPath) const; ///< Update cache below the specified path
void DeleteCache(DWORD nUnit, const BYTE* szHumanPath); ///< Delete cache for the specified path void DeleteCache(DWORD nUnit, const BYTE* szHumanPath) const; ///< Delete cache for the specified path
BOOL Find(DWORD nUnit, CHostFiles* pFiles) const; ///< Find host side name (path + file name (can be abbreviated) + attribute) BOOL Find(DWORD nUnit, CHostFiles* pFiles) const; ///< Find host side name (path + file name (can be abbreviated) + attribute)
void ShellNotify(DWORD nEvent, const TCHAR* szPath); ///< Notify status change in the host side file system void ShellNotify(DWORD nEvent, const TCHAR* szPath); ///< Notify status change in the host side file system
// Drive object operations // Drive object operations
void SetDrv(DWORD nUnit, CHostDrv* pDrv); void SetDrv(DWORD nUnit, CHostDrv* pDrv);
BOOL isWriteProtect(DWORD nUnit) const; BOOL isWriteProtect(DWORD nUnit) const;
BOOL isEnable(DWORD nUnit) const; ///< Is it accessible? BOOL isEnable(DWORD nUnit) const; ///< Is it accessible?
BOOL isMediaOffline(DWORD nUnit) const; BOOL isMediaOffline(DWORD nUnit) const;
BYTE GetMediaByte(DWORD nUnit) const; BYTE GetMediaByte(DWORD nUnit) const;
DWORD GetStatus(DWORD nUnit) const; ///< Get drive status DWORD GetStatus(DWORD nUnit) const; ///< Get drive status
BOOL CheckMedia(DWORD nUnit) const; ///< Media change check BOOL CheckMedia(DWORD nUnit) const; ///< Media change check
void Eject(DWORD nUnit); void Eject(DWORD nUnit) const;
void GetVolume(DWORD nUnit, TCHAR* szLabel); ///< Get volume label void GetVolume(DWORD nUnit, TCHAR* szLabel) const; ///< Get volume label
BOOL GetVolumeCache(DWORD nUnit, TCHAR* szLabel) const; ///< Get volume label from cache BOOL GetVolumeCache(DWORD nUnit, TCHAR* szLabel) const; ///< Get volume label from cache
DWORD GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const; DWORD GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const;
BOOL GetCapacityCache(DWORD nUnit, Human68k::capacity_t* pCapacity) const; BOOL GetCapacityCache(DWORD nUnit, Human68k::capacity_t* pCapacity) const; ///< Get cluster size from cache
///< Get cluster size from cache
enum {
DriveMax = 10 ///< Max number of drive candidates
};
private: private:
CHostDrv* m_pDrv[DriveMax]; ///< Host side drive object
DWORD m_nTimeout; ///< Last time a timeout check was carried out CHostDrv* m_pDrv[DRIVE_MAX] = {}; ///< Host side drive object
DWORD m_nTimeout = 0; ///< Last time a timeout check was carried out
}; };
//=========================================================================== //===========================================================================
@ -874,7 +881,7 @@ The easy solution is to put the content of 'class CFileSys' into 'class CWindrv'
class CFileSys class CFileSys
{ {
public: public:
CFileSys(); CFileSys() = default;
virtual ~CFileSys() = default; virtual ~CFileSys() = default;
void Reset(); ///< Reset (close all) void Reset(); ///< Reset (close all)
@ -882,13 +889,13 @@ public:
// Command handlers // Command handlers
DWORD InitDevice(const Human68k::argument_t* pArgument); ///< $40 - Device startup DWORD InitDevice(const Human68k::argument_t* pArgument); ///< $40 - Device startup
int CheckDir(DWORD nUnit, const Human68k::namests_t* pNamests); ///< $41 - Directory check int CheckDir(DWORD nUnit, const Human68k::namests_t* pNamests) const; ///< $41 - Directory check
int MakeDir(DWORD nUnit, const Human68k::namests_t* pNamests); ///< $42 - Create directory int MakeDir(DWORD nUnit, const Human68k::namests_t* pNamests) const; ///< $42 - Create directory
int RemoveDir(DWORD nUnit, const Human68k::namests_t* pNamests); ///< $43 - Delete directory int RemoveDir(DWORD nUnit, const Human68k::namests_t* pNamests) const; ///< $43 - Delete directory
int Rename(DWORD nUnit, const Human68k::namests_t* pNamests, const Human68k::namests_t* pNamestsNew); int Rename(DWORD nUnit, const Human68k::namests_t* pNamests, const Human68k::namests_t* pNamestsNew) const;
///< $44 - Change file name ///< $44 - Change file name
int Delete(DWORD nUnit, const Human68k::namests_t* pNamests); ///< $45 - Delete file int Delete(DWORD nUnit, const Human68k::namests_t* pNamests) const; ///< $45 - Delete file
int Attribute(DWORD nUnit, const Human68k::namests_t* pNamests, DWORD nHumanAttribute); int Attribute(DWORD nUnit, const Human68k::namests_t* pNamests, DWORD nHumanAttribute) const;
///< $46 - Get / set file attribute ///< $46 - Get / set file attribute
int Files(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests, Human68k::files_t* pFiles); int Files(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests, Human68k::files_t* pFiles);
///< $47 - Find file ///< $47 - Find file
@ -897,7 +904,7 @@ public:
///< $49 - Create file ///< $49 - Create file
int Open(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests, Human68k::fcb_t* pFcb); int Open(DWORD nUnit, DWORD nKey, const Human68k::namests_t* pNamests, Human68k::fcb_t* pFcb);
///< $4A - Open file ///< $4A - Open file
int Close(DWORD nUnit, DWORD nKey, Human68k::fcb_t* pFcb); ///< $4B - Close file int Close(DWORD nUnit, DWORD nKey, const Human68k::fcb_t* pFcb); ///< $4B - Close file
int Read(DWORD nKey, Human68k::fcb_t* pFcb, BYTE* pAddress, DWORD nSize); int Read(DWORD nKey, Human68k::fcb_t* pFcb, BYTE* pAddress, DWORD nSize);
///< $4C - Read file ///< $4C - Read file
int Write(DWORD nKey, Human68k::fcb_t* pFcb, const BYTE* pAddress, DWORD nSize); int Write(DWORD nKey, Human68k::fcb_t* pFcb, const BYTE* pAddress, DWORD nSize);
@ -906,7 +913,7 @@ public:
DWORD TimeStamp(DWORD nUnit, DWORD nKey, Human68k::fcb_t* pFcb, DWORD nHumanTime); DWORD TimeStamp(DWORD nUnit, DWORD nKey, Human68k::fcb_t* pFcb, DWORD nHumanTime);
///< $4F - Get / set file timestamp ///< $4F - Get / set file timestamp
int GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const; ///< $50 - Get capacity int GetCapacity(DWORD nUnit, Human68k::capacity_t* pCapacity) const; ///< $50 - Get capacity
int CtrlDrive(DWORD nUnit, Human68k::ctrldrive_t* pCtrlDrive); ///< $51 - Inspect / control drive status int CtrlDrive(DWORD nUnit, Human68k::ctrldrive_t* pCtrlDrive) const; ///< $51 - Inspect / control drive status
int GetDPB(DWORD nUnit, Human68k::dpb_t* pDpb) const; ///< $52 - Get DPB int GetDPB(DWORD nUnit, Human68k::dpb_t* pDpb) const; ///< $52 - Get DPB
int DiskRead(DWORD nUnit, BYTE* pBuffer, DWORD nSector, DWORD nSize); ///< $53 - Read sectors int DiskRead(DWORD nUnit, BYTE* pBuffer, DWORD nSector, DWORD nSize); ///< $53 - Read sectors
int DiskWrite(DWORD nUnit) const; ///< $54 - Write sectors int DiskWrite(DWORD nUnit) const; ///< $54 - Write sectors
@ -921,24 +928,24 @@ public:
static DWORD GetFileOption() { return g_nOption; } ///< Get file name change option static DWORD GetFileOption() { return g_nOption; } ///< Get file name change option
enum { enum {
DriveMax = CHostEntry::DriveMax ///< Max number of drive candidates DriveMax = CHostEntry::DRIVE_MAX ///< Max number of drive candidates
}; };
private: private:
void InitOption(const Human68k::argument_t* pArgument); void InitOption(const Human68k::argument_t* pArgument);
BOOL FilesVolume(DWORD nUnit, Human68k::files_t* pFiles); ///< Get volume label BOOL FilesVolume(DWORD nUnit, Human68k::files_t* pFiles) const; ///< Get volume label
DWORD m_nUnits; ///< Number of current drive objects (Changes for every resume) DWORD m_nUnits = 0; ///< Number of current drive objects (Changes for every resume)
DWORD m_nOption; ///< Current runtime flag DWORD m_nOption = 0; ///< Current runtime flag
DWORD m_nOptionDefault; ///< Runtime flag at reset DWORD m_nOptionDefault = 0; ///< Runtime flag at reset
DWORD m_nDrives; ///< Number of candidates for base path status restoration (scan every time if 0) DWORD m_nDrives = 0; ///< Number of candidates for base path status restoration (scan every time if 0)
DWORD m_nKernel; ///< Counter for kernel check DWORD m_nKernel = 0; ///< Counter for kernel check
DWORD m_nKernelSearch; ///< Initial address for NUL device DWORD m_nKernelSearch = 0; ///< Initial address for NUL device
DWORD m_nHostSectorCount; ///< Virtual sector identifier DWORD m_nHostSectorCount = 0; ///< Virtual sector identifier
CHostFilesManager m_cFiles; ///< File search memory CHostFilesManager m_cFiles; ///< File search memory
CHostFcbManager m_cFcb; ///< FCB operation memory CHostFcbManager m_cFcb; ///< FCB operation memory
@ -947,7 +954,7 @@ private:
DWORD m_nHostSectorBuffer[XM6_HOST_PSEUDO_CLUSTER_MAX]; DWORD m_nHostSectorBuffer[XM6_HOST_PSEUDO_CLUSTER_MAX];
///< Entity that the virtual sector points to ///< Entity that the virtual sector points to
DWORD m_nFlag[DriveMax]; ///< Candidate runtime flag for base path restoration DWORD m_nFlag[DriveMax] = {}; ///< Candidate runtime flag for base path restoration
TCHAR m_szBase[DriveMax][FILEPATH_MAX]; ///< Candidate for base path restoration TCHAR m_szBase[DriveMax][FILEPATH_MAX] = {}; ///< Candidate for base path restoration
static DWORD g_nOption; ///< File name change flag static DWORD g_nOption; ///< File name change flag
}; };

View File

@ -25,7 +25,7 @@
#include "rascsi_exceptions.h" #include "rascsi_exceptions.h"
#include <sstream> #include <sstream>
#define BRIDGE_NAME "rascsi_bridge" static const char *BRIDGE_NAME = "rascsi_bridge";
using namespace std; using namespace std;
using namespace ras_util; using namespace ras_util;
@ -42,7 +42,7 @@ static bool br_setif(int br_socket_fd, const char* bridgename, const char* ifnam
LOGERROR("Can't if_nametoindex: %s", strerror(errno)) LOGERROR("Can't if_nametoindex: %s", strerror(errno))
return false; return false;
} }
strncpy(ifr.ifr_name, bridgename, IFNAMSIZ); strncpy(ifr.ifr_name, bridgename, IFNAMSIZ - 1);
if (ioctl(br_socket_fd, add ? SIOCBRADDIF : SIOCBRDELIF, &ifr) < 0) { if (ioctl(br_socket_fd, add ? SIOCBRADDIF : SIOCBRDELIF, &ifr) < 0) {
LOGERROR("Can't ioctl %s: %s", add ? "SIOCBRADDIF" : "SIOCBRDELIF", strerror(errno)) LOGERROR("Can't ioctl %s: %s", add ? "SIOCBRADDIF" : "SIOCBRDELIF", strerror(errno))
return false; return false;
@ -70,7 +70,7 @@ static bool ip_link(int fd, const char* ifname, bool up) {
return true; return true;
} }
static bool is_interface_up(const string& interface) { static bool is_interface_up(string_view interface) {
string file = "/sys/class/net/"; string file = "/sys/class/net/";
file += interface; file += interface;
file += "/carrier"; file += "/carrier";
@ -381,7 +381,8 @@ void CTapDriver::Cleanup()
} }
} }
bool CTapDriver::Enable(){ bool CTapDriver::Enable() const
{
int fd = socket(PF_INET, SOCK_DGRAM, 0); int fd = socket(PF_INET, SOCK_DGRAM, 0);
LOGDEBUG("%s: ip link set ras0 up", __PRETTY_FUNCTION__) LOGDEBUG("%s: ip link set ras0 up", __PRETTY_FUNCTION__)
bool result = ip_link(fd, "ras0", true); bool result = ip_link(fd, "ras0", true);
@ -389,7 +390,8 @@ bool CTapDriver::Enable(){
return result; return result;
} }
bool CTapDriver::Disable(){ bool CTapDriver::Disable() const
{
int fd = socket(PF_INET, SOCK_DGRAM, 0); int fd = socket(PF_INET, SOCK_DGRAM, 0);
LOGDEBUG("%s: ip link set ras0 down", __PRETTY_FUNCTION__) LOGDEBUG("%s: ip link set ras0 down", __PRETTY_FUNCTION__)
bool result = ip_link(fd, "ras0", false); bool result = ip_link(fd, "ras0", false);
@ -397,14 +399,15 @@ bool CTapDriver::Disable(){
return result; return result;
} }
void CTapDriver::Flush(){ void CTapDriver::Flush()
{
LOGTRACE("%s", __PRETTY_FUNCTION__) LOGTRACE("%s", __PRETTY_FUNCTION__)
while(PendingPackets()){ while(PendingPackets()){
(void)Rx(m_garbage_buffer); (void)Rx(m_garbage_buffer);
} }
} }
void CTapDriver::GetMacAddr(BYTE *mac) void CTapDriver::GetMacAddr(BYTE *mac) const
{ {
ASSERT(mac); ASSERT(mac);
@ -416,7 +419,7 @@ void CTapDriver::GetMacAddr(BYTE *mac)
// Receive // Receive
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
bool CTapDriver::PendingPackets() bool CTapDriver::PendingPackets() const
{ {
pollfd fds; pollfd fds;
@ -436,7 +439,7 @@ bool CTapDriver::PendingPackets()
} }
// See https://stackoverflow.com/questions/21001659/crc32-algorithm-implementation-in-c-without-a-look-up-table-and-with-a-public-li // See https://stackoverflow.com/questions/21001659/crc32-algorithm-implementation-in-c-without-a-look-up-table-and-with-a-public-li
uint32_t crc32(BYTE *buf, int length) { uint32_t crc32(const BYTE *buf, int length) {
uint32_t crc = 0xffffffff; uint32_t crc = 0xffffffff;
for (int i = 0; i < length; i++) { for (int i = 0; i < length; i++) {
crc ^= buf[i]; crc ^= buf[i];

View File

@ -49,12 +49,12 @@ public:
void OpenDump(const Filepath& path); void OpenDump(const Filepath& path);
// Capture packets // Capture packets
void Cleanup(); // Cleanup void Cleanup(); // Cleanup
void GetMacAddr(BYTE *mac); // Get Mac Address void GetMacAddr(BYTE *mac) const; // Get Mac Address
int Rx(BYTE *buf); // Receive int Rx(BYTE *buf); // Receive
int Tx(const BYTE *buf, int len); // Send int Tx(const BYTE *buf, int len); // Send
bool PendingPackets(); // Check if there are IP packets available bool PendingPackets() const; // Check if there are IP packets available
bool Enable(); // Enable the ras0 interface bool Enable() const; // Enable the ras0 interface
bool Disable(); // Disable the ras0 interface bool Disable() const; // Disable the ras0 interface
void Flush(); // Purge all of the packets that are waiting to be processed void Flush(); // Purge all of the packets that are waiting to be processed
private: private:

View File

@ -14,14 +14,10 @@
#include "rascsi_exceptions.h" #include "rascsi_exceptions.h"
#include "device.h" #include "device.h"
unordered_set<Device *> Device::devices;
Device::Device(const string& t) : type(t) Device::Device(const string& t) : type(t)
{ {
assert(type.length() == 4); assert(type.length() == 4);
devices.insert(this);
char rev[5]; char rev[5];
sprintf(rev, "%02d%02d", rascsi_major_version, rascsi_minor_version); sprintf(rev, "%02d%02d", rascsi_major_version, rascsi_minor_version);
revision = rev; revision = rev;

View File

@ -10,7 +10,6 @@
#pragma once #pragma once
#include "scsi.h" #include "scsi.h"
#include <unordered_set>
#include <unordered_map> #include <unordered_map>
#include <string> #include <string>
@ -87,8 +86,6 @@ protected:
string GetParam(const string&) const; string GetParam(const string&) const;
void SetParams(const unordered_map<string, string>&); void SetParams(const unordered_map<string, string>&);
static unordered_set<Device *> devices;
explicit Device(const string&); explicit Device(const string&);
public: public:

View File

@ -22,7 +22,7 @@
using namespace std; using namespace std;
using namespace rascsi_interface; using namespace rascsi_interface;
multimap<int, Device *> DeviceFactory::devices; multimap<int, unique_ptr<PrimaryDevice>> DeviceFactory::devices;
DeviceFactory::DeviceFactory() DeviceFactory::DeviceFactory()
{ {
@ -66,25 +66,19 @@ DeviceFactory::DeviceFactory()
extension_mapping["iso"] = SCCD; extension_mapping["iso"] = SCCD;
} }
DeviceFactory::~DeviceFactory()
{
DeleteAllDevices();
}
DeviceFactory& DeviceFactory::instance() DeviceFactory& DeviceFactory::instance()
{ {
static DeviceFactory instance; static DeviceFactory instance;
return instance; return instance;
} }
void DeviceFactory::DeleteDevice(const Device *device) const void DeviceFactory::DeleteDevice(const PrimaryDevice *device) const
{ {
auto iterpair = devices.equal_range(device->GetId()); auto iterpair = devices.equal_range(device->GetId());
for (auto it = iterpair.first; it != iterpair.second; ++it) { for (auto it = iterpair.first; it != iterpair.second; ++it) {
if (it->second->GetLun() == device->GetLun()) { if (it->second->GetLun() == device->GetLun()) {
devices.erase(it); devices.erase(it);
delete device;
break; break;
} }
@ -93,30 +87,26 @@ void DeviceFactory::DeleteDevice(const Device *device) const
void DeviceFactory::DeleteAllDevices() const void DeviceFactory::DeleteAllDevices() const
{ {
for (const auto& [id, device] : devices) {
delete device;
}
devices.clear(); devices.clear();
} }
const Device * DeviceFactory::GetDeviceByIdAndLun(int i, int lun) const const PrimaryDevice *DeviceFactory::GetDeviceByIdAndLun(int i, int lun) const
{ {
for (const auto& [id, device] : devices) { for (const auto& [id, device] : devices) {
if (device->GetId() == i && device->GetLun() == lun) { if (device->GetId() == i && device->GetLun() == lun) {
return device; return device.get();
} }
} }
return nullptr; return nullptr;
} }
list<Device *> DeviceFactory::GetAllDevices() const list<PrimaryDevice *> DeviceFactory::GetAllDevices() const
{ {
list<Device *> result; list<PrimaryDevice *> result;
for (const auto& [id, device] : devices) { for (const auto& [id, device] : devices) {
result.push_back(device); result.push_back(device.get());
} }
return result; return result;
@ -155,7 +145,7 @@ PbDeviceType DeviceFactory::GetTypeForFile(const string& filename) const
} }
// ID -1 is used by rascsi to create a temporary device // ID -1 is used by rascsi to create a temporary device
Device *DeviceFactory::CreateDevice(PbDeviceType type, const string& filename, int id) PrimaryDevice *DeviceFactory::CreateDevice(PbDeviceType type, const string& filename, int id)
{ {
// If no type was specified try to derive the device type from the filename // If no type was specified try to derive the device type from the filename
if (type == UNDEFINED) { if (type == UNDEFINED) {
@ -165,7 +155,7 @@ Device *DeviceFactory::CreateDevice(PbDeviceType type, const string& filename, i
} }
} }
unique_ptr<Device> device; unique_ptr<PrimaryDevice> device;
switch (type) { switch (type) {
case SCHD: { case SCHD: {
if (string ext = GetExtension(filename); ext == "hdn" || ext == "hdi" || ext == "nhd") { if (string ext = GetExtension(filename); ext == "hdn" || ext == "hdi" || ext == "nhd") {
@ -248,7 +238,7 @@ Device *DeviceFactory::CreateDevice(PbDeviceType type, const string& filename, i
assert(device != nullptr); assert(device != nullptr);
Device *d = device.release(); PrimaryDevice *d = device.release();
if (d != nullptr) { if (d != nullptr) {
d->SetId(id); d->SetId(id);

View File

@ -23,14 +23,12 @@ using namespace rascsi_interface;
using Geometry = pair<uint32_t, uint32_t>; using Geometry = pair<uint32_t, uint32_t>;
class Device; class PrimaryDevice;
class DeviceFactory class DeviceFactory
{ {
friend class ControllerManager;
DeviceFactory(); DeviceFactory();
~DeviceFactory(); ~DeviceFactory() = default;
DeviceFactory(DeviceFactory&) = delete; DeviceFactory(DeviceFactory&) = delete;
DeviceFactory& operator=(const DeviceFactory&) = delete; DeviceFactory& operator=(const DeviceFactory&) = delete;
@ -38,10 +36,11 @@ public:
static DeviceFactory& instance(); static DeviceFactory& instance();
Device *CreateDevice(PbDeviceType, const string&, int); PrimaryDevice *CreateDevice(PbDeviceType, const string&, int);
void DeleteDevice(const Device *) const; void DeleteDevice(const PrimaryDevice *) const;
const Device *GetDeviceByIdAndLun(int, int) const; void DeleteAllDevices() const;
list<Device *> GetAllDevices() const; const PrimaryDevice *GetDeviceByIdAndLun(int, int) const;
list<PrimaryDevice *> GetAllDevices() const;
PbDeviceType GetTypeForFile(const string&) const; PbDeviceType GetTypeForFile(const string&) const;
const unordered_set<uint32_t>& GetSectorSizes(PbDeviceType type) { return sector_sizes[type]; } const unordered_set<uint32_t>& GetSectorSizes(PbDeviceType type) { return sector_sizes[type]; }
const unordered_set<uint32_t>& GetSectorSizes(const string&) const; const unordered_set<uint32_t>& GetSectorSizes(const string&) const;
@ -51,8 +50,6 @@ public:
private: private:
void DeleteAllDevices() const;
unordered_map<PbDeviceType, unordered_set<uint32_t>> sector_sizes; unordered_map<PbDeviceType, unordered_set<uint32_t>> sector_sizes;
// Optional mapping of drive capacities to drive geometries // Optional mapping of drive capacities to drive geometries
@ -64,5 +61,5 @@ private:
string GetExtension(const string&) const; string GetExtension(const string&) const;
static std::multimap<int, Device *> devices; static std::multimap<int, unique_ptr<PrimaryDevice>> devices;
}; };

View File

@ -57,10 +57,9 @@ Disk::Disk(const string& id) : ModePageDevice(id), ScsiBlockCommands()
Disk::~Disk() Disk::~Disk()
{ {
// Save disk cache // Save disk cache, only if ready
if (IsReady()) { if (IsReady() && disk.dcache) {
// Only if ready... disk.dcache->Save();
FlushCache();
} }
delete disk.dcache; delete disk.dcache;
@ -122,9 +121,7 @@ void Disk::FlushCache()
void Disk::Rezero() void Disk::Rezero()
{ {
CheckReady(); Seek();
EnterStatusPhase();
} }
void Disk::FormatUnit() void Disk::FormatUnit()
@ -136,9 +133,7 @@ void Disk::FormatUnit()
void Disk::ReassignBlocks() void Disk::ReassignBlocks()
{ {
CheckReady(); Seek();
EnterStatusPhase();
} }
void Disk::Read(access_mode mode) void Disk::Read(access_mode mode)

View File

@ -27,32 +27,14 @@
// //
//=========================================================================== //===========================================================================
DiskTrack::DiskTrack()
{
// Initialization of internal information
dt.track = 0;
dt.size = 0;
dt.sectors = 0;
dt.raw = FALSE;
dt.init = FALSE;
dt.changed = FALSE;
dt.length = 0;
dt.buffer = nullptr;
dt.maplen = 0;
dt.changemap = nullptr;
dt.imgoffset = 0;
}
DiskTrack::~DiskTrack() DiskTrack::~DiskTrack()
{ {
// Release memory, but do not save automatically // Release memory, but do not save automatically
if (dt.buffer) { if (dt.buffer) {
free(dt.buffer); free(dt.buffer);
dt.buffer = nullptr;
} }
if (dt.changemap) { if (dt.changemap) {
free(dt.changemap); free(dt.changemap);
dt.changemap = nullptr;
} }
} }

View File

@ -37,10 +37,10 @@ private:
BOOL *changemap; // Changed map BOOL *changemap; // Changed map
BOOL raw; // RAW mode flag BOOL raw; // RAW mode flag
off_t imgoffset; // Offset to actual data off_t imgoffset; // Offset to actual data
} dt; } dt = {};
public: public:
DiskTrack(); DiskTrack() = default;
~DiskTrack(); ~DiskTrack();
DiskTrack(DiskTrack&) = delete; DiskTrack(DiskTrack&) = delete;
DiskTrack& operator=(const DiskTrack&) = delete; DiskTrack& operator=(const DiskTrack&) = delete;

View File

@ -24,12 +24,7 @@ class Dispatcher
public: public:
Dispatcher() = default; Dispatcher() = default;
~Dispatcher() ~Dispatcher() = default;
{
for (auto const& [name, command] : commands) {
delete command;
}
}
Dispatcher(Dispatcher&) = delete; Dispatcher(Dispatcher&) = delete;
Dispatcher& operator=(const Dispatcher&) = delete; Dispatcher& operator=(const Dispatcher&) = delete;
@ -40,11 +35,11 @@ public:
_command_t(const char* _name, operation _execute) : name(_name), execute(_execute) { }; _command_t(const char* _name, operation _execute) : name(_name), execute(_execute) { };
}; };
unordered_map<scsi_command, command_t*> commands; unordered_map<scsi_command, unique_ptr<command_t>> commands;
void AddCommand(scsi_command opcode, const char* name, operation execute) void AddCommand(scsi_command opcode, const char* name, operation execute)
{ {
commands[opcode] = new command_t(name, execute); commands[opcode] = make_unique<command_t>(name, execute);
} }
bool Dispatch(T *instance, DWORD cmd) bool Dispatch(T *instance, DWORD cmd)

View File

@ -18,7 +18,7 @@ void FileSupport::ReserveFile(const Filepath& path, int id, int lun) const
reserved_files[path.GetPath()] = make_pair(id, lun); reserved_files[path.GetPath()] = make_pair(id, lun);
} }
void FileSupport::UnreserveFile() void FileSupport::UnreserveFile() const
{ {
reserved_files.erase(diskpath.GetPath()); reserved_files.erase(diskpath.GetPath());
} }

View File

@ -21,15 +21,11 @@ using id_set = pair<int, int>;
class FileSupport class FileSupport
{ {
friend class ControllerManager;
Filepath diskpath; Filepath diskpath;
// The list of image files in use and the IDs and LUNs using these files // The list of image files in use and the IDs and LUNs using these files
static unordered_map<string, id_set> reserved_files; static unordered_map<string, id_set> reserved_files;
static void UnreserveAll();
public: public:
FileSupport() = default; FileSupport() = default;
@ -41,7 +37,8 @@ public:
void SetPath(const Filepath& path) { diskpath = path; } void SetPath(const Filepath& path) { diskpath = path; }
void ReserveFile(const Filepath&, int, int) const; void ReserveFile(const Filepath&, int, int) const;
void UnreserveFile(); void UnreserveFile() const;
static void UnreserveAll();
static unordered_map<string, id_set> GetReservedFiles() { return reserved_files; } static unordered_map<string, id_set> GetReservedFiles() { return reserved_files; }
static void SetReservedFiles(const unordered_map<string, id_set>& files_in_use) static void SetReservedFiles(const unordered_map<string, id_set>& files_in_use)

View File

@ -35,6 +35,7 @@
#include "rascsi_exceptions.h" #include "rascsi_exceptions.h"
#include "device.h" #include "device.h"
#include "device_factory.h"
#include "host_services.h" #include "host_services.h"
using namespace scsi_defs; using namespace scsi_defs;
@ -69,7 +70,7 @@ void HostServices::StartStopUnit()
if (!start) { if (!start) {
// Flush any caches // Flush any caches
for (Device *device : devices) { for (Device *device : DeviceFactory::instance().GetAllDevices()) {
device->FlushCache(); device->FlushCache();
} }
@ -175,14 +176,15 @@ void HostServices::AddRealtimeClockPage(map<int, vector<BYTE>>& pages, bool chan
buf[3] = 0x00; buf[3] = 0x00;
std::time_t t = std::time(nullptr); std::time_t t = std::time(nullptr);
std::tm tm = *std::localtime(&t); tm localtime;
buf[4] = (BYTE)tm.tm_year; localtime_r(&t, &localtime);
buf[5] = (BYTE)tm.tm_mon; buf[4] = (BYTE)localtime.tm_year;
buf[6] = (BYTE)tm.tm_mday; buf[5] = (BYTE)localtime.tm_mon;
buf[7] = (BYTE)tm.tm_hour; buf[6] = (BYTE)localtime.tm_mday;
buf[8] = (BYTE)tm.tm_min; buf[7] = (BYTE)localtime.tm_hour;
buf[8] = (BYTE)localtime.tm_min;
// Ignore leap second for simplicity // Ignore leap second for simplicity
buf[9] = (BYTE)(tm.tm_sec < 60 ? tm.tm_sec : 59); buf[9] = (BYTE)(localtime.tm_sec < 60 ? localtime.tm_sec : 59);
pages[32] = buf; pages[32] = buf;
} }

View File

@ -11,14 +11,13 @@
#pragma once #pragma once
#include "scsi_primary_commands.h" class ScsiBlockCommands
class ScsiBlockCommands : virtual public ScsiPrimaryCommands
{ {
public: public:
ScsiBlockCommands() = default; ScsiBlockCommands() = default;
~ScsiBlockCommands() override = default; virtual ~ScsiBlockCommands() = default;
// Mandatory commands // Mandatory commands
virtual void FormatUnit() = 0; virtual void FormatUnit() = 0;

View File

@ -11,14 +11,13 @@
#pragma once #pragma once
#include "scsi_primary_commands.h" class ScsiMmcCommands
class ScsiMmcCommands : virtual public ScsiPrimaryCommands
{ {
public: public:
ScsiMmcCommands() = default; ScsiMmcCommands() = default;
~ScsiMmcCommands() override = default; virtual ~ScsiMmcCommands() = default;
virtual void ReadToc() = 0; virtual void ReadToc() = 0;
virtual void GetEventStatusNotification() = 0; virtual void GetEventStatusNotification() = 0;

View File

@ -13,6 +13,7 @@
class ScsiPrimaryCommands class ScsiPrimaryCommands
{ {
public: public:
ScsiPrimaryCommands() = default; ScsiPrimaryCommands() = default;

View File

@ -11,14 +11,13 @@
#pragma once #pragma once
#include "scsi_primary_commands.h" class ScsiPrinterCommands
class ScsiPrinterCommands : virtual public ScsiPrimaryCommands
{ {
public: public:
ScsiPrinterCommands() = default; ScsiPrinterCommands() = default;
~ScsiPrinterCommands() override = default; virtual ~ScsiPrinterCommands() = default;
// Mandatory commands // Mandatory commands
virtual void Print() = 0; virtual void Print() = 0;

View File

@ -123,7 +123,7 @@ void ModePageDevice::ModeSelect10()
EnterDataOutPhase(); EnterDataOutPhase();
} }
int ModePageDevice::ModeSelectCheck(int length) int ModePageDevice::ModeSelectCheck(int length) const
{ {
// Error if save parameters are set for other types than of SCHD, SCRM or SCMO // Error if save parameters are set for other types than of SCHD, SCRM or SCMO
// TODO The assumption above is not correct, and this code should be located elsewhere // TODO The assumption above is not correct, and this code should be located elsewhere
@ -134,13 +134,13 @@ int ModePageDevice::ModeSelectCheck(int length)
return length; return length;
} }
int ModePageDevice::ModeSelectCheck6() int ModePageDevice::ModeSelectCheck6() const
{ {
// Receive the data specified by the parameter length // Receive the data specified by the parameter length
return ModeSelectCheck(ctrl->cmd[4]); return ModeSelectCheck(ctrl->cmd[4]);
} }
int ModePageDevice::ModeSelectCheck10() int ModePageDevice::ModeSelectCheck10() const
{ {
// Receive the data specified by the parameter length // Receive the data specified by the parameter length
int length = ctrl->cmd[7]; int length = ctrl->cmd[7];

View File

@ -50,7 +50,7 @@ private:
void ModeSelect6(); void ModeSelect6();
void ModeSelect10(); void ModeSelect10();
int ModeSelectCheck(int); int ModeSelectCheck(int) const;
int ModeSelectCheck6(); int ModeSelectCheck6() const;
int ModeSelectCheck10(); int ModeSelectCheck10() const;
}; };

View File

@ -182,7 +182,7 @@ vector<BYTE> PrimaryDevice::HandleInquiry(device_type type, scsi_level level, bo
return buf; return buf;
} }
vector<BYTE> PrimaryDevice::HandleRequestSense() vector<BYTE> PrimaryDevice::HandleRequestSense() const
{ {
// Return not ready only if there are no errors // Return not ready only if there are no errors
if (!GetStatusCode() && !IsReady()) { if (!GetStatusCode() && !IsReady()) {

View File

@ -19,8 +19,9 @@
using namespace std; using namespace std;
class PrimaryDevice: public Device, virtual public ScsiPrimaryCommands class PrimaryDevice: public ScsiPrimaryCommands, public Device
{ {
public: public:
explicit PrimaryDevice(const string&); explicit PrimaryDevice(const string&);
@ -54,7 +55,7 @@ private:
void ReportLuns() override; void ReportLuns() override;
void Inquiry() override; void Inquiry() override;
vector<BYTE> HandleRequestSense(); vector<BYTE> HandleRequestSense() const;
Dispatcher<PrimaryDevice> dispatcher; Dispatcher<PrimaryDevice> dispatcher;
}; };

View File

@ -314,7 +314,7 @@ int SCSIDaynaPort::WriteCheck(uint64_t)
// XX XX ... is the actual packet // XX XX ... is the actual packet
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
bool SCSIDaynaPort::WriteBytes(const DWORD *cdb, BYTE *buf, uint64_t) bool SCSIDaynaPort::WriteBytes(const DWORD *cdb, const BYTE *buf, uint64_t)
{ {
auto data_format = (BYTE)cdb[5]; auto data_format = (BYTE)cdb[5];
WORD data_length = (WORD)cdb[4] + ((WORD)cdb[3] << 8); WORD data_length = (WORD)cdb[4] + ((WORD)cdb[3] << 8);

View File

@ -53,7 +53,7 @@ public:
// Commands // Commands
vector<BYTE> InquiryInternal() const override; vector<BYTE> InquiryInternal() const override;
int Read(const DWORD *cdb, BYTE *, uint64_t) override; int Read(const DWORD *cdb, BYTE *, uint64_t) override;
bool WriteBytes(const DWORD *, BYTE *, uint64_t); bool WriteBytes(const DWORD *, const BYTE *, uint64_t);
int WriteCheck(uint64_t block) override; int WriteCheck(uint64_t block) override;
int RetrieveStats(const DWORD *cdb, BYTE *buffer) const; int RetrieveStats(const DWORD *cdb, BYTE *buffer) const;

View File

@ -304,8 +304,8 @@ void SCSIBR::SendMessage10()
// Reallocate buffer (because it is not transfer for each block) // Reallocate buffer (because it is not transfer for each block)
if (ctrl->bufsize < 0x1000000) { if (ctrl->bufsize < 0x1000000) {
delete[] ctrl->buffer; delete[] ctrl->buffer;
ctrl->buffer = new BYTE[ctrl->bufsize];
ctrl->bufsize = 0x1000000; ctrl->bufsize = 0x1000000;
ctrl->buffer = new BYTE[ctrl->bufsize];
} }
// Set transfer amount // Set transfer amount
@ -352,11 +352,9 @@ void SCSIBR::ReceivePacket()
packet_len = tap->Rx(packet_buf); packet_len = tap->Rx(packet_buf);
// Check if received packet // Check if received packet
if (memcmp(packet_buf, mac_addr, 6) != 0) { if (memcmp(packet_buf, mac_addr, 6) != 0 && memcmp(packet_buf, bcast_addr, 6) != 0) {
if (memcmp(packet_buf, bcast_addr, 6) != 0) { packet_len = 0;
packet_len = 0; return;
return;
}
} }
// Discard if it exceeds the buffer size // Discard if it exceeds the buffer size
@ -388,7 +386,7 @@ void SCSIBR::GetPacketBuf(BYTE *buf)
packet_enable = false; packet_enable = false;
} }
void SCSIBR::SendPacket(BYTE *buf, int len) void SCSIBR::SendPacket(const BYTE *buf, int len)
{ {
assert(tap); assert(tap);
@ -1144,7 +1142,7 @@ void SCSIBR::WriteFs(int func, BYTE *buf)
// File system write (input option data) // File system write (input option data)
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
void SCSIBR::WriteFsOpt(BYTE *buf, int num) void SCSIBR::WriteFsOpt(const BYTE *buf, int num)
{ {
memcpy(fsopt, buf, num); memcpy(fsopt, buf, num);
} }

View File

@ -60,7 +60,7 @@ private:
void SetMacAddr(const BYTE *buf); // Set MAC address void SetMacAddr(const BYTE *buf); // Set MAC address
void ReceivePacket(); // Receive a packet void ReceivePacket(); // Receive a packet
void GetPacketBuf(BYTE *buf); // Get a packet void GetPacketBuf(BYTE *buf); // Get a packet
void SendPacket(BYTE *buf, int len); // Send a packet void SendPacket(const BYTE *buf, int len); // Send a packet
CTapDriver *tap = nullptr; // TAP driver CTapDriver *tap = nullptr; // TAP driver
bool m_bTapEnable = false; // TAP valid flag bool m_bTapEnable = false; // TAP valid flag
@ -73,7 +73,7 @@ private:
int ReadFsOut(BYTE *buf) const; // Read filesystem (return data) int ReadFsOut(BYTE *buf) const; // Read filesystem (return data)
int ReadFsOpt(BYTE *buf) const; // Read file system (optional data) int ReadFsOpt(BYTE *buf) const; // Read file system (optional data)
void WriteFs(int func, BYTE *buf); // File system write (execute) void WriteFs(int func, BYTE *buf); // File system write (execute)
void WriteFsOpt(BYTE *buf, int len); // File system write (optional data) void WriteFsOpt(const BYTE *buf, int len); // File system write (optional data)
// Command handlers // Command handlers
void FS_InitDevice(BYTE *buf); // $40 - boot void FS_InitDevice(BYTE *buf); // $40 - boot

View File

@ -212,11 +212,8 @@ void SCSIPrinter::SendDiagnostic()
void SCSIPrinter::StopPrint() void SCSIPrinter::StopPrint()
{ {
CheckReservation(); // Both command implemntations are identical
TestUnitReady();
// Nothing to do, printing has not yet been started
EnterStatusPhase();
} }
bool SCSIPrinter::WriteByteSequence(BYTE *buf, uint32_t length) bool SCSIPrinter::WriteByteSequence(BYTE *buf, uint32_t length)
@ -234,7 +231,7 @@ bool SCSIPrinter::WriteByteSequence(BYTE *buf, uint32_t length)
LOGTRACE("Appending %d byte(s) to printer output file", length) LOGTRACE("Appending %d byte(s) to printer output file", length)
uint32_t num_written = (uint32_t)write(fd, buf, length); auto num_written = (uint32_t)write(fd, buf, length);
return num_written == length; return num_written == length;
} }

View File

@ -17,7 +17,7 @@
using namespace std; using namespace std;
class SCSIPrinter: public PrimaryDevice, public ScsiPrinterCommands class SCSIPrinter: public PrimaryDevice, public ScsiPrinterCommands //NOSONAR Custom destructor cannot be removed
{ {
static constexpr const char *TMP_FILE_PATTERN = "/tmp/rascsi_sclp-XXXXXX"; static constexpr const char *TMP_FILE_PATTERN = "/tmp/rascsi_sclp-XXXXXX";
static constexpr const int TMP_FILENAME_LENGTH = strlen(TMP_FILE_PATTERN); static constexpr const int TMP_FILENAME_LENGTH = strlen(TMP_FILE_PATTERN);

View File

@ -299,11 +299,11 @@ void SCSICD::OpenIso(const Filepath& path)
} }
// Create only one data track // Create only one data track
assert(!track[0]); assert(!tracks.size());
track[0] = new CDTrack(); auto track = make_unique<CDTrack>();
track[0]->Init(1, 0, GetBlockCount() - 1); track->Init(1, 0, GetBlockCount() - 1);
track[0]->SetPath(false, path); track->SetPath(false, path);
tracks = 1; tracks.push_back(move(track));
dataindex = 0; dataindex = 0;
} }
@ -332,11 +332,11 @@ void SCSICD::OpenPhysical(const Filepath& path)
SetBlockCount((DWORD)(size >> GetSectorSizeShiftCount())); SetBlockCount((DWORD)(size >> GetSectorSizeShiftCount()));
// Create only one data track // Create only one data track
ASSERT(!track[0]); ASSERT(!tracks.size());
track[0] = new CDTrack(); auto track = make_unique<CDTrack>();
track[0]->Init(1, 0, GetBlockCount() - 1); track->Init(1, 0, GetBlockCount() - 1);
track[0]->SetPath(false, path); track->SetPath(false, path);
tracks = 1; tracks.push_back(move(track));
dataindex = 0; dataindex = 0;
} }
@ -440,7 +440,7 @@ int SCSICD::Read(const DWORD *cdb, BYTE *buf, uint64_t block)
throw scsi_error_exception(sense_key::ILLEGAL_REQUEST, asc::LBA_OUT_OF_RANGE); throw scsi_error_exception(sense_key::ILLEGAL_REQUEST, asc::LBA_OUT_OF_RANGE);
} }
assert(track[index]); assert(tracks[index]);
// If different from the current data track // If different from the current data track
if (dataindex != index) { if (dataindex != index) {
@ -449,12 +449,12 @@ int SCSICD::Read(const DWORD *cdb, BYTE *buf, uint64_t block)
disk.dcache = nullptr; disk.dcache = nullptr;
// Reset the number of blocks // Reset the number of blocks
SetBlockCount(track[index]->GetBlocks()); SetBlockCount(tracks[index]->GetBlocks());
ASSERT(GetBlockCount() > 0); ASSERT(GetBlockCount() > 0);
// Recreate the disk cache // Recreate the disk cache
Filepath path; Filepath path;
track[index]->GetPath(path); tracks[index]->GetPath(path);
disk.dcache = new DiskCache(path, GetSectorSizeShiftCount(), GetBlockCount()); disk.dcache = new DiskCache(path, GetSectorSizeShiftCount(), GetBlockCount());
disk.dcache->SetRawMode(rawfile); disk.dcache->SetRawMode(rawfile);
@ -475,8 +475,8 @@ int SCSICD::ReadToc(const DWORD *cdb, BYTE *buf)
CheckReady(); CheckReady();
// If ready, there is at least one track // If ready, there is at least one track
assert(tracks > 0); assert(tracks.size() > 0);
assert(track[0]); assert(tracks[0]);
// Get allocation length, clear buffer // Get allocation length, clear buffer
int length = cdb[7] << 8; int length = cdb[7] << 8;
@ -487,35 +487,33 @@ int SCSICD::ReadToc(const DWORD *cdb, BYTE *buf)
bool msf = cdb[1] & 0x02; bool msf = cdb[1] & 0x02;
// Get and check the last track number // Get and check the last track number
int last = track[tracks - 1]->GetTrackNo(); int last = tracks[tracks.size() - 1]->GetTrackNo();
if ((int)cdb[6] > last) { // Except for AA
// Except for AA if ((int)cdb[6] > last && cdb[6] != 0xaa) {
if (cdb[6] != 0xaa) { throw scsi_error_exception(sense_key::ILLEGAL_REQUEST, asc::INVALID_FIELD_IN_CDB);
throw scsi_error_exception(sense_key::ILLEGAL_REQUEST, asc::INVALID_FIELD_IN_CDB);
}
} }
// Check start index // Check start index
int index = 0; int index = 0;
if (cdb[6] != 0x00) { if (cdb[6] != 0x00) {
// Advance the track until the track numbers match // Advance the track until the track numbers match
while (track[index]) { while (tracks[index]) {
if ((int)cdb[6] == track[index]->GetTrackNo()) { if ((int)cdb[6] == tracks[index]->GetTrackNo()) {
break; break;
} }
index++; index++;
} }
// AA if not found or internal error // AA if not found or internal error
if (!track[index]) { if (!tracks[index]) {
if (cdb[6] == 0xaa) { if (cdb[6] == 0xaa) {
// Returns the final LBA+1 because it is AA // Returns the final LBA+1 because it is AA
buf[0] = 0x00; buf[0] = 0x00;
buf[1] = 0x0a; buf[1] = 0x0a;
buf[2] = (BYTE)track[0]->GetTrackNo(); buf[2] = (BYTE)tracks[0]->GetTrackNo();
buf[3] = (BYTE)last; buf[3] = (BYTE)last;
buf[6] = 0xaa; buf[6] = 0xaa;
DWORD lba = track[tracks - 1]->GetLast() + 1; DWORD lba = tracks[tracks.size() - 1]->GetLast() + 1;
if (msf) { if (msf) {
LBAtoMSF(lba, &buf[8]); LBAtoMSF(lba, &buf[8]);
} else { } else {
@ -531,20 +529,20 @@ int SCSICD::ReadToc(const DWORD *cdb, BYTE *buf)
} }
// Number of track descriptors returned this time (number of loops) // Number of track descriptors returned this time (number of loops)
int loop = last - track[index]->GetTrackNo() + 1; int loop = last - tracks[index]->GetTrackNo() + 1;
assert(loop >= 1); assert(loop >= 1);
// Create header // Create header
buf[0] = (BYTE)(((loop << 3) + 2) >> 8); buf[0] = (BYTE)(((loop << 3) + 2) >> 8);
buf[1] = (BYTE)((loop << 3) + 2); buf[1] = (BYTE)((loop << 3) + 2);
buf[2] = (BYTE)track[0]->GetTrackNo(); buf[2] = (BYTE)tracks[0]->GetTrackNo();
buf[3] = (BYTE)last; buf[3] = (BYTE)last;
buf += 4; buf += 4;
// Loop.... // Loop....
for (int i = 0; i < loop; i++) { for (int i = 0; i < loop; i++) {
// ADR and Control // ADR and Control
if (track[index]->IsAudio()) { if (tracks[index]->IsAudio()) {
// audio track // audio track
buf[1] = 0x10; buf[1] = 0x10;
} else { } else {
@ -553,14 +551,14 @@ int SCSICD::ReadToc(const DWORD *cdb, BYTE *buf)
} }
// track number // track number
buf[2] = (BYTE)track[index]->GetTrackNo(); buf[2] = (BYTE)tracks[index]->GetTrackNo();
// track address // track address
if (msf) { if (msf) {
LBAtoMSF(track[index]->GetFirst(), &buf[4]); LBAtoMSF(tracks[index]->GetFirst(), &buf[4]);
} else { } else {
buf[6] = (BYTE)(track[index]->GetFirst() >> 8); buf[6] = (BYTE)(tracks[index]->GetFirst() >> 8);
buf[7] = (BYTE)(track[index]->GetFirst()); buf[7] = (BYTE)(tracks[index]->GetFirst());
} }
// Advance buffer pointer and index // Advance buffer pointer and index
@ -615,14 +613,7 @@ void SCSICD::LBAtoMSF(DWORD lba, BYTE *msf) const
void SCSICD::ClearTrack() void SCSICD::ClearTrack()
{ {
// delete the track object tracks.clear();
for (auto t: track) {
delete t;
t = nullptr;
}
// Number of tracks is 0
tracks = 0;
// No settings for data and audio // No settings for data and audio
dataindex = -1; dataindex = -1;
@ -638,10 +629,10 @@ void SCSICD::ClearTrack()
int SCSICD::SearchTrack(DWORD lba) const int SCSICD::SearchTrack(DWORD lba) const
{ {
// Track loop // Track loop
for (int i = 0; i < tracks; i++) { for (size_t i = 0; i < tracks.size(); i++) {
// Listen to the track // Listen to the track
assert(track[i]); assert(tracks[i]);
if (track[i]->IsValid(lba)) { if (tracks[i]->IsValid(lba)) {
return i; return i;
} }
} }

View File

@ -28,15 +28,13 @@
//=========================================================================== //===========================================================================
class CDTrack class CDTrack
{ {
private:
friend class SCSICD; public:
CDTrack() = default; CDTrack() = default;
virtual ~CDTrack() final = default; virtual ~CDTrack() final = default;
CDTrack(CDTrack&) = delete; CDTrack(CDTrack&) = delete;
CDTrack& operator=(const CDTrack&) = delete;
public:
void Init(int track, DWORD first, DWORD last); void Init(int track, DWORD first, DWORD last);
@ -66,8 +64,6 @@ private:
//=========================================================================== //===========================================================================
class SCSICD : public Disk, public ScsiMmcCommands, public FileSupport class SCSICD : public Disk, public ScsiMmcCommands, public FileSupport
{ {
// Maximum number of tracks
static const int TRACK_MAX = 96;
public: public:
@ -114,8 +110,7 @@ private:
// Track management // Track management
void ClearTrack(); // Clear the track void ClearTrack(); // Clear the track
int SearchTrack(DWORD lba) const; // Track search int SearchTrack(DWORD lba) const; // Track search
CDTrack* track[TRACK_MAX] = {}; // Track opbject references vector<unique_ptr<CDTrack>> tracks; // Track opbject references
int tracks = 0; // Effective number of track objects
int dataindex = -1; // Current data track int dataindex = -1; // Current data track
int audioindex = -1; // Current audio track int audioindex = -1; // Current audio track
}; };

View File

@ -161,7 +161,6 @@ bool protobuf_util::ReturnLocalizedError(const CommandContext& context, const Lo
const PbErrorCode error_code, const string& arg1, const string& arg2, const string& arg3) const PbErrorCode error_code, const string& arg1, const string& arg2, const string& arg3)
{ {
// For the logfile always use English // For the logfile always use English
// TODO This line forces rasctl to depend on the localizer. This should be fixed.
LOGERROR("%s", localizer.Localize(key, "en", arg1, arg2, arg3).c_str()) LOGERROR("%s", localizer.Localize(key, "en", arg1, arg2, arg3).c_str())
return ReturnStatus(context, false, localizer.Localize(key, context.locale, arg1, arg2, arg3), error_code, false); return ReturnStatus(context, false, localizer.Localize(key, context.locale, arg1, arg2, arg3), error_code, false);

View File

@ -57,7 +57,7 @@ static const char COMPONENT_SEPARATOR = ':';
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
static volatile bool running; // Running flag static volatile bool running; // Running flag
static volatile bool active; // Processing flag static volatile bool active; // Processing flag
unique_ptr<GPIOBUS> bus; // GPIO Bus shared_ptr<GPIOBUS> bus; // GPIO Bus
int monsocket; // Monitor Socket int monsocket; // Monitor Socket
pthread_t monthread; // Monitor Thread pthread_t monthread; // Monitor Thread
pthread_mutex_t ctrl_mutex; // Semaphore for the ctrl array pthread_mutex_t ctrl_mutex; // Semaphore for the ctrl array
@ -177,7 +177,7 @@ bool InitService(int port)
bool InitBus() bool InitBus()
{ {
// GPIOBUS creation // GPIOBUS creation
bus = make_unique<GPIOBUS>(); bus = make_shared<GPIOBUS>();
// GPIO Initialization // GPIO Initialization
if (!bus->Init()) { if (!bus->Init()) {
@ -262,7 +262,7 @@ string ValidateLunSetup(const PbCommand& command)
} }
// Collect LUN bit vectors of existing devices // Collect LUN bit vectors of existing devices
for (const Device *device : device_factory.GetAllDevices()) { for (const auto device : device_factory.GetAllDevices()) {
luns[device->GetId()] |= 1 << device->GetLun(); luns[device->GetId()] |= 1 << device->GetLun();
} }
@ -369,7 +369,9 @@ string SetReservedIds(string_view ids)
void DetachAll() void DetachAll()
{ {
controller_manager.DeleteAllControllersAndDevices(); controller_manager.DeleteAllControllers();
DeviceFactory::instance().DeleteAllDevices();
FileSupport::UnreserveAll();
LOGINFO("Detached all devices") LOGINFO("Detached all devices")
} }
@ -391,7 +393,7 @@ bool Attach(const CommandContext& context, const PbDeviceDefinition& pb_device,
string filename = GetParam(pb_device, "file"); string filename = GetParam(pb_device, "file");
Device *device = device_factory.CreateDevice(type, filename, id); PrimaryDevice *device = device_factory.CreateDevice(type, filename, id);
if (device == nullptr) { if (device == nullptr) {
if (type == UNDEFINED) { if (type == UNDEFINED) {
return ReturnLocalizedError(context, ERROR_MISSING_DEVICE_TYPE, filename); return ReturnLocalizedError(context, ERROR_MISSING_DEVICE_TYPE, filename);
@ -451,7 +453,7 @@ bool Attach(const CommandContext& context, const PbDeviceDefinition& pb_device,
} }
Filepath filepath; Filepath filepath;
if (file_support && !filename.empty()) { if (file_support != nullptr && !filename.empty()) {
filepath.SetPath(filename.c_str()); filepath.SetPath(filename.c_str());
string initial_filename = filepath.GetPath(); string initial_filename = filepath.GetPath();
@ -513,11 +515,9 @@ bool Attach(const CommandContext& context, const PbDeviceDefinition& pb_device,
", unit " +to_string(unit) + " failed"); ", unit " +to_string(unit) + " failed");
} }
// Replace with the newly created unit
pthread_mutex_lock(&ctrl_mutex); pthread_mutex_lock(&ctrl_mutex);
if (auto primary_device = static_cast<PrimaryDevice *>(device); if (!controller_manager.CreateScsiController(bus, device)) {
!controller_manager.CreateScsiController(bus.get(), primary_device)) {
pthread_mutex_unlock(&ctrl_mutex); pthread_mutex_unlock(&ctrl_mutex);
return ReturnStatus(context, false, "Couldn't create SCSI controller instance"); return ReturnStatus(context, false, "Couldn't create SCSI controller instance");
@ -1511,7 +1511,7 @@ int main(int argc, char* argv[])
pthread_mutex_lock(&ctrl_mutex); pthread_mutex_lock(&ctrl_mutex);
// Identify the responsible controller // Identify the responsible controller
AbstractController *controller = controller_manager.IdentifyController(id_data); shared_ptr<AbstractController> controller = controller_manager.IdentifyController(id_data);
if (controller != nullptr) { if (controller != nullptr) {
initiator_id = controller->ExtractInitiatorId(id_data); initiator_id = controller->ExtractInitiatorId(id_data);

View File

@ -124,7 +124,7 @@ bool RascsiImage::IsValidDstFilename(const string& filename) const
return stat(filename.c_str(), &st); return stat(filename.c_str(), &st);
} }
bool RascsiImage::CreateImage(const CommandContext& context, const PbCommand& command) bool RascsiImage::CreateImage(const CommandContext& context, const PbCommand& command) const
{ {
string filename = GetParam(command, "file"); string filename = GetParam(command, "file");
if (filename.empty()) { if (filename.empty()) {
@ -189,7 +189,7 @@ bool RascsiImage::CreateImage(const CommandContext& context, const PbCommand& co
return ReturnStatus(context); return ReturnStatus(context);
} }
bool RascsiImage::DeleteImage(const CommandContext& context, const PbCommand& command) bool RascsiImage::DeleteImage(const CommandContext& context, const PbCommand& command) const
{ {
string filename = GetParam(command, "file"); string filename = GetParam(command, "file");
if (filename.empty()) { if (filename.empty()) {
@ -237,7 +237,7 @@ bool RascsiImage::DeleteImage(const CommandContext& context, const PbCommand& co
return ReturnStatus(context); return ReturnStatus(context);
} }
bool RascsiImage::RenameImage(const CommandContext& context, const PbCommand& command) bool RascsiImage::RenameImage(const CommandContext& context, const PbCommand& command) const
{ {
string from = GetParam(command, "from"); string from = GetParam(command, "from");
if (from.empty()) { if (from.empty()) {
@ -280,7 +280,7 @@ bool RascsiImage::RenameImage(const CommandContext& context, const PbCommand& co
return ReturnStatus(context); return ReturnStatus(context);
} }
bool RascsiImage::CopyImage(const CommandContext& context, const PbCommand& command) bool RascsiImage::CopyImage(const CommandContext& context, const PbCommand& command) const
{ {
string from = GetParam(command, "from"); string from = GetParam(command, "from");
if (from.empty()) { if (from.empty()) {
@ -364,7 +364,7 @@ bool RascsiImage::CopyImage(const CommandContext& context, const PbCommand& comm
return ReturnStatus(context); return ReturnStatus(context);
} }
bool RascsiImage::SetImagePermissions(const CommandContext& context, const PbCommand& command) bool RascsiImage::SetImagePermissions(const CommandContext& context, const PbCommand& command) const
{ {
string filename = GetParam(command, "file"); string filename = GetParam(command, "file");
if (filename.empty()) { if (filename.empty()) {

View File

@ -22,6 +22,8 @@ public:
RascsiImage(); RascsiImage();
~RascsiImage() = default; ~RascsiImage() = default;
RascsiImage(RascsiImage&) = delete;
RascsiImage& operator=(const RascsiImage&) = delete;
void SetDepth(int d) { depth = d; } void SetDepth(int d) { depth = d; }
int GetDepth() const { return depth; } int GetDepth() const { return depth; }
@ -31,11 +33,11 @@ public:
string SetDefaultImageFolder(const string&); string SetDefaultImageFolder(const string&);
bool IsValidSrcFilename(const string&) const; bool IsValidSrcFilename(const string&) const;
bool IsValidDstFilename(const string&) const; bool IsValidDstFilename(const string&) const;
bool CreateImage(const CommandContext&, const PbCommand&); bool CreateImage(const CommandContext&, const PbCommand&) const;
bool DeleteImage(const CommandContext&, const PbCommand&); bool DeleteImage(const CommandContext&, const PbCommand&) const;
bool RenameImage(const CommandContext&, const PbCommand&); bool RenameImage(const CommandContext&, const PbCommand&) const;
bool CopyImage(const CommandContext&, const PbCommand&); bool CopyImage(const CommandContext&, const PbCommand&) const;
bool SetImagePermissions(const CommandContext&, const PbCommand&); bool SetImagePermissions(const CommandContext&, const PbCommand&) const;
private: private:

View File

@ -32,7 +32,7 @@ PbDeviceProperties *RascsiResponse::GetDeviceProperties(const Device *device)
properties->set_stoppable(device->IsStoppable()); properties->set_stoppable(device->IsStoppable());
properties->set_removable(device->IsRemovable()); properties->set_removable(device->IsRemovable());
properties->set_lockable(device->IsLockable()); properties->set_lockable(device->IsLockable());
properties->set_supports_file(dynamic_cast<const FileSupport *>(device)); properties->set_supports_file(dynamic_cast<const FileSupport *>(device) != nullptr);
properties->set_supports_params(device->SupportsParams()); properties->set_supports_params(device->SupportsParams());
PbDeviceType t = UNDEFINED; PbDeviceType t = UNDEFINED;
@ -56,9 +56,9 @@ void RascsiResponse::GetDeviceTypeProperties(PbDeviceTypesInfo& device_types_inf
{ {
PbDeviceTypeProperties *type_properties = device_types_info.add_properties(); PbDeviceTypeProperties *type_properties = device_types_info.add_properties();
type_properties->set_type(type); type_properties->set_type(type);
const Device *device = device_factory->CreateDevice(type, "", -1); const PrimaryDevice *device = device_factory->CreateDevice(type, "", -1);
type_properties->set_allocated_properties(GetDeviceProperties(device)); type_properties->set_allocated_properties(GetDeviceProperties(device));
device_factory->DeleteDevice(device); device_factory->DeleteDevice(device); //NOSONAR The alloced memory is managed by protobuf
} }
void RascsiResponse::GetAllDeviceTypeProperties(PbDeviceTypesInfo& device_types_info) void RascsiResponse::GetAllDeviceTypeProperties(PbDeviceTypesInfo& device_types_info)
@ -94,7 +94,7 @@ void RascsiResponse::GetDevice(const Device *device, PbDevice *pb_device)
status->set_removed(device->IsRemoved()); status->set_removed(device->IsRemoved());
status->set_locked(device->IsLocked()); status->set_locked(device->IsLocked());
if (device->SupportsParams()) { if (device->SupportsParams()) { //NOSONAR The alloced memory is managed by protobuf
for (const auto& [key, value] : device->GetParams()) { for (const auto& [key, value] : device->GetParams()) {
AddParam(*pb_device, key, value); AddParam(*pb_device, key, value);
} }
@ -113,9 +113,9 @@ void RascsiResponse::GetDevice(const Device *device, PbDevice *pb_device)
GetImageFile(image_file, device->IsRemovable() && !device->IsReady() ? "" : filepath.GetPath()); GetImageFile(image_file, device->IsRemovable() && !device->IsReady() ? "" : filepath.GetPath());
pb_device->set_allocated_file(image_file); pb_device->set_allocated_file(image_file);
} }
} } //NOSONAR The alloced memory is managed by protobuf
bool RascsiResponse::GetImageFile(PbImageFile *image_file, const string& filename) bool RascsiResponse::GetImageFile(PbImageFile *image_file, const string& filename) const
{ {
if (!filename.empty()) { if (!filename.empty()) {
image_file->set_name(filename); image_file->set_name(filename);
@ -209,7 +209,7 @@ void RascsiResponse::GetAvailableImages(PbResult& result, PbServerInfo& server_i
image_files_info->set_default_image_folder(rascsi_image->GetDefaultImageFolder()); image_files_info->set_default_image_folder(rascsi_image->GetDefaultImageFolder());
server_info.set_allocated_image_files_info(image_files_info); server_info.set_allocated_image_files_info(image_files_info);
result.set_status(true); result.set_status(true); //NOSONAR The alloced memory is managed by protobuf
} }
PbReservedIdsInfo *RascsiResponse::GetReservedIds(PbResult& result, const unordered_set<int>& ids) PbReservedIdsInfo *RascsiResponse::GetReservedIds(PbResult& result, const unordered_set<int>& ids)
@ -280,14 +280,14 @@ PbServerInfo *RascsiResponse::GetServerInfo(PbResult& result, const unordered_se
auto server_info = make_unique<PbServerInfo>().release(); auto server_info = make_unique<PbServerInfo>().release();
server_info->set_allocated_version_info(GetVersionInfo(result)); server_info->set_allocated_version_info(GetVersionInfo(result));
server_info->set_allocated_log_level_info(GetLogLevelInfo(result, current_log_level)); server_info->set_allocated_log_level_info(GetLogLevelInfo(result, current_log_level)); //NOSONAR The alloced memory is managed by protobuf
GetAllDeviceTypeProperties(*server_info->mutable_device_types_info()); GetAllDeviceTypeProperties(*server_info->mutable_device_types_info()); //NOSONAR The alloced memory is managed by protobuf
GetAvailableImages(result, *server_info, folder_pattern, file_pattern, scan_depth); GetAvailableImages(result, *server_info, folder_pattern, file_pattern, scan_depth);
server_info->set_allocated_network_interfaces_info(GetNetworkInterfacesInfo(result)); server_info->set_allocated_network_interfaces_info(GetNetworkInterfacesInfo(result));
server_info->set_allocated_mapping_info(GetMappingInfo(result)); server_info->set_allocated_mapping_info(GetMappingInfo(result)); //NOSONAR The alloced memory is managed by protobuf
GetDevices(*server_info); GetDevices(*server_info); //NOSONAR The alloced memory is managed by protobuf
server_info->set_allocated_reserved_ids_info(GetReservedIds(result, reserved_ids)); server_info->set_allocated_reserved_ids_info(GetReservedIds(result, reserved_ids));
server_info->set_allocated_operation_info(GetOperationInfo(result, scan_depth)); server_info->set_allocated_operation_info(GetOperationInfo(result, scan_depth)); //NOSONAR The alloced memory is managed by protobuf
result.set_status(true); result.set_status(true);
@ -492,7 +492,7 @@ PbOperationInfo *RascsiResponse::GetOperationInfo(PbResult& result, int depth)
} }
void RascsiResponse::CreateOperation(PbOperationInfo *operation_info, PbOperationMetaData *meta_data, void RascsiResponse::CreateOperation(PbOperationInfo *operation_info, PbOperationMetaData *meta_data,
const PbOperation& operation, const string& description) const PbOperation& operation, const string& description) const
{ {
meta_data->set_server_side_name(PbOperation_Name(operation)); meta_data->set_server_side_name(PbOperation_Name(operation));
meta_data->set_description(description); meta_data->set_description(description);

View File

@ -28,8 +28,10 @@ public:
RascsiResponse(DeviceFactory *device_factory, const RascsiImage *rascsi_image) RascsiResponse(DeviceFactory *device_factory, const RascsiImage *rascsi_image)
: device_factory(device_factory), rascsi_image(rascsi_image) {} : device_factory(device_factory), rascsi_image(rascsi_image) {}
~RascsiResponse() = default; ~RascsiResponse() = default;
RascsiResponse(RascsiResponse&) = delete;
RascsiResponse& operator=(const RascsiResponse&) = delete;
bool GetImageFile(PbImageFile *, const string&); bool GetImageFile(PbImageFile *, const string&) const;
PbImageFilesInfo *GetAvailableImages(PbResult&, const string&, const string&, int); PbImageFilesInfo *GetAvailableImages(PbResult&, const string&, const string&, int);
PbReservedIdsInfo *GetReservedIds(PbResult&, const unordered_set<int>&); PbReservedIdsInfo *GetReservedIds(PbResult&, const unordered_set<int>&);
void GetDevices(PbServerInfo&); void GetDevices(PbServerInfo&);
@ -55,7 +57,7 @@ private:
void GetDeviceTypeProperties(PbDeviceTypesInfo&, PbDeviceType); void GetDeviceTypeProperties(PbDeviceTypesInfo&, PbDeviceType);
void GetAvailableImages(PbImageFilesInfo&, string_view, const string&, const string&, const string&, int); void GetAvailableImages(PbImageFilesInfo&, string_view, const string&, const string&, const string&, int);
void GetAvailableImages(PbResult& result, PbServerInfo&, const string&, const string&, int); void GetAvailableImages(PbResult& result, PbServerInfo&, const string&, const string&, int);
void CreateOperation(PbOperationInfo *, PbOperationMetaData *, const PbOperation&, const string&); void CreateOperation(PbOperationInfo *, PbOperationMetaData *, const PbOperation&, const string&) const;
PbOperationParameter *AddOperationParameter(PbOperationMetaData *, const string&, const string&, PbOperationParameter *AddOperationParameter(PbOperationMetaData *, const string&, const string&,
const string& = "", bool = false); const string& = "", bool = false);
}; };

View File

@ -22,6 +22,8 @@ public:
RasctlCommands(const PbCommand&, const string&, int, const string&, const string&); RasctlCommands(const PbCommand&, const string&, int, const string&, const string&);
~RasctlCommands() = default; ~RasctlCommands() = default;
RasctlCommands(RasctlCommands&) = delete;
RasctlCommands& operator=(const RasctlCommands&) = delete;
void SendCommand(); void SendCommand();
void CommandDevicesInfo(); void CommandDevicesInfo();

View File

@ -19,6 +19,8 @@ public:
RasctlDisplay() = default; RasctlDisplay() = default;
~RasctlDisplay() = default; ~RasctlDisplay() = default;
RasctlDisplay(RasctlDisplay&) = delete;
RasctlDisplay& operator=(const RasctlDisplay&) = delete;
void DisplayDevices(const PbDevicesInfo&) const; void DisplayDevices(const PbDevicesInfo&) const;
void DisplayDeviceInfo(const PbDevice&) const; void DisplayDeviceInfo(const PbDevice&) const;

View File

@ -37,7 +37,7 @@ bool ras_util::GetAsInt(const string& value, int& result)
string ras_util::ListDevices(const list<PbDevice>& pb_devices) string ras_util::ListDevices(const list<PbDevice>& pb_devices)
{ {
if (pb_devices.empty()) { if (pb_devices.empty()) {
return "No images currently attached."; return "No devices currently attached.";
} }
ostringstream s; ostringstream s;

View File

@ -30,7 +30,7 @@ using namespace std;
// //
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
static volatile bool running; // Running flag static volatile bool running; // Running flag
GPIOBUS *bus; // GPIO Bus unique_ptr<GPIOBUS> bus; // GPIO Bus
DWORD buff_size = 1000000; DWORD buff_size = 1000000;
data_capture *data_buffer; data_capture *data_buffer;
@ -183,7 +183,7 @@ bool Init()
} }
// GPIO Initialization // GPIO Initialization
bus = new GPIOBUS(); bus = make_unique<GPIOBUS>();
if (!bus->Init()) if (!bus->Init())
{ {
LOGERROR("Unable to intiailize the GPIO bus. Exiting....") LOGERROR("Unable to intiailize the GPIO bus. Exiting....")
@ -217,7 +217,6 @@ void Cleanup()
{ {
// Cleanup the Bus // Cleanup the Bus
bus->Cleanup(); bus->Cleanup();
delete bus;
} }
} }

View File

@ -15,7 +15,7 @@ TEST(ControllerManagerTest, ControllerManager)
const int ID = 4; const int ID = 4;
const int LUN = 6; const int LUN = 6;
auto device = static_cast<PrimaryDevice *>(device_factory.CreateDevice(UNDEFINED, "services", ID)); auto device = device_factory.CreateDevice(UNDEFINED, "services", ID);
device->SetId(ID); device->SetId(ID);
device->SetLun(LUN); device->SetLun(LUN);
@ -27,7 +27,8 @@ TEST(ControllerManagerTest, ControllerManager)
EXPECT_EQ(device, controller_manager.GetDeviceByIdAndLun(ID, LUN)); EXPECT_EQ(device, controller_manager.GetDeviceByIdAndLun(ID, LUN));
EXPECT_EQ(nullptr, controller_manager.GetDeviceByIdAndLun(0, 0)); EXPECT_EQ(nullptr, controller_manager.GetDeviceByIdAndLun(0, 0));
controller_manager.DeleteAllControllersAndDevices(); controller_manager.DeleteAllControllers();
device_factory.DeleteAllDevices();
EXPECT_EQ(nullptr, controller_manager.FindController(ID)); EXPECT_EQ(nullptr, controller_manager.FindController(ID));
EXPECT_EQ(nullptr, controller_manager.GetDeviceByIdAndLun(ID, LUN)); EXPECT_EQ(nullptr, controller_manager.GetDeviceByIdAndLun(ID, LUN));
} }

View File

@ -36,11 +36,11 @@ TEST(DeviceFactoryTest, GetTypeForFile)
TEST(DeviceFactoryTest, LifeCycle) TEST(DeviceFactoryTest, LifeCycle)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "services", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "services", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCHS", device->GetType()); EXPECT_EQ("SCHS", device->GetType());
list<Device *> devices = device_factory.GetAllDevices(); list<PrimaryDevice *> devices = device_factory.GetAllDevices();
EXPECT_EQ(1, devices.size()); EXPECT_EQ(1, devices.size());
EXPECT_EQ(device, devices.front()); EXPECT_EQ(device, devices.front());
@ -98,13 +98,13 @@ TEST(DeviceFactoryTest, GetSectorSizes)
TEST(DeviceFactoryTest, UnknownDeviceType) TEST(DeviceFactoryTest, UnknownDeviceType)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "test", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "test", -1);
EXPECT_EQ(nullptr, device); EXPECT_EQ(nullptr, device);
} }
TEST(DeviceFactoryTest, SCHD_Device_Defaults) TEST(DeviceFactoryTest, SCHD_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "test.hda", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "test.hda", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCHD", device->GetType()); EXPECT_EQ("SCHD", device->GetType());
EXPECT_TRUE(device->SupportsFile()); EXPECT_TRUE(device->SupportsFile());
@ -144,7 +144,7 @@ TEST(DeviceFactoryTest, SCHD_Device_Defaults)
TEST(DeviceFactoryTest, SCRM_Device_Defaults) TEST(DeviceFactoryTest, SCRM_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "test.hdr", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "test.hdr", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCRM", device->GetType()); EXPECT_EQ("SCRM", device->GetType());
EXPECT_TRUE(device->SupportsFile()); EXPECT_TRUE(device->SupportsFile());
@ -169,7 +169,7 @@ TEST(DeviceFactoryTest, SCRM_Device_Defaults)
TEST(DeviceFactoryTest, SCMO_Device_Defaults) TEST(DeviceFactoryTest, SCMO_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "test.mos", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "test.mos", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCMO", device->GetType()); EXPECT_EQ("SCMO", device->GetType());
EXPECT_TRUE(device->SupportsFile()); EXPECT_TRUE(device->SupportsFile());
@ -194,7 +194,7 @@ TEST(DeviceFactoryTest, SCMO_Device_Defaults)
TEST(DeviceFactoryTest, SCCD_Device_Defaults) TEST(DeviceFactoryTest, SCCD_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "test.iso", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "test.iso", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCCD", device->GetType()); EXPECT_EQ("SCCD", device->GetType());
EXPECT_TRUE(device->SupportsFile()); EXPECT_TRUE(device->SupportsFile());
@ -219,7 +219,7 @@ TEST(DeviceFactoryTest, SCCD_Device_Defaults)
TEST(DeviceFactoryTest, SCBR_Device_Defaults) TEST(DeviceFactoryTest, SCBR_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "bridge", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "bridge", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCBR", device->GetType()); EXPECT_EQ("SCBR", device->GetType());
EXPECT_FALSE(device->SupportsFile()); EXPECT_FALSE(device->SupportsFile());
@ -244,7 +244,7 @@ TEST(DeviceFactoryTest, SCBR_Device_Defaults)
TEST(DeviceFactoryTest, SCDP_Device_Defaults) TEST(DeviceFactoryTest, SCDP_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "daynaport", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "daynaport", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCDP", device->GetType()); EXPECT_EQ("SCDP", device->GetType());
EXPECT_FALSE(device->SupportsFile()); EXPECT_FALSE(device->SupportsFile());
@ -268,7 +268,7 @@ TEST(DeviceFactoryTest, SCDP_Device_Defaults)
TEST(DeviceFactoryTest, SCHS_Device_Defaults) TEST(DeviceFactoryTest, SCHS_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "services", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "services", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCHS", device->GetType()); EXPECT_EQ("SCHS", device->GetType());
EXPECT_FALSE(device->SupportsFile()); EXPECT_FALSE(device->SupportsFile());
@ -293,7 +293,7 @@ TEST(DeviceFactoryTest, SCHS_Device_Defaults)
TEST(DeviceFactoryTest, SCLP_Device_Defaults) TEST(DeviceFactoryTest, SCLP_Device_Defaults)
{ {
Device *device = device_factory.CreateDevice(UNDEFINED, "printer", -1); PrimaryDevice *device = device_factory.CreateDevice(UNDEFINED, "printer", -1);
EXPECT_NE(nullptr, device); EXPECT_NE(nullptr, device);
EXPECT_EQ("SCLP", device->GetType()); EXPECT_EQ("SCLP", device->GetType());
EXPECT_FALSE(device->SupportsFile()); EXPECT_FALSE(device->SupportsFile());

View File

@ -154,26 +154,27 @@ TEST(PrimaryDeviceTest, ReportLuns)
EXPECT_CALL(controller, DataIn()).Times(1); EXPECT_CALL(controller, DataIn()).Times(1);
EXPECT_TRUE(device1.Dispatch()); EXPECT_TRUE(device1.Dispatch());
EXPECT_EQ(0x00, controller.ctrl.buffer[0]) << "Wrong data length"; const BYTE *buffer = controller.ctrl.buffer;
EXPECT_EQ(0x00, controller.ctrl.buffer[1]) << "Wrong data length"; EXPECT_EQ(0x00, buffer[0]) << "Wrong data length";
EXPECT_EQ(0x00, controller.ctrl.buffer[2]) << "Wrong data length"; EXPECT_EQ(0x00, buffer[1]) << "Wrong data length";
EXPECT_EQ(0x10, controller.ctrl.buffer[3]) << "Wrong data length"; EXPECT_EQ(0x00, buffer[2]) << "Wrong data length";
EXPECT_EQ(0x00, controller.ctrl.buffer[8]) << "Wrong LUN1 number"; EXPECT_EQ(0x10, buffer[3]) << "Wrong data length";
EXPECT_EQ(0x00, controller.ctrl.buffer[9]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[8]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[10]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[9]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[11]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[10]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[12]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[11]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[13]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[12]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[14]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[13]) << "Wrong LUN1 number";
EXPECT_EQ(LUN1, controller.ctrl.buffer[15]) << "Wrong LUN1 number"; EXPECT_EQ(0x00, buffer[14]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[16]) << "Wrong LUN2 number"; EXPECT_EQ(LUN1, buffer[15]) << "Wrong LUN1 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[17]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[16]) << "Wrong LUN2 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[18]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[17]) << "Wrong LUN2 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[19]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[18]) << "Wrong LUN2 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[20]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[19]) << "Wrong LUN2 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[21]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[20]) << "Wrong LUN2 number";
EXPECT_EQ(0x00, controller.ctrl.buffer[22]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[21]) << "Wrong LUN2 number";
EXPECT_EQ(LUN2, controller.ctrl.buffer[23]) << "Wrong LUN2 number"; EXPECT_EQ(0x00, buffer[22]) << "Wrong LUN2 number";
EXPECT_EQ(LUN2, buffer[23]) << "Wrong LUN2 number";
controller.ctrl.cmd[2] = 0x01; controller.ctrl.cmd[2] = 0x01;
EXPECT_THROW(device1.Dispatch(), scsi_error_exception) << "Only SELECT REPORT mode 0 is supported"; EXPECT_THROW(device1.Dispatch(), scsi_error_exception) << "Only SELECT REPORT mode 0 is supported";

View File

@ -12,8 +12,7 @@
TEST(ScsiControllerTest, ScsiController) TEST(ScsiControllerTest, ScsiController)
{ {
MockBus bus; MockScsiController controller(nullptr, 0);
MockScsiController controller(&bus, 0);
EXPECT_EQ(32, controller.GetMaxLuns()); EXPECT_EQ(32, controller.GetMaxLuns());

View File

@ -25,45 +25,6 @@
extern DeviceFactory& device_factory; extern DeviceFactory& device_factory;
extern ControllerManager& controller_manager; extern ControllerManager& controller_manager;
class MockBus : public BUS
{
public:
MOCK_METHOD(bool, Init, (mode_e), (override));
MOCK_METHOD(void, Reset, (), (override));
MOCK_METHOD(void, Cleanup, (), (override));
MOCK_METHOD(bool, GetBSY, (), (const override));
MOCK_METHOD(void, SetBSY, (bool), (override));
MOCK_METHOD(bool, GetSEL, (), (const override));
MOCK_METHOD(void, SetSEL, (bool), (override));
MOCK_METHOD(bool, GetATN, (), (const override));
MOCK_METHOD(void, SetATN, (bool), (override));
MOCK_METHOD(bool, GetACK, (), (const override));
MOCK_METHOD(void, SetACK, (bool), (override));
MOCK_METHOD(bool, GetRST, (), (const override));
MOCK_METHOD(void, SetRST, (bool), (override));
MOCK_METHOD(bool, GetMSG, (), (const override));
MOCK_METHOD(void, SetMSG, (bool), (override));
MOCK_METHOD(bool, GetCD, (), (const override));
MOCK_METHOD(void, SetCD, (bool), (override));
MOCK_METHOD(bool, GetIO, (), (override));
MOCK_METHOD(void, SetIO, (bool), (override));
MOCK_METHOD(bool, GetREQ, (), (const override));
MOCK_METHOD(void, SetREQ, (bool), (override));
MOCK_METHOD(BYTE, GetDAT, (), (override));
MOCK_METHOD(void, SetDAT, (BYTE), (override));
MOCK_METHOD(bool, GetDP, (), (const, override));
MOCK_METHOD(DWORD, Acquire,(), (override));
MOCK_METHOD(int, CommandHandShake, (BYTE *), (override));
MOCK_METHOD(int, ReceiveHandShake, (BYTE *, int), (override));
MOCK_METHOD(int, SendHandShake, (BYTE *, int, int), (override));
MOCK_METHOD(bool, GetSignal, (int), (const, override));
MOCK_METHOD(void, SetSignal, (int, bool), (override));
MockBus() = default;
~MockBus() final = default;
};
class MockAbstractController : public AbstractController class MockAbstractController : public AbstractController
{ {
public: public:
@ -180,7 +141,7 @@ public:
// Make protected methods visible for testing // Make protected methods visible for testing
// TODO Why does FRIEND_TEST not work for this method? // TODO Why does FRIEND_TEST not work for this method?
int AddModePages(const DWORD *cdb, BYTE *buf, int max_length) { int AddModePages(const DWORD *cdb, BYTE *buf, int max_length) const {
return ModePageDevice::AddModePages(cdb, buf, max_length); return ModePageDevice::AddModePages(cdb, buf, max_length);
} }
}; };