1
0
mirror of https://github.com/TomHarte/CLK.git synced 2024-11-01 10:05:55 +00:00

Gave tapes their own namespace.

This commit is contained in:
Thomas Harte 2016-08-27 17:09:45 -04:00
parent 8c333059a8
commit c0402d0c2b
16 changed files with 60 additions and 48 deletions

View File

@ -262,14 +262,14 @@ void Machine::set_prg(const char *file_name, size_t length, const uint8_t *data)
} }
else else
{ {
set_tape(std::shared_ptr<Storage::Tape>(new Storage::TapePRG(file_name))); set_tape(std::shared_ptr<Storage::Tape::Tape>(new Storage::Tape::PRG(file_name)));
} }
} }
} }
#pragma mar - Tape #pragma mar - Tape
void Machine::set_tape(std::shared_ptr<Storage::Tape> tape) void Machine::set_tape(std::shared_ptr<Storage::Tape::Tape> tape)
{ {
_tape.set_tape(tape); _tape.set_tape(tape);
if(_should_automatically_load_media) set_typer_for_string("LOAD\nRUN\n"); if(_should_automatically_load_media) set_typer_for_string("LOAD\nRUN\n");
@ -422,9 +422,9 @@ Tape::Tape() : TapePlayer(1022727) {}
void Tape::set_motor_control(bool enabled) {} void Tape::set_motor_control(bool enabled) {}
void Tape::set_tape_output(bool set) {} void Tape::set_tape_output(bool set) {}
void Tape::process_input_pulse(Storage::Tape::Pulse pulse) void Tape::process_input_pulse(Storage::Tape::PRG::Pulse pulse)
{ {
bool new_input_level = pulse.type == Storage::Tape::Pulse::Low; bool new_input_level = pulse.type == Storage::Tape::PRG::Pulse::Low;
if(_input_level != new_input_level) if(_input_level != new_input_level)
{ {
_input_level = new_input_level; _input_level = new_input_level;

View File

@ -213,7 +213,7 @@ class SerialPort : public ::Commodore::Serial::Port {
std::weak_ptr<UserPortVIA> _userPortVIA; std::weak_ptr<UserPortVIA> _userPortVIA;
}; };
class Tape: public Storage::TapePlayer { class Tape: public Storage::Tape::TapePlayer {
public: public:
Tape(); Tape();
@ -232,7 +232,7 @@ class Tape: public Storage::TapePlayer {
private: private:
Delegate *_delegate; Delegate *_delegate;
virtual void process_input_pulse(Storage::Tape::Pulse pulse); virtual void process_input_pulse(Storage::Tape::Tape::Pulse pulse);
bool _input_level; bool _input_level;
}; };
@ -261,7 +261,7 @@ class Machine:
void set_rom(ROMSlot slot, size_t length, const uint8_t *data); void set_rom(ROMSlot slot, size_t length, const uint8_t *data);
void set_prg(const char *file_name, size_t length, const uint8_t *data); void set_prg(const char *file_name, size_t length, const uint8_t *data);
void set_tape(std::shared_ptr<Storage::Tape> tape); void set_tape(std::shared_ptr<Storage::Tape::Tape> tape);
void set_disk(std::shared_ptr<Storage::Disk> disk); void set_disk(std::shared_ptr<Storage::Disk> disk);
void set_key_state(Key key, bool isPressed) { _keyboardVIA->set_key_state(key, isPressed); } void set_key_state(Key key, bool isPressed) { _keyboardVIA->set_key_state(key, isPressed); }

View File

@ -458,7 +458,7 @@ void Machine::synchronise()
update_audio(); update_audio();
} }
void Machine::set_tape(std::shared_ptr<Storage::Tape> tape) void Machine::set_tape(std::shared_ptr<Storage::Tape::Tape> tape)
{ {
_tape.set_tape(tape); _tape.set_tape(tape);
} }
@ -971,14 +971,14 @@ inline uint8_t Tape::get_data_register()
return (uint8_t)(_data_register >> 2); return (uint8_t)(_data_register >> 2);
} }
inline void Tape::process_input_pulse(Storage::Tape::Pulse pulse) inline void Tape::process_input_pulse(Storage::Tape::Tape::Pulse pulse)
{ {
_crossings[0] = _crossings[1]; _crossings[0] = _crossings[1];
_crossings[1] = _crossings[2]; _crossings[1] = _crossings[2];
_crossings[2] = _crossings[3]; _crossings[2] = _crossings[3];
_crossings[3] = Tape::Unrecognised; _crossings[3] = Tape::Unrecognised;
if(pulse.type != Storage::Tape::Pulse::Zero) if(pulse.type != Storage::Tape::Tape::Pulse::Zero)
{ {
float pulse_length = (float)pulse.length.length / (float)pulse.length.clock_rate; float pulse_length = (float)pulse.length.length / (float)pulse.length.clock_rate;
if(pulse_length >= 0.35 / 2400.0 && pulse_length < 0.7 / 2400.0) _crossings[3] = Tape::Short; if(pulse_length >= 0.35 / 2400.0 && pulse_length < 0.7 / 2400.0) _crossings[3] = Tape::Short;

View File

@ -62,7 +62,7 @@ enum Key: uint16_t {
TerminateSequence = 0, NotMapped = 0xfffe, TerminateSequence = 0, NotMapped = 0xfffe,
}; };
class Tape: public Storage::TapePlayer { class Tape: public Storage::Tape::TapePlayer {
public: public:
Tape(); Tape();
@ -86,7 +86,7 @@ class Tape: public Storage::TapePlayer {
inline void set_is_in_input_mode(bool is_in_input_mode); inline void set_is_in_input_mode(bool is_in_input_mode);
private: private:
void process_input_pulse(Storage::Tape::Pulse pulse); void process_input_pulse(Storage::Tape::Tape::Pulse pulse);
inline void push_tape_bit(uint16_t bit); inline void push_tape_bit(uint16_t bit);
inline void get_next_tape_pulse(); inline void get_next_tape_pulse();
@ -145,7 +145,7 @@ class Machine:
Machine(); Machine();
void set_rom(ROMSlot slot, size_t length, const uint8_t *data); void set_rom(ROMSlot slot, size_t length, const uint8_t *data);
void set_tape(std::shared_ptr<Storage::Tape> tape); void set_tape(std::shared_ptr<Storage::Tape::Tape> tape);
void set_key_state(Key key, bool isPressed); void set_key_state(Key key, bool isPressed);
void clear_all_keys(); void clear_all_keys();

View File

@ -41,7 +41,7 @@
- (BOOL)openUEFAtURL:(NSURL *)URL { - (BOOL)openUEFAtURL:(NSURL *)URL {
@synchronized(self) { @synchronized(self) {
try { try {
std::shared_ptr<Storage::TapeUEF> tape(new Storage::TapeUEF([URL fileSystemRepresentation])); std::shared_ptr<Storage::Tape::UEF> tape(new Storage::Tape::UEF([URL fileSystemRepresentation]));
_electron.set_tape(tape); _electron.set_tape(tape);
return YES; return YES;
} catch(...) { } catch(...) {

View File

@ -49,7 +49,7 @@ using namespace Commodore::Vic20;
- (BOOL)openTAPAtURL:(NSURL *)URL { - (BOOL)openTAPAtURL:(NSURL *)URL {
@synchronized(self) { @synchronized(self) {
try { try {
std::shared_ptr<Storage::CommodoreTAP> tape(new Storage::CommodoreTAP([URL fileSystemRepresentation])); std::shared_ptr<Storage::Tape::CommodoreTAP> tape(new Storage::Tape::CommodoreTAP([URL fileSystemRepresentation]));
_vic20.set_tape(tape); _vic20.set_tape(tape);
return YES; return YES;
} catch(...) { } catch(...) {

View File

@ -49,7 +49,7 @@ std::list<Target> StaticAnalyser::GetTargets(const char *file_name)
// Collect all disks, tapes and ROMs as can be extrapolated from this file, forming the // Collect all disks, tapes and ROMs as can be extrapolated from this file, forming the
// union of all platforms this file might be a target for. // union of all platforms this file might be a target for.
std::list<std::shared_ptr<Storage::Disk>> disks; std::list<std::shared_ptr<Storage::Disk>> disks;
std::list<std::shared_ptr<Storage::Tape>> tapes; std::list<std::shared_ptr<Storage::Tape::Tape>> tapes;
TargetPlatformType potential_platforms = 0; TargetPlatformType potential_platforms = 0;
#define Format(extension, list, class, platforms) \ #define Format(extension, list, class, platforms) \
@ -79,7 +79,7 @@ std::list<Target> StaticAnalyser::GetTargets(const char *file_name)
{ {
// try instantiating as a ROM; failing that accept as a tape // try instantiating as a ROM; failing that accept as a tape
try { try {
tapes.emplace_back(new Storage::TapePRG(file_name)); tapes.emplace_back(new Storage::Tape::PRG(file_name));
potential_platforms |= (TargetPlatformType)TargetPlatform::Commodore; potential_platforms |= (TargetPlatformType)TargetPlatform::Commodore;
} catch(...) {} } catch(...) {}
} }
@ -89,8 +89,8 @@ std::list<Target> StaticAnalyser::GetTargets(const char *file_name)
{ {
} }
Format("tap", tapes, CommodoreTAP, TargetPlatform::Commodore) // TAP Format("tap", tapes, Tape::CommodoreTAP, TargetPlatform::Commodore) // TAP
Format("uef", tapes, TapeUEF, TargetPlatform::Acorn) // UEF (tape) Format("uef", tapes, Tape::UEF, TargetPlatform::Acorn) // UEF (tape)
#undef Format #undef Format

View File

@ -53,7 +53,7 @@ struct Target {
} loadingMethod; } loadingMethod;
std::list<std::shared_ptr<Storage::Disk>> disks; std::list<std::shared_ptr<Storage::Disk>> disks;
std::list<std::shared_ptr<Storage::Tape>> tapes; std::list<std::shared_ptr<Storage::Tape::Tape>> tapes;
// TODO: ROMs. Probably can't model as raw data, but then how to handle bus complexities? // TODO: ROMs. Probably can't model as raw data, but then how to handle bus complexities?
}; };

View File

@ -11,6 +11,7 @@
#include <cstring> #include <cstring>
using namespace Storage; using namespace Storage;
using namespace Tape;
CommodoreTAP::CommodoreTAP(const char *file_name) CommodoreTAP::CommodoreTAP(const char *file_name)
{ {
@ -64,7 +65,7 @@ void CommodoreTAP::reset()
_current_pulse.type = Pulse::High; _current_pulse.type = Pulse::High;
} }
Tape::Pulse CommodoreTAP::get_next_pulse() Storage::Tape::Tape::Pulse CommodoreTAP::get_next_pulse()
{ {
if(_current_pulse.type == Pulse::High) if(_current_pulse.type == Pulse::High)
{ {

View File

@ -13,6 +13,7 @@
#include <stdint.h> #include <stdint.h>
namespace Storage { namespace Storage {
namespace Tape {
/*! /*!
Provides a @c Tape containing a Commodore-format tape image, which is simply a timed list of downward-going zero crossings. Provides a @c Tape containing a Commodore-format tape image, which is simply a timed list of downward-going zero crossings.
@ -43,6 +44,7 @@ class CommodoreTAP: public Tape {
Pulse _current_pulse; Pulse _current_pulse;
}; };
}
} }
#endif /* CommodoreTAP_hpp */ #endif /* CommodoreTAP_hpp */

View File

@ -47,8 +47,9 @@
#include <sys/stat.h> #include <sys/stat.h>
using namespace Storage; using namespace Storage;
using namespace Tape;
TapePRG::TapePRG(const char *file_name) : _file(nullptr), _bitPhase(3), _filePhase(FilePhaseLeadIn), _phaseOffset(0), _copy_mask(0x80) PRG::PRG(const char *file_name) : _file(nullptr), _bitPhase(3), _filePhase(FilePhaseLeadIn), _phaseOffset(0), _copy_mask(0x80)
{ {
struct stat file_stats; struct stat file_stats;
stat(file_name, &file_stats); stat(file_name, &file_stats);
@ -69,12 +70,12 @@ TapePRG::TapePRG(const char *file_name) : _file(nullptr), _bitPhase(3), _filePha
throw ErrorBadFormat; throw ErrorBadFormat;
} }
TapePRG::~TapePRG() PRG::~PRG()
{ {
if(_file) fclose(_file); if(_file) fclose(_file);
} }
Tape::Pulse TapePRG::get_next_pulse() Storage::Tape::Tape::Pulse PRG::get_next_pulse()
{ {
// these are all microseconds per pole // these are all microseconds per pole
static const unsigned int leader_zero_length = 179; static const unsigned int leader_zero_length = 179;
@ -87,7 +88,7 @@ Tape::Pulse TapePRG::get_next_pulse()
Tape::Pulse pulse; Tape::Pulse pulse;
pulse.length.clock_rate = 1000000; pulse.length.clock_rate = 1000000;
pulse.type = (_bitPhase&1) ? Pulse::High : Pulse::Low; pulse.type = (_bitPhase&1) ? Tape::Pulse::High : Tape::Pulse::Low;
switch(_outputToken) switch(_outputToken)
{ {
case Leader: pulse.length.length = leader_zero_length; break; case Leader: pulse.length.length = leader_zero_length; break;
@ -95,12 +96,12 @@ Tape::Pulse TapePRG::get_next_pulse()
case One: pulse.length.length = (_bitPhase&2) ? zero_length : one_length; break; case One: pulse.length.length = (_bitPhase&2) ? zero_length : one_length; break;
case WordMarker: pulse.length.length = (_bitPhase&2) ? one_length : marker_length; break; case WordMarker: pulse.length.length = (_bitPhase&2) ? one_length : marker_length; break;
case EndOfBlock: pulse.length.length = (_bitPhase&2) ? zero_length : marker_length; break; case EndOfBlock: pulse.length.length = (_bitPhase&2) ? zero_length : marker_length; break;
case Silence: pulse.type = Pulse::Zero; pulse.length.length = 5000; break; case Silence: pulse.type = Tape::Pulse::Zero; pulse.length.length = 5000; break;
} }
return pulse; return pulse;
} }
void TapePRG::reset() void PRG::reset()
{ {
_bitPhase = 3; _bitPhase = 3;
fseek(_file, 2, SEEK_SET); fseek(_file, 2, SEEK_SET);
@ -109,7 +110,7 @@ void TapePRG::reset()
_copy_mask = 0x80; _copy_mask = 0x80;
} }
void TapePRG::get_next_output_token() void PRG::get_next_output_token()
{ {
static const int block_length = 192; // not counting the checksum static const int block_length = 192; // not counting the checksum
static const int countdown_bytes = 9; static const int countdown_bytes = 9;

View File

@ -6,18 +6,19 @@
// Copyright © 2016 Thomas Harte. All rights reserved. // Copyright © 2016 Thomas Harte. All rights reserved.
// //
#ifndef TapePRG_hpp #ifndef Storage_Tape_PRG_hpp
#define TapePRG_hpp #define Storage_Tape_PRG_hpp
#include "../Tape.hpp" #include "../Tape.hpp"
#include <stdint.h> #include <stdint.h>
namespace Storage { namespace Storage {
namespace Tape {
/*! /*!
Provides a @c Tape containing a .PRG, which is a direct local file. Provides a @c Tape containing a .PRG, which is a direct local file.
*/ */
class TapePRG: public Tape { class PRG: public Tape {
public: public:
/*! /*!
Constructs a @c T64 containing content from the file with name @c file_name, of type @c type. Constructs a @c T64 containing content from the file with name @c file_name, of type @c type.
@ -26,8 +27,8 @@ class TapePRG: public Tape {
@param type The type of data the file should contain. @param type The type of data the file should contain.
@throws ErrorBadFormat if this file could not be opened and recognised as the specified type. @throws ErrorBadFormat if this file could not be opened and recognised as the specified type.
*/ */
TapePRG(const char *file_name); PRG(const char *file_name);
~TapePRG(); ~PRG();
enum { enum {
ErrorBadFormat ErrorBadFormat
@ -64,6 +65,7 @@ class TapePRG: public Tape {
uint8_t _copy_mask; uint8_t _copy_mask;
}; };
}
} }
#endif /* T64_hpp */ #endif /* T64_hpp */

View File

@ -11,6 +11,7 @@
#include <math.h> #include <math.h>
using namespace Storage; using namespace Storage;
using namespace Tape;
static float gzgetfloat(gzFile file) static float gzgetfloat(gzFile file)
{ {
@ -43,7 +44,7 @@ static float gzgetfloat(gzFile file)
return result; return result;
} }
TapeUEF::TapeUEF(const char *file_name) : UEF::UEF(const char *file_name) :
_chunk_id(0), _chunk_length(0), _chunk_position(0), _chunk_id(0), _chunk_length(0), _chunk_position(0),
_time_base(1200) _time_base(1200)
{ {
@ -69,17 +70,17 @@ TapeUEF::TapeUEF(const char *file_name) :
find_next_tape_chunk(); find_next_tape_chunk();
} }
TapeUEF::~TapeUEF() UEF::~UEF()
{ {
gzclose(_file); gzclose(_file);
} }
void TapeUEF::reset() void UEF::reset()
{ {
gzseek(_file, 12, SEEK_SET); gzseek(_file, 12, SEEK_SET);
} }
Tape::Pulse TapeUEF::get_next_pulse() Storage::Tape::Tape::Pulse UEF::get_next_pulse()
{ {
Pulse next_pulse; Pulse next_pulse;
@ -147,7 +148,7 @@ Tape::Pulse TapeUEF::get_next_pulse()
return next_pulse; return next_pulse;
} }
void TapeUEF::find_next_tape_chunk() void UEF::find_next_tape_chunk()
{ {
int reset_count = 0; int reset_count = 0;
_chunk_position = 0; _chunk_position = 0;
@ -236,7 +237,7 @@ void TapeUEF::find_next_tape_chunk()
} }
} }
bool TapeUEF::chunk_is_finished() bool UEF::chunk_is_finished()
{ {
switch(_chunk_id) switch(_chunk_id)
{ {
@ -252,7 +253,7 @@ bool TapeUEF::chunk_is_finished()
} }
} }
bool TapeUEF::get_next_bit() bool UEF::get_next_bit()
{ {
switch(_chunk_id) switch(_chunk_id)
{ {

View File

@ -14,19 +14,20 @@
#include <stdint.h> #include <stdint.h>
namespace Storage { namespace Storage {
namespace Tape {
/*! /*!
Provides a @c Tape containing a UEF tape image, a slightly-convoluted description of pulses. Provides a @c Tape containing a UEF tape image, a slightly-convoluted description of pulses.
*/ */
class TapeUEF : public Tape { class UEF : public Tape {
public: public:
/*! /*!
Constructs a @c UEF containing content from the file with name @c file_name. Constructs a @c UEF containing content from the file with name @c file_name.
@throws ErrorNotUEF if this file could not be opened and recognised as a valid UEF. @throws ErrorNotUEF if this file could not be opened and recognised as a valid UEF.
*/ */
TapeUEF(const char *file_name); UEF(const char *file_name);
~TapeUEF(); ~UEF();
enum { enum {
ErrorNotUEF ErrorNotUEF
@ -72,6 +73,7 @@ class TapeUEF : public Tape {
bool chunk_is_finished(); bool chunk_is_finished();
}; };
}
} }
#endif /* TapeUEF_hpp */ #endif /* TapeUEF_hpp */

View File

@ -10,8 +10,9 @@
#include "../../NumberTheory/Factors.hpp" #include "../../NumberTheory/Factors.hpp"
using namespace Storage; using namespace Storage;
using namespace Tape;
void Tape::seek(Time seek_time) void Storage::Tape::Tape::seek(Time seek_time)
{ {
// TODO: as best we can // TODO: as best we can
} }
@ -20,7 +21,7 @@ TapePlayer::TapePlayer(unsigned int input_clock_rate) :
TimedEventLoop(input_clock_rate) TimedEventLoop(input_clock_rate)
{} {}
void TapePlayer::set_tape(std::shared_ptr<Storage::Tape> tape) void TapePlayer::set_tape(std::shared_ptr<Storage::Tape::Tape> tape)
{ {
_tape = tape; _tape = tape;
reset_timer(); reset_timer();
@ -41,7 +42,7 @@ void TapePlayer::get_next_pulse()
{ {
_current_pulse.length.length = 1; _current_pulse.length.length = 1;
_current_pulse.length.clock_rate = 1; _current_pulse.length.clock_rate = 1;
_current_pulse.type = Storage::Tape::Pulse::Zero; _current_pulse.type = Tape::Pulse::Zero;
} }
set_next_event_time_interval(_current_pulse.length); set_next_event_time_interval(_current_pulse.length);

View File

@ -13,6 +13,7 @@
#include "../TimedEventLoop.hpp" #include "../TimedEventLoop.hpp"
namespace Storage { namespace Storage {
namespace Tape {
/*! /*!
Models a tape as a sequence of pulses, each pulse being of arbitrary length and described Models a tape as a sequence of pulses, each pulse being of arbitrary length and described
@ -51,7 +52,7 @@ class TapePlayer: public TimedEventLoop {
public: public:
TapePlayer(unsigned int input_clock_rate); TapePlayer(unsigned int input_clock_rate);
void set_tape(std::shared_ptr<Storage::Tape> tape); void set_tape(std::shared_ptr<Storage::Tape::Tape> tape);
bool has_tape(); bool has_tape();
void run_for_cycles(int number_of_cycles); void run_for_cycles(int number_of_cycles);
@ -64,10 +65,11 @@ class TapePlayer: public TimedEventLoop {
private: private:
inline void get_next_pulse(); inline void get_next_pulse();
std::shared_ptr<Storage::Tape> _tape; std::shared_ptr<Storage::Tape::Tape> _tape;
Tape::Pulse _current_pulse; Tape::Pulse _current_pulse;
}; };
}
} }
#endif /* Tape_hpp */ #endif /* Tape_hpp */