Compare commits

...

8 Commits

Author SHA1 Message Date
35e5c7c90f Merge pull request #12 from lioncash/const
General: Make member functions const where applicable
2019-09-03 00:37:32 -07:00
d48ba9523f Merge pull request #13 from lioncash/explicit
General: Use explicit where applicable
2019-09-03 00:37:23 -07:00
f74f1a3a6c Merge pull request #11 from lioncash/array
General: Use std::array for constructors where applicable
2019-09-03 00:36:32 -07:00
Lioncash
9d3a436e70 Card: Use UINT32_MAX for FileHandle's default initializer
Avoids a sign conversion
2019-09-02 08:45:07 -04:00
Lioncash
e96db1e032 General: Use explicit where applicable
Makes conversions explicit in order to prevent error-prone implicit
conversions.
2019-09-02 08:42:37 -04:00
Lioncash
ed2a6b3ce8 Card: Make querying functions const member functions where applicable
These don't modify member state, so they can be made const .
2019-09-02 08:26:43 -04:00
Lioncash
66ce5ed823 Directory: Make indexForFile() a const member function
This doesn't modify instance state, so it can be turned into a const
member function.
2019-09-02 08:20:50 -04:00
Lioncash
69d24d1027 General: Use std::array for constructors where applicable
Same behavior, but ensures input absolutely satisfies the total amount
of data that needs to be copied.
2019-09-02 08:14:44 -04:00
7 changed files with 55 additions and 38 deletions

View File

@@ -28,7 +28,7 @@ class AsyncIO {
public: public:
AsyncIO() = default; AsyncIO() = default;
AsyncIO(SystemStringView filename, bool truncate = false); explicit AsyncIO(SystemStringView filename, bool truncate = false);
~AsyncIO(); ~AsyncIO();
AsyncIO(AsyncIO&& other); AsyncIO(AsyncIO&& other);
AsyncIO& operator=(AsyncIO&& other); AsyncIO& operator=(AsyncIO&& other);
@@ -41,9 +41,9 @@ public:
ECardResult pollStatus() const; ECardResult pollStatus() const;
void waitForCompletion() const; void waitForCompletion() const;
#ifndef _WIN32 #ifndef _WIN32
operator bool() const { return m_fd != -1; } explicit operator bool() const { return m_fd != -1; }
#else #else
operator bool() const { return m_fh != INVALID_HANDLE_VALUE; } explicit operator bool() const { return m_fh != INVALID_HANDLE_VALUE; }
#endif #endif
}; };

View File

@@ -17,14 +17,14 @@ namespace kabufuda {
class FileHandle { class FileHandle {
friend class Card; friend class Card;
uint32_t idx = -1; uint32_t idx = UINT32_MAX;
int32_t offset = 0; int32_t offset = 0;
FileHandle(uint32_t idx) : idx(idx) {} explicit FileHandle(uint32_t idx) : idx(idx) {}
public: public:
FileHandle() = default; FileHandle() = default;
uint32_t getFileNo() const { return idx; } uint32_t getFileNo() const { return idx; }
operator bool() const { return getFileNo() != UINT32_MAX; } explicit operator bool() const { return getFileNo() != UINT32_MAX; }
}; };
struct ProbeResults { struct ProbeResults {
@@ -136,7 +136,7 @@ public:
* @param game The game code. * @param game The game code.
* @param maker The maker code. * @param maker The maker code.
*/ */
Card(const char* game = nullptr, const char* maker = nullptr); explicit Card(const char* game = nullptr, const char* maker = nullptr);
~Card(); ~Card();
/** /**
@@ -204,7 +204,7 @@ public:
* *
* @return Gets the name of the given file. * @return Gets the name of the given file.
*/ */
const char* getFilename(const FileHandle& fh); const char* getFilename(const FileHandle& fh) const;
/** /**
* @brief deleteFile * @brief deleteFile
@@ -269,7 +269,7 @@ public:
* *
* @return The offset or -1 if an invalid handle is passed. * @return The offset or -1 if an invalid handle is passed.
*/ */
int32_t tell(const FileHandle& fh); int32_t tell(const FileHandle& fh) const;
/** /**
* @brief setPublic * @brief setPublic
@@ -425,7 +425,7 @@ public:
* @param checksum The checksum of the system header. * @param checksum The checksum of the system header.
* @param inverse The inverse checksum of the system header. * @param inverse The inverse checksum of the system header.
*/ */
void getChecksum(uint16_t& checksum, uint16_t& inverse); void getChecksum(uint16_t& checksum, uint16_t& inverse) const;
/** /**
* @brief Retrieves the available storage and directory space. * @brief Retrieves the available storage and directory space.
@@ -433,7 +433,7 @@ public:
* @param bytesNotUsed Number of free bytes out. * @param bytesNotUsed Number of free bytes out.
* @param filesNotUsed Number of free files out. * @param filesNotUsed Number of free files out.
*/ */
void getFreeBlocks(int32_t& bytesNotUsed, int32_t& filesNotUsed); void getFreeBlocks(int32_t& bytesNotUsed, int32_t& filesNotUsed) const;
/** /**
* @brief Formats the memory card and assigns a new serial. * @brief Formats the memory card and assigns a new serial.
@@ -489,6 +489,6 @@ public:
/** /**
* @return Whether or not the card is within a ready state. * @return Whether or not the card is within a ready state.
*/ */
operator bool() const { return getError() == ECardResult::READY; } explicit operator bool() const { return getError() == ECardResult::READY; }
}; };
} // namespace kabufuda } // namespace kabufuda

View File

@@ -15,9 +15,12 @@ class Directory {
uint16_t m_checksum; uint16_t m_checksum;
uint16_t m_checksumInv; uint16_t m_checksumInv;
}; };
using RawData = std::array<uint8_t, BlockSize>;
union { union {
Data data; Data data;
std::array<uint8_t, BlockSize> raw; RawData raw;
}; };
#pragma pack(pop) #pragma pack(pop)
@@ -27,7 +30,7 @@ class Directory {
public: public:
Directory(); Directory();
Directory(uint8_t data[BlockSize]); explicit Directory(const RawData& rawData);
~Directory() = default; ~Directory() = default;
bool hasFreeFile() const; bool hasFreeFile() const;
@@ -36,6 +39,6 @@ public:
File* getFirstNonFreeFile(uint32_t start, const char* game, const char* maker); File* getFirstNonFreeFile(uint32_t start, const char* game, const char* maker);
File* getFile(const char* game, const char* maker, const char* filename); File* getFile(const char* game, const char* maker, const char* filename);
File* getFile(uint32_t idx); File* getFile(uint32_t idx);
int32_t indexForFile(File* f); int32_t indexForFile(const File* f) const;
}; };
} // namespace kabufuda } // namespace kabufuda

View File

@@ -10,6 +10,8 @@ class File {
friend class Directory; friend class Directory;
friend class Card; friend class Card;
#pragma pack(push, 4) #pragma pack(push, 4)
using RawData = std::array<uint8_t, 0x40>;
union { union {
struct { struct {
std::array<uint8_t, 4> m_game; std::array<uint8_t, 4> m_game;
@@ -28,7 +30,7 @@ class File {
uint16_t m_reserved2; uint16_t m_reserved2;
uint32_t m_commentAddr; uint32_t m_commentAddr;
}; };
std::array<uint8_t, 0x40> raw; RawData raw;
}; };
#pragma pack(pop) #pragma pack(pop)
@@ -36,8 +38,8 @@ class File {
public: public:
File(); File();
File(char data[0x40]); explicit File(const RawData& rawData);
File(const char* filename); explicit File(const char* filename);
~File() = default; ~File() = default;
}; };
} // namespace kabufuda } // namespace kabufuda

View File

@@ -118,19 +118,23 @@ Card::Card(const char* game, const char* maker) {
Card::~Card() { close(); } Card::~Card() { close(); }
ECardResult Card::openFile(const char* filename, FileHandle& handleOut) { ECardResult Card::openFile(const char* filename, FileHandle& handleOut) {
ECardResult openRes = _pumpOpen(); const ECardResult openRes = _pumpOpen();
if (openRes != ECardResult::READY) if (openRes != ECardResult::READY) {
return openRes; return openRes;
}
handleOut = {}; handleOut = {};
File* f = m_dirs[m_currentDir].getFile(m_game, m_maker, filename); const File* const f = m_dirs[m_currentDir].getFile(m_game, m_maker, filename);
if (!f || f->m_game[0] == 0xFF) if (!f || f->m_game[0] == 0xFF) {
return ECardResult::NOFILE; return ECardResult::NOFILE;
int32_t idx = m_dirs[m_currentDir].indexForFile(f); }
const int32_t idx = m_dirs[m_currentDir].indexForFile(f);
if (idx != -1) { if (idx != -1) {
handleOut = FileHandle(idx); handleOut = FileHandle(idx);
return ECardResult::READY; return ECardResult::READY;
} }
return ECardResult::FATAL_ERROR; return ECardResult::FATAL_ERROR;
} }
@@ -219,11 +223,13 @@ ECardResult Card::closeFile(FileHandle& fh) {
} }
FileHandle Card::firstFile() { FileHandle Card::firstFile() {
File* f = m_dirs[m_currentDir].getFirstNonFreeFile(0, m_game, m_maker); const File* const f = m_dirs[m_currentDir].getFirstNonFreeFile(0, m_game, m_maker);
if (f)
return FileHandle(m_dirs[m_currentDir].indexForFile(f));
if (f == nullptr) {
return {}; return {};
}
return FileHandle(m_dirs[m_currentDir].indexForFile(f));
} }
FileHandle Card::nextFile(const FileHandle& cur) { FileHandle Card::nextFile(const FileHandle& cur) {
@@ -231,16 +237,22 @@ FileHandle Card::nextFile(const FileHandle& cur) {
NullFileAccess(); NullFileAccess();
return {}; return {};
} }
File* next = m_dirs[m_currentDir].getFirstNonFreeFile(cur.idx + 1, m_game, m_maker);
if (!next) const File* const next = m_dirs[m_currentDir].getFirstNonFreeFile(cur.idx + 1, m_game, m_maker);
if (next == nullptr) {
return {}; return {};
}
return FileHandle(m_dirs[m_currentDir].indexForFile(next)); return FileHandle(m_dirs[m_currentDir].indexForFile(next));
} }
const char* Card::getFilename(const FileHandle& fh) { const char* Card::getFilename(const FileHandle& fh) const {
File* f = _fileFromHandle(fh); const File* const f = _fileFromHandle(fh);
if (!f)
if (f == nullptr) {
return nullptr; return nullptr;
}
return f->m_filename; return f->m_filename;
} }
@@ -445,7 +457,7 @@ void Card::seek(FileHandle& fh, int32_t pos, SeekOrigin whence) {
} }
} }
int32_t Card::tell(const FileHandle& fh) { return fh.offset; } int32_t Card::tell(const FileHandle& fh) const { return fh.offset; }
void Card::setPublic(const FileHandle& fh, bool pub) { void Card::setPublic(const FileHandle& fh, bool pub) {
File* file = _fileFromHandle(fh); File* file = _fileFromHandle(fh);
@@ -746,12 +758,12 @@ void Card::getSerial(uint64_t& serial) {
m_ch._swapEndian(); m_ch._swapEndian();
} }
void Card::getChecksum(uint16_t& checksum, uint16_t& inverse) { void Card::getChecksum(uint16_t& checksum, uint16_t& inverse) const {
checksum = m_ch.m_checksum; checksum = m_ch.m_checksum;
inverse = m_ch.m_checksumInv; inverse = m_ch.m_checksumInv;
} }
void Card::getFreeBlocks(int32_t& bytesNotUsed, int32_t& filesNotUsed) { void Card::getFreeBlocks(int32_t& bytesNotUsed, int32_t& filesNotUsed) const {
bytesNotUsed = m_bats[m_currentBat].numFreeBlocks() * 0x2000; bytesNotUsed = m_bats[m_currentBat].numFreeBlocks() * 0x2000;
filesNotUsed = m_dirs[m_currentDir].numFreeFiles(); filesNotUsed = m_dirs[m_currentDir].numFreeFiles();
} }

View File

@@ -35,7 +35,7 @@ Directory::Directory() {
updateChecksum(); updateChecksum();
} }
Directory::Directory(uint8_t data[]) { std::memcpy(raw.data(), data, BlockSize); } Directory::Directory(const RawData& rawData) : raw{rawData} {}
bool Directory::hasFreeFile() const { bool Directory::hasFreeFile() const {
return std::any_of(data.m_files.cbegin(), data.m_files.cend(), return std::any_of(data.m_files.cbegin(), data.m_files.cend(),
@@ -125,7 +125,7 @@ File* Directory::getFile(uint32_t idx) {
return &data.m_files[idx]; return &data.m_files[idx];
} }
int32_t Directory::indexForFile(File* f) { int32_t Directory::indexForFile(const File* f) const {
if (f == nullptr) { if (f == nullptr) {
return -1; return -1;
} }

View File

@@ -8,7 +8,7 @@
namespace kabufuda { namespace kabufuda {
File::File() { raw.fill(0xFF); } File::File() { raw.fill(0xFF); }
File::File(char data[]) { std::memcpy(raw.data(), data, raw.size()); } File::File(const RawData& rawData) : raw{rawData} {}
File::File(const char* filename) { File::File(const char* filename) {
raw.fill(0); raw.fill(0);