From 0490a4705893a62e32f34b08930996b6b273d820 Mon Sep 17 00:00:00 2001 From: Thomas Harte Date: Mon, 26 Dec 2016 14:24:33 -0500 Subject: [PATCH] Worked on the all-around framework for decoding sectors back from tracks when closing down a file. Hit the wall that the parser is more observant of CRCs than the WD. No, really. So I guess I have to stop avoiding that whole issue. --- Components/1770/1770.cpp | 2 +- Storage/Disk/Disk.hpp | 1 + Storage/Disk/DiskController.hpp | 2 +- Storage/Disk/Drive.cpp | 13 +++++++++++-- Storage/Disk/Drive.hpp | 10 ++++++++-- Storage/Disk/Encodings/MFM.cpp | 15 +++++++++++++-- Storage/Disk/Encodings/MFM.hpp | 3 +++ Storage/Disk/Formats/SSD.cpp | 23 +++++++++++++++++++++++ Storage/Disk/Formats/SSD.hpp | 1 + 9 files changed, 62 insertions(+), 8 deletions(-) diff --git a/Components/1770/1770.cpp b/Components/1770/1770.cpp index e320d01f4..ee0763b40 100644 --- a/Components/1770/1770.cpp +++ b/Components/1770/1770.cpp @@ -535,7 +535,7 @@ void WD1770::posit_event(Event new_event_type) } if(distance_into_section_ == 7) { - printf("Considering %d/%d at %0.4f\n", header_[0], header_[2], get_time_into_track().get_float()); + printf("Considering %d/%d\n", header_[0], header_[2]); is_reading_data_ = false; if(header_[0] == track_ && header_[2] == sector_ && (has_motor_on_line() || !(command_&0x02) || ((command_&0x08) >> 3) == header_[1])) diff --git a/Storage/Disk/Disk.hpp b/Storage/Disk/Disk.hpp index 514bc0c61..7b435d838 100644 --- a/Storage/Disk/Disk.hpp +++ b/Storage/Disk/Disk.hpp @@ -66,6 +66,7 @@ class Track { */ class Disk { public: + virtual ~Disk() {} /*! @returns the number of discrete positions that this disk uses to model its complete surface area. diff --git a/Storage/Disk/DiskController.hpp b/Storage/Disk/DiskController.hpp index 19e9e8755..a39b74b48 100644 --- a/Storage/Disk/DiskController.hpp +++ b/Storage/Disk/DiskController.hpp @@ -110,7 +110,6 @@ class Controller: public DigitalPhaseLockedLoop::Delegate, public TimedEventLoop void step(int direction); virtual bool get_drive_is_ready(); bool get_drive_is_read_only(); - Time get_time_into_track(); private: Time bit_length_; @@ -136,6 +135,7 @@ class Controller: public DigitalPhaseLockedLoop::Delegate, public TimedEventLoop Time cycles_per_bit_; void setup_track(); + Time get_time_into_track(); }; } diff --git a/Storage/Disk/Drive.cpp b/Storage/Disk/Drive.cpp index 0b9fb34cb..3b58d8fbb 100644 --- a/Storage/Disk/Drive.cpp +++ b/Storage/Disk/Drive.cpp @@ -14,14 +14,21 @@ using namespace Storage::Disk; Drive::Drive() : head_position_(0), head_(0) {} -void Drive::set_disk(std::shared_ptr disk) +void Drive::set_disk(const std::shared_ptr &disk) { disk_ = disk; + track_ = nullptr; +} + +void Drive::set_disk_with_track(const std::shared_ptr &track) +{ + disk_ = nullptr; + track_ = track; } bool Drive::has_disk() { - return (bool)disk_; + return (bool)disk_ || (bool)track_; } bool Drive::get_is_track_zero() @@ -42,12 +49,14 @@ void Drive::set_head(unsigned int head) bool Drive::get_is_read_only() { if(disk_) return disk_->get_is_read_only(); + if(track_) return true; return false; } std::shared_ptr Drive::get_track() { if(disk_) return disk_->get_track_at_position(head_, (unsigned int)head_position_); + if(track_) return track_; return nullptr; } diff --git a/Storage/Disk/Drive.hpp b/Storage/Disk/Drive.hpp index 1506e8a2c..82e34fcd6 100644 --- a/Storage/Disk/Drive.hpp +++ b/Storage/Disk/Drive.hpp @@ -20,9 +20,14 @@ class Drive { Drive(); /*! - Inserts @c disk into the drive. + Replaces whatever is in the drive with @c disk. */ - void set_disk(std::shared_ptr disk); + void set_disk(const std::shared_ptr &disk); + + /*! + Replaces whatever is in the drive with a disk that contains endless copies of @c track. + */ + void set_disk_with_track(const std::shared_ptr &track); /*! @returns @c true if a disk is currently inserted; @c false otherwise. @@ -61,6 +66,7 @@ class Drive { void set_track(const std::shared_ptr &track); private: + std::shared_ptr track_; std::shared_ptr disk_; int head_position_; unsigned int head_; diff --git a/Storage/Disk/Encodings/MFM.cpp b/Storage/Disk/Encodings/MFM.cpp index 2af4e5bfb..69767ad20 100644 --- a/Storage/Disk/Encodings/MFM.cpp +++ b/Storage/Disk/Encodings/MFM.cpp @@ -214,7 +214,7 @@ std::unique_ptr Storage::Encodings::MFM::GetFMEncoder(std::vector &disk) : +Parser::Parser(bool is_mfm) : Storage::Disk::Controller(4000000, 1, 300), crc_generator_(0x1021, 0xffff), shift_register_(0), track_(0), is_mfm_(is_mfm) @@ -225,11 +225,22 @@ Parser::Parser(bool is_mfm, const std::shared_ptr &disk) : set_expected_bit_length(bit_length); drive.reset(new Storage::Disk::Drive); - drive->set_disk(disk); set_drive(drive); set_motor_on(true); } +Parser::Parser(bool is_mfm, const std::shared_ptr &disk) : + Parser(is_mfm) +{ + drive->set_disk(disk); +} + +Parser::Parser(bool is_mfm, const std::shared_ptr &track) : + Parser(is_mfm) +{ + drive->set_disk_with_track(track); +} + std::shared_ptr Parser::get_sector(uint8_t track, uint8_t sector) { int difference = (int)track - (int)track_; diff --git a/Storage/Disk/Encodings/MFM.hpp b/Storage/Disk/Encodings/MFM.hpp index 6fdccdd96..5f26ec7c0 100644 --- a/Storage/Disk/Encodings/MFM.hpp +++ b/Storage/Disk/Encodings/MFM.hpp @@ -61,6 +61,7 @@ std::unique_ptr GetFMEncoder(std::vector &target); class Parser: public Storage::Disk::Controller { public: Parser(bool is_mfm, const std::shared_ptr &disk); + Parser(bool is_mfm, const std::shared_ptr &track); /*! Attempts to read the sector located at @c track and @c sector. @@ -70,6 +71,8 @@ class Parser: public Storage::Disk::Controller { std::shared_ptr get_sector(uint8_t track, uint8_t sector); private: + Parser(bool is_mfm); + std::shared_ptr drive; unsigned int shift_register_; int index_count_; diff --git a/Storage/Disk/Formats/SSD.cpp b/Storage/Disk/Formats/SSD.cpp index efb10b73b..4f6863214 100644 --- a/Storage/Disk/Formats/SSD.cpp +++ b/Storage/Disk/Formats/SSD.cpp @@ -30,6 +30,29 @@ SSD::SSD(const char *file_name) : else if(track_count_ < 80) track_count_ = 80; } +SSD::~SSD() +{ + if(get_is_modified()) + { + for(unsigned int head = 0; head < head_count_; head++) + { + for(unsigned int track = 0; track < track_count_; track++) + { + std::shared_ptr modified_track = get_modified_track_at_position(head, track); + if(modified_track) + { + Storage::Encodings::MFM::Parser parser(false, modified_track); + for(unsigned int c = 0; c < 10; c++) + { + std::shared_ptr sector = parser.get_sector((uint8_t)track, (uint8_t)c); + printf("Sector %d: %p\n", c, sector.get()); + } + } + } + } + } +} + unsigned int SSD::get_head_position_count() { return track_count_; diff --git a/Storage/Disk/Formats/SSD.hpp b/Storage/Disk/Formats/SSD.hpp index 90febd2cb..b7c21ccb3 100644 --- a/Storage/Disk/Formats/SSD.hpp +++ b/Storage/Disk/Formats/SSD.hpp @@ -27,6 +27,7 @@ class SSD: public Disk, public Storage::FileHolder { @throws ErrorNotSSD if the file doesn't appear to contain a .SSD format image. */ SSD(const char *file_name); + ~SSD(); enum { ErrorNotSSD,