1
0
mirror of https://github.com/TomHarte/CLK.git synced 2026-04-26 19:17:52 +00:00

Factors out boilerplate around full-device sector images.

This commit is contained in:
Thomas Harte
2021-05-01 21:10:46 -04:00
parent c906dc3c0a
commit 20c814a4dd
4 changed files with 64 additions and 38 deletions
+7 -26
View File
@@ -10,32 +10,13 @@
using namespace Storage::MassStorage;
DAT::DAT(const std::string &file_name) : file_(file_name) {
// Is the file a multiple of 256 bytes in size?
const auto file_size = file_.stats().st_size;
if(file_size & 255) throw std::exception();
// Does it contain the 'Hugo' signature?
file_.seek(0x201, SEEK_SET);
if(!file_.check_signature("Hugo")) {
DAT::DAT(const std::string &file_name) : RawSectorDump(file_name) {
// Does the third sector contain the 'Hugo' signature?
const auto sector3 = get_block(2);
if(sector3.size() != 256) {
throw std::exception();
}
if(sector3[1] != 'H' || sector3[2] != 'u' || sector3[3] != 'g' || sector3[4] != 'o') {
throw std::exception();
}
}
size_t DAT::get_block_size() {
return 256;
}
size_t DAT::get_number_of_blocks() {
return size_t(file_.stats().st_size) / 256;
}
std::vector<uint8_t> DAT::get_block(size_t address) {
file_.seek(long(address * 256), SEEK_SET);
return file_.read(256);
}
void DAT::set_block(size_t address, const std::vector<uint8_t> &contents) {
file_.seek(long(address * 256), SEEK_SET);
file_.write(contents);
}
+2 -12
View File
@@ -9,8 +9,7 @@
#ifndef MassStorage_DAT_hpp
#define MassStorage_DAT_hpp
#include "../MassStorageDevice.hpp"
#include "../../FileHolder.hpp"
#include "RawSectorDump.hpp"
namespace Storage {
namespace MassStorage {
@@ -20,18 +19,9 @@ namespace MassStorage {
sector dump of an ADFS volume. It will be validated for an ADFS catalogue and communicate
in 256-byte blocks.
*/
class DAT: public MassStorageDevice {
class DAT: public RawSectorDump<256> {
public:
DAT(const std::string &file_name);
private:
FileHolder file_;
/* MassStorageDevices overrides. */
size_t get_block_size() final;
size_t get_number_of_blocks() final;
std::vector<uint8_t> get_block(size_t address) final;
void set_block(size_t address, const std::vector<uint8_t> &) final;
};
}
@@ -0,0 +1,53 @@
//
// RawSectorDump.hpp
// Clock Signal
//
// Created by Thomas Harte on 01/05/2021.
// Copyright © 2021 Thomas Harte. All rights reserved.
//
#ifndef RawSectorDump_h
#define RawSectorDump_h
#include "../MassStorageDevice.hpp"
#include "../../FileHolder.hpp"
namespace Storage {
namespace MassStorage {
template <size_t sector_size> class RawSectorDump: public MassStorageDevice {
public:
RawSectorDump(const std::string &file_name) : file_(file_name) {
// Is the file a multiple of sector_size bytes in size?
const auto file_size = size_t(file_.stats().st_size);
if(file_size % sector_size) throw std::exception();
}
/* MassStorageDevices overrides. */
size_t get_block_size() final {
return sector_size;
}
size_t get_number_of_blocks() final {
return size_t(file_.stats().st_size) / sector_size;
}
std::vector<uint8_t> get_block(size_t address) final {
file_.seek(long(address * sector_size), SEEK_SET);
return file_.read(sector_size);
}
void set_block(size_t address, const std::vector<uint8_t> &contents) final {
assert(contents.size() == sector_size);
file_.seek(long(address * sector_size), SEEK_SET);
file_.write(contents);
}
private:
FileHolder file_;
};
}
}
#endif /* RawSectorDump_h */