From fe621d7e524fc9c2f1efb861c6a368d9c2bf89d4 Mon Sep 17 00:00:00 2001 From: Thomas Harte Date: Thu, 3 Oct 2019 22:10:10 -0400 Subject: [PATCH] Adds a route through the static analyser to the Atari ST. --- .../{Atari => Atari2600}/StaticAnalyser.cpp | 49 +++++++------- .../{Atari => Atari2600}/StaticAnalyser.hpp | 2 +- .../Static/{Atari => Atari2600}/Target.hpp | 6 +- Analyser/Static/AtariST/StaticAnalyser.cpp | 26 ++++++++ Analyser/Static/AtariST/StaticAnalyser.hpp | 27 ++++++++ Analyser/Static/AtariST/Target.hpp | 23 +++++++ Analyser/Static/StaticAnalyser.cpp | 8 ++- Machines/Atari2600/Atari2600.cpp | 9 +-- .../Clock Signal.xcodeproj/project.pbxproj | 66 +++++++++++++------ OSBindings/Mac/Clock Signal/Info.plist | 20 ++++++ Storage/Disk/DiskImage/Formats/MSA.cpp | 23 +++++++ Storage/Disk/DiskImage/Formats/MSA.hpp | 38 +++++++++++ Storage/TargetPlatforms.hpp | 31 ++++----- 13 files changed, 259 insertions(+), 69 deletions(-) rename Analyser/Static/{Atari => Atari2600}/StaticAnalyser.cpp (73%) rename Analyser/Static/{Atari => Atari2600}/StaticAnalyser.hpp (96%) rename Analyser/Static/{Atari => Atari2600}/Target.hpp (85%) create mode 100644 Analyser/Static/AtariST/StaticAnalyser.cpp create mode 100644 Analyser/Static/AtariST/StaticAnalyser.hpp create mode 100644 Analyser/Static/AtariST/Target.hpp create mode 100644 Storage/Disk/DiskImage/Formats/MSA.cpp create mode 100644 Storage/Disk/DiskImage/Formats/MSA.hpp diff --git a/Analyser/Static/Atari/StaticAnalyser.cpp b/Analyser/Static/Atari2600/StaticAnalyser.cpp similarity index 73% rename from Analyser/Static/Atari/StaticAnalyser.cpp rename to Analyser/Static/Atari2600/StaticAnalyser.cpp index 84773bb9b..74d048cd5 100644 --- a/Analyser/Static/Atari/StaticAnalyser.cpp +++ b/Analyser/Static/Atari2600/StaticAnalyser.cpp @@ -12,9 +12,10 @@ #include "../Disassembler/6502.hpp" -using namespace Analyser::Static::Atari; +using namespace Analyser::Static::Atari2600; +using Target = Analyser::Static::Atari2600::Target; -static void DeterminePagingFor2kCartridge(Analyser::Static::Atari::Target &target, const Storage::Cartridge::Cartridge::Segment &segment) { +static void DeterminePagingFor2kCartridge(Target &target, const Storage::Cartridge::Cartridge::Segment &segment) { // if this is a 2kb cartridge then it's definitely either unpaged or a CommaVid uint16_t entry_address, break_address; @@ -48,10 +49,10 @@ static void DeterminePagingFor2kCartridge(Analyser::Static::Atari::Target &targe // caveat: false positives aren't likely to be problematic; a false positive is a 2KB ROM that always addresses // itself so as to land in ROM even if mapped as a CommaVid and this code is on the fence as to whether it // attempts to modify itself but it probably doesn't - if(has_wide_area_store) target.paging_model = Analyser::Static::Atari::Target::PagingModel::CommaVid; + if(has_wide_area_store) target.paging_model = Target::PagingModel::CommaVid; } -static void DeterminePagingFor8kCartridge(Analyser::Static::Atari::Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { +static void DeterminePagingFor8kCartridge(Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { // Activision stack titles have their vectors at the top of the low 4k, not the top, and // always list 0xf000 as both vectors; they do not repeat them, and, inexplicably, they all // issue an SEI as their first instruction (maybe some sort of relic of the development environment?) @@ -60,12 +61,12 @@ static void DeterminePagingFor8kCartridge(Analyser::Static::Atari::Target &targe (segment.data[8191] != 0xf0 || segment.data[8189] != 0xf0 || segment.data[8190] != 0x00 || segment.data[8188] != 0x00) && segment.data[0] == 0x78 ) { - target.paging_model = Analyser::Static::Atari::Target::PagingModel::ActivisionStack; + target.paging_model = Target::PagingModel::ActivisionStack; return; } // make an assumption that this is the Atari paging model - target.paging_model = Analyser::Static::Atari::Target::PagingModel::Atari8k; + target.paging_model = Target::PagingModel::Atari8k; std::set internal_accesses; internal_accesses.insert(disassembly.internal_stores.begin(), disassembly.internal_stores.end()); @@ -85,13 +86,13 @@ static void DeterminePagingFor8kCartridge(Analyser::Static::Atari::Target &targe tigervision_access_count += masked_address == 0x3f; } - if(parker_access_count > atari_access_count) target.paging_model = Analyser::Static::Atari::Target::PagingModel::ParkerBros; - else if(tigervision_access_count > atari_access_count) target.paging_model = Analyser::Static::Atari::Target::PagingModel::Tigervision; + if(parker_access_count > atari_access_count) target.paging_model = Target::PagingModel::ParkerBros; + else if(tigervision_access_count > atari_access_count) target.paging_model = Target::PagingModel::Tigervision; } -static void DeterminePagingFor16kCartridge(Analyser::Static::Atari::Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { +static void DeterminePagingFor16kCartridge(Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { // make an assumption that this is the Atari paging model - target.paging_model = Analyser::Static::Atari::Target::PagingModel::Atari16k; + target.paging_model = Target::PagingModel::Atari16k; std::set internal_accesses; internal_accesses.insert(disassembly.internal_stores.begin(), disassembly.internal_stores.end()); @@ -106,17 +107,17 @@ static void DeterminePagingFor16kCartridge(Analyser::Static::Atari::Target &targ mnetwork_access_count += masked_address >= 0x1fe0 && masked_address < 0x1ffb; } - if(mnetwork_access_count > atari_access_count) target.paging_model = Analyser::Static::Atari::Target::PagingModel::MNetwork; + if(mnetwork_access_count > atari_access_count) target.paging_model = Target::PagingModel::MNetwork; } -static void DeterminePagingFor64kCartridge(Analyser::Static::Atari::Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { +static void DeterminePagingFor64kCartridge(Target &target, const Storage::Cartridge::Cartridge::Segment &segment, const Analyser::Static::MOS6502::Disassembly &disassembly) { // make an assumption that this is a Tigervision if there is a write to 3F target.paging_model = (disassembly.external_stores.find(0x3f) != disassembly.external_stores.end()) ? - Analyser::Static::Atari::Target::PagingModel::Tigervision : Analyser::Static::Atari::Target::PagingModel::MegaBoy; + Target::PagingModel::Tigervision : Target::PagingModel::MegaBoy; } -static void DeterminePagingForCartridge(Analyser::Static::Atari::Target &target, const Storage::Cartridge::Cartridge::Segment &segment) { +static void DeterminePagingForCartridge(Target &target, const Storage::Cartridge::Cartridge::Segment &segment) { if(segment.data.size() == 2048) { DeterminePagingFor2kCartridge(target, segment); return; @@ -140,16 +141,16 @@ static void DeterminePagingForCartridge(Analyser::Static::Atari::Target &target, DeterminePagingFor8kCartridge(target, segment, disassembly); break; case 10495: - target.paging_model = Analyser::Static::Atari::Target::PagingModel::Pitfall2; + target.paging_model = Target::PagingModel::Pitfall2; break; case 12288: - target.paging_model = Analyser::Static::Atari::Target::PagingModel::CBSRamPlus; + target.paging_model = Target::PagingModel::CBSRamPlus; break; case 16384: DeterminePagingFor16kCartridge(target, segment, disassembly); break; case 32768: - target.paging_model = Analyser::Static::Atari::Target::PagingModel::Atari32k; + target.paging_model = Target::PagingModel::Atari32k; break; case 65536: DeterminePagingFor64kCartridge(target, segment, disassembly); @@ -161,8 +162,8 @@ static void DeterminePagingForCartridge(Analyser::Static::Atari::Target &target, // check for a Super Chip. Atari ROM images [almost] always have the same value stored over RAM // regions; when they don't they at least seem to have the first 128 bytes be the same as the // next 128 bytes. So check for that. - if( target.paging_model != Analyser::Static::Atari::Target::PagingModel::CBSRamPlus && - target.paging_model != Analyser::Static::Atari::Target::PagingModel::MNetwork) { + if( target.paging_model != Target::PagingModel::CBSRamPlus && + target.paging_model != Target::PagingModel::MNetwork) { bool has_superchip = true; for(std::size_t address = 0; address < 128; address++) { if(segment.data[address] != segment.data[address+128]) { @@ -174,19 +175,19 @@ static void DeterminePagingForCartridge(Analyser::Static::Atari::Target &target, } // check for a Tigervision or Tigervision-esque scheme - if(target.paging_model == Analyser::Static::Atari::Target::PagingModel::None && segment.data.size() > 4096) { + if(target.paging_model == Target::PagingModel::None && segment.data.size() > 4096) { bool looks_like_tigervision = disassembly.external_stores.find(0x3f) != disassembly.external_stores.end(); - if(looks_like_tigervision) target.paging_model = Analyser::Static::Atari::Target::PagingModel::Tigervision; + if(looks_like_tigervision) target.paging_model = Target::PagingModel::Tigervision; } } -Analyser::Static::TargetList Analyser::Static::Atari::GetTargets(const Media &media, const std::string &file_name, TargetPlatform::IntType potential_platforms) { +Analyser::Static::TargetList Analyser::Static::Atari2600::GetTargets(const Media &media, const std::string &file_name, TargetPlatform::IntType potential_platforms) { // TODO: sanity checking; is this image really for an Atari 2600? - std::unique_ptr target(new Analyser::Static::Atari::Target); + std::unique_ptr target(new Target); target->machine = Machine::Atari2600; target->confidence = 0.5; target->media.cartridges = media.cartridges; - target->paging_model = Analyser::Static::Atari::Target::PagingModel::None; + target->paging_model = Target::PagingModel::None; target->uses_superchip = false; // try to figure out the paging scheme diff --git a/Analyser/Static/Atari/StaticAnalyser.hpp b/Analyser/Static/Atari2600/StaticAnalyser.hpp similarity index 96% rename from Analyser/Static/Atari/StaticAnalyser.hpp rename to Analyser/Static/Atari2600/StaticAnalyser.hpp index a311b2834..0cf6e6fd3 100644 --- a/Analyser/Static/Atari/StaticAnalyser.hpp +++ b/Analyser/Static/Atari2600/StaticAnalyser.hpp @@ -15,7 +15,7 @@ namespace Analyser { namespace Static { -namespace Atari { +namespace Atari2600 { TargetList GetTargets(const Media &media, const std::string &file_name, TargetPlatform::IntType potential_platforms); diff --git a/Analyser/Static/Atari/Target.hpp b/Analyser/Static/Atari2600/Target.hpp similarity index 85% rename from Analyser/Static/Atari/Target.hpp rename to Analyser/Static/Atari2600/Target.hpp index 0e2ab69c2..4bd4c5384 100644 --- a/Analyser/Static/Atari/Target.hpp +++ b/Analyser/Static/Atari2600/Target.hpp @@ -6,14 +6,14 @@ // Copyright 2018 Thomas Harte. All rights reserved. // -#ifndef Analyser_Static_Atari_Target_h -#define Analyser_Static_Atari_Target_h +#ifndef Analyser_Static_Atari2600_Target_h +#define Analyser_Static_Atari2600_Target_h #include "../StaticAnalyser.hpp" namespace Analyser { namespace Static { -namespace Atari { +namespace Atari2600 { struct Target: public ::Analyser::Static::Target { enum class PagingModel { diff --git a/Analyser/Static/AtariST/StaticAnalyser.cpp b/Analyser/Static/AtariST/StaticAnalyser.cpp new file mode 100644 index 000000000..b46d0e17d --- /dev/null +++ b/Analyser/Static/AtariST/StaticAnalyser.cpp @@ -0,0 +1,26 @@ +// +// StaticAnalyser.cpp +// Clock Signal +// +// Created by Thomas Harte on 03/10/2019. +// Copyright © 2019 Thomas Harte. All rights reserved. +// + +#include "StaticAnalyser.hpp" +#include "Target.hpp" + +Analyser::Static::TargetList Analyser::Static::AtariST::GetTargets(const Media &media, const std::string &file_name, TargetPlatform::IntType potential_platforms) { + // This analyser can comprehend disks and mass-storage devices only. + if(media.disks.empty()) return {}; + + // As there is at least one usable media image, wave it through. + Analyser::Static::TargetList targets; + + using Target = Analyser::Static::Target; + auto *target = new Target; + target->machine = Analyser::Machine::AtariST; + target->media = media; + targets.push_back(std::unique_ptr(target)); + + return targets; +} diff --git a/Analyser/Static/AtariST/StaticAnalyser.hpp b/Analyser/Static/AtariST/StaticAnalyser.hpp new file mode 100644 index 000000000..54c041eed --- /dev/null +++ b/Analyser/Static/AtariST/StaticAnalyser.hpp @@ -0,0 +1,27 @@ +// +// StaticAnalyser.hpp +// Clock Signal +// +// Created by Thomas Harte on 03/10/2019. +// Copyright © 2019 Thomas Harte. All rights reserved. +// + +#ifndef Analyser_Static_AtariST_StaticAnalyser_hpp +#define Analyser_Static_AtariST_StaticAnalyser_hpp + +#include "../StaticAnalyser.hpp" +#include "../../../Storage/TargetPlatforms.hpp" +#include + +namespace Analyser { +namespace Static { +namespace AtariST { + +TargetList GetTargets(const Media &media, const std::string &file_name, TargetPlatform::IntType potential_platforms); + +} +} +} + + +#endif /* Analyser_Static_AtariST_StaticAnalyser_hpp */ diff --git a/Analyser/Static/AtariST/Target.hpp b/Analyser/Static/AtariST/Target.hpp new file mode 100644 index 000000000..f9c6f2828 --- /dev/null +++ b/Analyser/Static/AtariST/Target.hpp @@ -0,0 +1,23 @@ +// +// Target.hpp +// Clock Signal +// +// Created by Thomas Harte on 03/06/2019. +// Copyright © 2019 Thomas Harte. All rights reserved. +// + +#ifndef Analyser_Static_AtariST_Target_h +#define Analyser_Static_AtariST_Target_h + +namespace Analyser { +namespace Static { +namespace AtariST { + +struct Target: public ::Analyser::Static::Target { +}; + +} +} +} + +#endif /* Analyser_Static_AtariST_Target_h */ diff --git a/Analyser/Static/StaticAnalyser.cpp b/Analyser/Static/StaticAnalyser.cpp index a9df90cf0..bbd49c8d2 100644 --- a/Analyser/Static/StaticAnalyser.cpp +++ b/Analyser/Static/StaticAnalyser.cpp @@ -17,7 +17,8 @@ #include "Acorn/StaticAnalyser.hpp" #include "AmstradCPC/StaticAnalyser.hpp" #include "AppleII/StaticAnalyser.hpp" -#include "Atari/StaticAnalyser.hpp" +#include "Atari2600/StaticAnalyser.hpp" +#include "AtariST/StaticAnalyser.hpp" #include "Coleco/StaticAnalyser.hpp" #include "Commodore/StaticAnalyser.hpp" #include "DiskII/StaticAnalyser.hpp" @@ -40,6 +41,7 @@ #include "../../Storage/Disk/DiskImage/Formats/G64.hpp" #include "../../Storage/Disk/DiskImage/Formats/DMK.hpp" #include "../../Storage/Disk/DiskImage/Formats/HFE.hpp" +#include "../../Storage/Disk/DiskImage/Formats/MSA.hpp" #include "../../Storage/Disk/DiskImage/Formats/MSXDSK.hpp" #include "../../Storage/Disk/DiskImage/Formats/NIB.hpp" #include "../../Storage/Disk/DiskImage/Formats/OricMFMDSK.hpp" @@ -117,6 +119,7 @@ static Media GetMediaAndPlatforms(const std::string &file_name, TargetPlatform:: // HFE (TODO: switch to AllDisk once the MSX stops being so greedy) Format("img", result.disks, Disk::DiskImageHolder, TargetPlatform::Macintosh) // IMG (DiskCopy 4.2) Format("image", result.disks, Disk::DiskImageHolder, TargetPlatform::Macintosh) // IMG (DiskCopy 4.2) + Format("msa", result.disks, Disk::DiskImageHolder, TargetPlatform::AtariST) // MSA Format("nib", result.disks, Disk::DiskImageHolder, TargetPlatform::DiskII) // NIB Format("o", result.tapes, Tape::ZX80O81P, TargetPlatform::ZX8081) // O Format("p", result.tapes, Tape::ZX80O81P, TargetPlatform::ZX8081) // P @@ -178,7 +181,8 @@ TargetList Analyser::Static::GetTargets(const std::string &file_name) { if(potential_platforms & TargetPlatform::Acorn) Append(Acorn); if(potential_platforms & TargetPlatform::AmstradCPC) Append(AmstradCPC); if(potential_platforms & TargetPlatform::AppleII) Append(AppleII); - if(potential_platforms & TargetPlatform::Atari2600) Append(Atari); + if(potential_platforms & TargetPlatform::Atari2600) Append(Atari2600); + if(potential_platforms & TargetPlatform::AtariST) Append(AtariST); if(potential_platforms & TargetPlatform::ColecoVision) Append(Coleco); if(potential_platforms & TargetPlatform::Commodore) Append(Commodore); if(potential_platforms & TargetPlatform::DiskII) Append(DiskII); diff --git a/Machines/Atari2600/Atari2600.cpp b/Machines/Atari2600/Atari2600.cpp index a9ac5d483..0324f900c 100644 --- a/Machines/Atari2600/Atari2600.cpp +++ b/Machines/Atari2600/Atari2600.cpp @@ -14,7 +14,7 @@ #include "../CRTMachine.hpp" #include "../JoystickMachine.hpp" -#include "../../Analyser/Static/Atari/Target.hpp" +#include "../../Analyser/Static/Atari2600/Target.hpp" #include "Cartridges/Atari8k.hpp" #include "Cartridges/Atari16k.hpp" @@ -72,18 +72,20 @@ class Joystick: public Inputs::ConcreteJoystick { std::size_t shift_, fire_tia_input_; }; +using Target = Analyser::Static::Atari2600::Target; + class ConcreteMachine: public Machine, public CRTMachine::Machine, public JoystickMachine::Machine, public Outputs::CRT::Delegate { public: - ConcreteMachine(const Analyser::Static::Atari::Target &target) { + ConcreteMachine(const Target &target) { set_clock_rate(NTSC_clock_rate); const std::vector &rom = target.media.cartridges.front()->get_segments().front().data; - using PagingModel = Analyser::Static::Atari::Target::PagingModel; + using PagingModel = Target::PagingModel; switch(target.paging_model) { case PagingModel::ActivisionStack: bus_.reset(new Cartridge::Cartridge(rom)); break; case PagingModel::CBSRamPlus: bus_.reset(new Cartridge::Cartridge(rom)); break; @@ -232,7 +234,6 @@ class ConcreteMachine: using namespace Atari2600; Machine *Machine::Atari2600(const Analyser::Static::Target *target, const ROMMachine::ROMFetcher &rom_fetcher) { - using Target = Analyser::Static::Atari::Target; const Target *const atari_target = dynamic_cast(target); return new Atari2600::ConcreteMachine(*atari_target); } diff --git a/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj b/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj index 05e9a8eff..b083d6697 100644 --- a/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj +++ b/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj @@ -280,8 +280,6 @@ 4B89451F201967B4007DE474 /* Tape.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F0201967B4007DE474 /* Tape.cpp */; }; 4B894520201967B4007DE474 /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F2201967B4007DE474 /* StaticAnalyser.cpp */; }; 4B894521201967B4007DE474 /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F2201967B4007DE474 /* StaticAnalyser.cpp */; }; - 4B894522201967B4007DE474 /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F5201967B4007DE474 /* StaticAnalyser.cpp */; }; - 4B894523201967B4007DE474 /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F5201967B4007DE474 /* StaticAnalyser.cpp */; }; 4B894524201967B4007DE474 /* Tape.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F9201967B4007DE474 /* Tape.cpp */; }; 4B894525201967B4007DE474 /* Tape.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944F9201967B4007DE474 /* Tape.cpp */; }; 4B894526201967B4007DE474 /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4B8944FA201967B4007DE474 /* StaticAnalyser.cpp */; }; @@ -638,6 +636,12 @@ 4BBFFEE61F7B27F1005F3FEB /* TrackSerialiser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BBFFEE51F7B27F1005F3FEB /* TrackSerialiser.cpp */; }; 4BC1316A2346C61100E4FF3D /* AtariST.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131682346C61100E4FF3D /* AtariST.cpp */; }; 4BC1316B2346C61100E4FF3D /* AtariST.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131682346C61100E4FF3D /* AtariST.cpp */; }; + 4BC131702346DE5000E4FF3D /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC1316F2346DE5000E4FF3D /* StaticAnalyser.cpp */; }; + 4BC131712346DE5000E4FF3D /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC1316F2346DE5000E4FF3D /* StaticAnalyser.cpp */; }; + 4BC131762346DE9100E4FF3D /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131752346DE9100E4FF3D /* StaticAnalyser.cpp */; }; + 4BC131772346DE9100E4FF3D /* StaticAnalyser.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131752346DE9100E4FF3D /* StaticAnalyser.cpp */; }; + 4BC1317A2346DF2B00E4FF3D /* MSA.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131782346DF2B00E4FF3D /* MSA.cpp */; }; + 4BC1317B2346DF2B00E4FF3D /* MSA.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BC131782346DF2B00E4FF3D /* MSA.cpp */; }; 4BC5C3E022C994CD00795658 /* 68000MoveTests.mm in Sources */ = {isa = PBXBuildFile; fileRef = 4BC5C3DF22C994CC00795658 /* 68000MoveTests.mm */; }; 4BC5FC3020CDDDEF00410AA0 /* AppleIIOptions.xib in Resources */ = {isa = PBXBuildFile; fileRef = 4BC5FC2E20CDDDEE00410AA0 /* AppleIIOptions.xib */; }; 4BC751B21D157E61006C31D9 /* 6522Tests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4BC751B11D157E61006C31D9 /* 6522Tests.swift */; }; @@ -1053,8 +1057,6 @@ 4B8944F0201967B4007DE474 /* Tape.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Tape.cpp; sourceTree = ""; }; 4B8944F1201967B4007DE474 /* Disk.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Disk.hpp; sourceTree = ""; }; 4B8944F2201967B4007DE474 /* StaticAnalyser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StaticAnalyser.cpp; sourceTree = ""; }; - 4B8944F4201967B4007DE474 /* StaticAnalyser.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = StaticAnalyser.hpp; sourceTree = ""; }; - 4B8944F5201967B4007DE474 /* StaticAnalyser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StaticAnalyser.cpp; sourceTree = ""; }; 4B8944F7201967B4007DE474 /* StaticAnalyser.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = StaticAnalyser.hpp; sourceTree = ""; }; 4B8944F8201967B4007DE474 /* Tape.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Tape.hpp; sourceTree = ""; }; 4B8944F9201967B4007DE474 /* Tape.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Tape.cpp; sourceTree = ""; }; @@ -1447,6 +1449,14 @@ 4BBFFEE51F7B27F1005F3FEB /* TrackSerialiser.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = TrackSerialiser.cpp; sourceTree = ""; }; 4BC131682346C61100E4FF3D /* AtariST.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = AtariST.cpp; sourceTree = ""; }; 4BC131692346C61100E4FF3D /* AtariST.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = AtariST.hpp; sourceTree = ""; }; + 4BC1316D2346DE5000E4FF3D /* StaticAnalyser.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = StaticAnalyser.hpp; sourceTree = ""; }; + 4BC1316E2346DE5000E4FF3D /* Target.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; + 4BC1316F2346DE5000E4FF3D /* StaticAnalyser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StaticAnalyser.cpp; sourceTree = ""; }; + 4BC131732346DE9100E4FF3D /* StaticAnalyser.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = StaticAnalyser.hpp; sourceTree = ""; }; + 4BC131742346DE9100E4FF3D /* Target.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; + 4BC131752346DE9100E4FF3D /* StaticAnalyser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StaticAnalyser.cpp; sourceTree = ""; }; + 4BC131782346DF2B00E4FF3D /* MSA.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = MSA.cpp; sourceTree = ""; }; + 4BC131792346DF2B00E4FF3D /* MSA.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = MSA.hpp; sourceTree = ""; }; 4BC5C3DF22C994CC00795658 /* 68000MoveTests.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = 68000MoveTests.mm; sourceTree = ""; }; 4BC5FC2F20CDDDEE00410AA0 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = "Clock Signal/Base.lproj/AppleIIOptions.xib"; sourceTree = SOURCE_ROOT; }; 4BC751B11D157E61006C31D9 /* 6522Tests.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = 6522Tests.swift; sourceTree = ""; }; @@ -1525,7 +1535,6 @@ 4BE32314205328FF006EF799 /* Target.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; 4BE3231520532AA7006EF799 /* Target.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; 4BE3231620532BED006EF799 /* Target.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; - 4BE3231720532CC0006EF799 /* Target.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Target.hpp; sourceTree = ""; }; 4BE76CF822641ED300ACD6FA /* QLTests.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = QLTests.mm; sourceTree = ""; }; 4BE7C9161E3D397100A5496D /* TIA.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TIA.cpp; sourceTree = ""; }; 4BE7C9171E3D397100A5496D /* TIA.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = TIA.hpp; sourceTree = ""; }; @@ -2041,11 +2050,12 @@ 4B0333AD2094081A0050B93D /* AppleDSK.cpp */, 4B45188F1F75FD1B00926311 /* CPCDSK.cpp */, 4B4518911F75FD1B00926311 /* D64.cpp */, - 4BB4BFAE22A42F290069048D /* MacintoshIMG.cpp */, 4BAF2B4C2004580C00480230 /* DMK.cpp */, 4B4518931F75FD1B00926311 /* G64.cpp */, 4B4518951F75FD1B00926311 /* HFE.cpp */, + 4BB4BFAE22A42F290069048D /* MacintoshIMG.cpp */, 4B58601C1F806AB200AEE2E3 /* MFMSectorDump.cpp */, + 4BC131782346DF2B00E4FF3D /* MSA.cpp */, 4BEBFB4B2002C4BF000708CC /* MSXDSK.cpp */, 4B0F94FC208C1A1600FE41D9 /* NIB.cpp */, 4B4518971F75FD1B00926311 /* OricMFMDSK.cpp */, @@ -2055,11 +2065,12 @@ 4B0333AE2094081A0050B93D /* AppleDSK.hpp */, 4B4518901F75FD1B00926311 /* CPCDSK.hpp */, 4B4518921F75FD1B00926311 /* D64.hpp */, - 4BB4BFAF22A42F290069048D /* MacintoshIMG.hpp */, 4BAF2B4D2004580C00480230 /* DMK.hpp */, 4B4518941F75FD1B00926311 /* G64.hpp */, 4B4518961F75FD1B00926311 /* HFE.hpp */, + 4BB4BFAF22A42F290069048D /* MacintoshIMG.hpp */, 4B58601D1F806AB200AEE2E3 /* MFMSectorDump.hpp */, + 4BC131792346DF2B00E4FF3D /* MSA.hpp */, 4BEBFB4C2002C4BF000708CC /* MSXDSK.hpp */, 4B0F94FD208C1A1600FE41D9 /* NIB.hpp */, 4B4518981F75FD1B00926311 /* OricMFMDSK.hpp */, @@ -2491,7 +2502,8 @@ 4B8944EB201967B4007DE474 /* Acorn */, 4B894514201967B4007DE474 /* AmstradCPC */, 4B15A9FE20824C9F005E6C8D /* AppleII */, - 4B8944F3201967B4007DE474 /* Atari */, + 4BC1316C2346DE5000E4FF3D /* Atari2600 */, + 4BC131722346DE9100E4FF3D /* AtariST */, 4B7A90EA20410A85008514A2 /* Coleco */, 4B8944FB201967B4007DE474 /* Commodore */, 4B894507201967B4007DE474 /* Disassembler */, @@ -2520,16 +2532,6 @@ path = Acorn; sourceTree = ""; }; - 4B8944F3201967B4007DE474 /* Atari */ = { - isa = PBXGroup; - children = ( - 4B8944F5201967B4007DE474 /* StaticAnalyser.cpp */, - 4B8944F4201967B4007DE474 /* StaticAnalyser.hpp */, - 4BE3231720532CC0006EF799 /* Target.hpp */, - ); - path = Atari; - sourceTree = ""; - }; 4B8944F6201967B4007DE474 /* Oric */ = { isa = PBXGroup; children = ( @@ -3193,6 +3195,26 @@ path = AtariST; sourceTree = ""; }; + 4BC1316C2346DE5000E4FF3D /* Atari2600 */ = { + isa = PBXGroup; + children = ( + 4BC1316D2346DE5000E4FF3D /* StaticAnalyser.hpp */, + 4BC1316E2346DE5000E4FF3D /* Target.hpp */, + 4BC1316F2346DE5000E4FF3D /* StaticAnalyser.cpp */, + ); + path = Atari2600; + sourceTree = ""; + }; + 4BC131722346DE9100E4FF3D /* AtariST */ = { + isa = PBXGroup; + children = ( + 4BC131732346DE9100E4FF3D /* StaticAnalyser.hpp */, + 4BC131742346DE9100E4FF3D /* Target.hpp */, + 4BC131752346DE9100E4FF3D /* StaticAnalyser.cpp */, + ); + path = AtariST; + sourceTree = ""; + }; 4BC9DF4A1D04691600F44158 /* Components */ = { isa = PBXGroup; children = ( @@ -4048,6 +4070,7 @@ 4B89451D201967B4007DE474 /* Disk.cpp in Sources */, 4BDACBED22FFA5D20045EF7E /* ncr5380.cpp in Sources */, 4BC1316B2346C61100E4FF3D /* AtariST.cpp in Sources */, + 4BC131772346DE9100E4FF3D /* StaticAnalyser.cpp in Sources */, 4B055ACF1FAE9B030060FFFF /* SoundGenerator.cpp in Sources */, 4B894519201967B4007DE474 /* ConfidenceCounter.cpp in Sources */, 4B055AEE1FAE9BBF0060FFFF /* Keyboard.cpp in Sources */, @@ -4071,6 +4094,7 @@ 4B055AEF1FAE9BF00060FFFF /* Typer.cpp in Sources */, 4B89453F201967B4007DE474 /* StaticAnalyser.cpp in Sources */, 4B89453D201967B4007DE474 /* StaticAnalyser.cpp in Sources */, + 4BC131712346DE5000E4FF3D /* StaticAnalyser.cpp in Sources */, 4B055ACA1FAE9AFB0060FFFF /* Vic20.cpp in Sources */, 4B8318B222D3E53C006DB630 /* Video.cpp in Sources */, 4B055ABC1FAE86170060FFFF /* ZX8081.cpp in Sources */, @@ -4080,6 +4104,7 @@ 4B74CF822312FA9C00500CE8 /* HFV.cpp in Sources */, 4B8318B022D3E531006DB630 /* AppleII.cpp in Sources */, 4B055AB11FAE86070060FFFF /* Tape.cpp in Sources */, + 4BC1317B2346DF2B00E4FF3D /* MSA.cpp in Sources */, 4BFE7B881FC39D8900160B38 /* StandardOptions.cpp in Sources */, 4B894533201967B4007DE474 /* 6502.cpp in Sources */, 4B055AA91FAE85EF0060FFFF /* CommodoreGCR.cpp in Sources */, @@ -4133,7 +4158,6 @@ 4B055A9F1FAE85DA0060FFFF /* HFE.cpp in Sources */, 4B07835B1FC11D42001D12BB /* Configurable.cpp in Sources */, 4BD191F52191180E0042E144 /* ScanTarget.cpp in Sources */, - 4B894523201967B4007DE474 /* StaticAnalyser.cpp in Sources */, 4B055AEC1FAE9BA20060FFFF /* Z80Base.cpp in Sources */, 4B0F94FF208C1A1600FE41D9 /* NIB.cpp in Sources */, 4B0E04EB1FC9E78800F43484 /* CAS.cpp in Sources */, @@ -4275,7 +4299,6 @@ 4B2B3A4B1F9B8FA70062DABF /* Typer.cpp in Sources */, 4B4518821F75E91A00926311 /* PCMSegment.cpp in Sources */, 4B74CF812312FA9C00500CE8 /* HFV.cpp in Sources */, - 4B894522201967B4007DE474 /* StaticAnalyser.cpp in Sources */, 4B17B58B20A8A9D9007CCA8F /* StringSerialiser.cpp in Sources */, 4BE7C9181E3D397100A5496D /* TIA.cpp in Sources */, 4B80AD001F85CACA00176895 /* BestEffortUpdater.cpp in Sources */, @@ -4310,6 +4333,7 @@ 4BCE0051227CE8CA000CA200 /* Video.cpp in Sources */, 4B894536201967B4007DE474 /* Z80.cpp in Sources */, 4BCA6CC81D9DD9F000C2D7B2 /* CommodoreROM.cpp in Sources */, + 4BC1317A2346DF2B00E4FF3D /* MSA.cpp in Sources */, 4BEA52661DF3472B007E74F2 /* TIASound.cpp in Sources */, 4BEBFB4D2002C4BF000708CC /* MSXDSK.cpp in Sources */, 4BBFBB6C1EE8401E00C01E7A /* ZX8081.cpp in Sources */, @@ -4329,12 +4353,14 @@ 4B79A5011FC913C900EEDAD5 /* MSX.cpp in Sources */, 4BEE0A701D72496600532C7B /* PRG.cpp in Sources */, 4BF437EE209D0F7E008CBD6B /* SegmentParser.cpp in Sources */, + 4BC131762346DE9100E4FF3D /* StaticAnalyser.cpp in Sources */, 4B8334861F5DA3780097E338 /* 6502Storage.cpp in Sources */, 4B8FE2271DA1DE2D0090D3CE /* NSBundle+DataResource.m in Sources */, 4BC91B831D1F160E00884B76 /* CommodoreTAP.cpp in Sources */, 4B55DD8320DF06680043F2E5 /* MachinePicker.swift in Sources */, 4B2A539F1D117D36003C6002 /* CSAudioQueue.m in Sources */, 4B89453E201967B4007DE474 /* StaticAnalyser.cpp in Sources */, + 4BC131702346DE5000E4FF3D /* StaticAnalyser.cpp in Sources */, 4B37EE821D7345A6006A09A4 /* BinaryDump.cpp in Sources */, 4BCE0053227CE8CA000CA200 /* AppleII.cpp in Sources */, 4B8334821F5D9FF70097E338 /* PartialMachineCycle.cpp in Sources */, diff --git a/OSBindings/Mac/Clock Signal/Info.plist b/OSBindings/Mac/Clock Signal/Info.plist index d318aa73b..c6ef0500a 100644 --- a/OSBindings/Mac/Clock Signal/Info.plist +++ b/OSBindings/Mac/Clock Signal/Info.plist @@ -387,6 +387,26 @@ LSTypeIsPackage + + CFBundleTypeExtensions + + msa + + CFBundleTypeIconFile + floppy35.png + CFBundleTypeName + Atari ST Disk Image + CFBundleTypeOSTypes + + ???? + + CFBundleTypeRole + Viewer + LSHandlerRank + Owner + LSTypeIsPackage + + CFBundleTypeExtensions diff --git a/Storage/Disk/DiskImage/Formats/MSA.cpp b/Storage/Disk/DiskImage/Formats/MSA.cpp new file mode 100644 index 000000000..9e24a87a3 --- /dev/null +++ b/Storage/Disk/DiskImage/Formats/MSA.cpp @@ -0,0 +1,23 @@ +// +// MSA.cpp +// Clock Signal +// +// Created by Thomas Harte on 03/10/2019. +// Copyright © 2019 Thomas Harte. All rights reserved. +// + +#include "MSA.hpp" + +using namespace Storage::Disk; + +MSA::MSA(const std::string &file_name) : + file_(file_name) { +} + +std::shared_ptr<::Storage::Disk::Track> MSA::get_track_at_position(::Storage::Disk::Track::Address address) { + return nullptr; +} + +HeadPosition MSA::get_maximum_head_position() { + return HeadPosition(10); +} diff --git a/Storage/Disk/DiskImage/Formats/MSA.hpp b/Storage/Disk/DiskImage/Formats/MSA.hpp new file mode 100644 index 000000000..076f85201 --- /dev/null +++ b/Storage/Disk/DiskImage/Formats/MSA.hpp @@ -0,0 +1,38 @@ +// +// MSA.hpp +// Clock Signal +// +// Created by Thomas Harte on 03/10/2019. +// Copyright © 2019 Thomas Harte. All rights reserved. +// + +#ifndef MSA_hpp +#define MSA_hpp + +#include "../DiskImage.hpp" +#include "../../../FileHolder.hpp" + +namespace Storage { +namespace Disk { + +/*! + Provides a @c DiskImage describing an Atari ST MSA disk image: + a track dump with some metadata and potentially patches of RLE compression. +*/ +class MSA final: public DiskImage { + public: + MSA(const std::string &file_name); + + // Implemented to satisfy @c DiskImage. + HeadPosition get_maximum_head_position() override; + std::shared_ptr<::Storage::Disk::Track> get_track_at_position(::Storage::Disk::Track::Address address) override; + + private: + FileHolder file_; +}; + + +} +} + +#endif /* MSA_hpp */ diff --git a/Storage/TargetPlatforms.hpp b/Storage/TargetPlatforms.hpp index 4df8a6a1c..1056147c2 100644 --- a/Storage/TargetPlatforms.hpp +++ b/Storage/TargetPlatforms.hpp @@ -16,25 +16,26 @@ enum Type: IntType { AmstradCPC = 1 << 1, AppleII = 1 << 2, Atari2600 = 1 << 3, - AcornAtom = 1 << 4, - AcornElectron = 1 << 5, - BBCMaster = 1 << 6, - BBCModelA = 1 << 7, - BBCModelB = 1 << 8, - ColecoVision = 1 << 9, - Commodore = 1 << 10, - DiskII = 1 << 11, - Sega = 1 << 12, - Macintosh = 1 << 13, - MSX = 1 << 14, - Oric = 1 << 15, - ZX80 = 1 << 16, - ZX81 = 1 << 17, + AtariST = 1 << 4, + AcornAtom = 1 << 5, + AcornElectron = 1 << 6, + BBCMaster = 1 << 7, + BBCModelA = 1 << 8, + BBCModelB = 1 << 9, + ColecoVision = 1 << 10, + Commodore = 1 << 11, + DiskII = 1 << 12, + Sega = 1 << 13, + Macintosh = 1 << 14, + MSX = 1 << 15, + Oric = 1 << 16, + ZX80 = 1 << 17, + ZX81 = 1 << 18, Acorn = AcornAtom | AcornElectron | BBCMaster | BBCModelA | BBCModelB, ZX8081 = ZX80 | ZX81, AllCartridge = Atari2600 | AcornElectron | ColecoVision | MSX, - AllDisk = Acorn | AmstradCPC | Commodore | Oric | MSX, + AllDisk = Acorn | AmstradCPC | Commodore | Oric | MSX, // TODO: | AtariST AllTape = Acorn | AmstradCPC | Commodore | Oric | ZX80 | ZX81 | MSX, };