// // Acorn.hpp // Clock Signal // // Created by Thomas Harte on 06/11/2016. // Copyright 2016 Thomas Harte. All rights reserved. // #pragma once #include "TapeParser.hpp" #include "../../../Numeric/CRC.hpp" #include "../../Disk/DPLL/DigitalPhaseLockedLoop.hpp" namespace Storage::Tape::Acorn { class Shifter { public: Shifter(); void process_pulse(const Storage::Tape::Tape::Pulse &); struct Delegate { virtual void acorn_shifter_output_bit(int value) = 0; }; void set_delegate(Delegate *delegate) { delegate_ = delegate; } void digital_phase_locked_loop_output_bit(int value); private: Storage::DigitalPhaseLockedLoop pll_; bool was_high_; unsigned int input_pattern_; Delegate *delegate_; }; enum class SymbolType { One, Zero }; class Parser: public Storage::Tape::Parser, public Shifter::Delegate { public: Parser(); int get_next_bit(const std::shared_ptr &); int get_next_byte(const std::shared_ptr &); unsigned int get_next_short(const std::shared_ptr &); unsigned int get_next_word(const std::shared_ptr &); void reset_crc(); uint16_t get_crc() const; private: void acorn_shifter_output_bit(int value) override; void process_pulse(const Storage::Tape::Tape::Pulse &) override; bool did_update_shifter(int new_value, int length); CRC::Generator crc_; Shifter shifter_; }; }