From 308b3ca4481709a0c1fce4de66be2b27550b9a63 Mon Sep 17 00:00:00 2001 From: Thomas Harte Date: Mon, 13 May 2024 22:25:02 -0400 Subject: [PATCH] Gamely attempt to pick an Arc program to start. --- Analyser/Static/Acorn/Disk.cpp | 5 ++-- Analyser/Static/Acorn/StaticAnalyser.cpp | 37 +++++++++++++++++++++--- 2 files changed, 36 insertions(+), 6 deletions(-) diff --git a/Analyser/Static/Acorn/Disk.cpp b/Analyser/Static/Acorn/Disk.cpp index b83eedee8..e0da241e6 100644 --- a/Analyser/Static/Acorn/Disk.cpp +++ b/Analyser/Static/Acorn/Disk.cpp @@ -145,8 +145,9 @@ std::unique_ptr Analyser::Static::Acorn::GetADFSCatalogue(const std:: } name[c] = '\0'; - // Skip if the name is empty. - if(name[0] == '\0') continue; + // An empty name implies the directory has ended; files are always listed in case-insensitive + // sorted order, with that list being terminated by a '\0'. + if(name[0] == '\0') break; // Populate a file then. File new_file; diff --git a/Analyser/Static/Acorn/StaticAnalyser.cpp b/Analyser/Static/Acorn/StaticAnalyser.cpp index a82a8e1cf..84a8a36a8 100644 --- a/Analyser/Static/Acorn/StaticAnalyser.cpp +++ b/Analyser/Static/Acorn/StaticAnalyser.cpp @@ -102,14 +102,14 @@ Analyser::Static::TargetList Analyser::Static::Acorn::GetTargets(const Media &me } if(!media.disks.empty()) { - // TODO: below requires an [8-bit compatible] 'Hugo' ADFS catalogue, disallowing - // [Archimedes-exclusive] 'Nick' catalogues. - // - // Would be better to form the appropriate target in the latter case. std::shared_ptr disk = media.disks.front(); std::unique_ptr dfs_catalogue, adfs_catalogue; + + // Get any sort of catalogue that can be found. dfs_catalogue = GetDFSCatalogue(disk); if(dfs_catalogue == nullptr) adfs_catalogue = GetADFSCatalogue(disk); + + // 8-bit options: DFS and Hugo-style ADFS. if(dfs_catalogue || (adfs_catalogue && !adfs_catalogue->has_large_sectors && adfs_catalogue->is_hugo)) { // Accept the disk and determine whether DFS or ADFS ROMs are implied. // Use the Pres ADFS if using an ADFS, as it leaves Page at &EOO. @@ -144,7 +144,36 @@ Analyser::Static::TargetList Analyser::Static::Acorn::GetTargets(const Media &me } } } else if(adfs_catalogue) { + // Archimedes options, implicitly: ADFS, non-Hugo. targetArchimedes->media.disks = media.disks; + + // Always try a shift-restart; it's worth a go. + targetArchimedes->should_shift_restart = true; + + // Also look for the best possible startup program name, if it can be discerned. + for(const auto &file: adfs_catalogue->files) { + // Skip files that would have been caught by shift-restart if suitable. + if(file.name == "!System" || file.name == "!Boot") continue; + + // Skip non-Pling files. + if(file.name[0] != '!') continue; + + // Take whatever else comes with a preference for things that don't + // have 'read' in them (which will tend to be read_me or read_this or similar). + constexpr char read[] = "read"; + const auto has_read = + std::search( + file.name.begin(), file.name.end(), + std::begin(read), std::end(read) - 1, // i.e. don't compare the trailing NULL. + [](char lhs, char rhs) { + return std::tolower(lhs) == rhs; + } + ) != file.name.end(); + + if(targetArchimedes->main_program.empty() || !has_read) { + targetArchimedes->main_program = file.name; + } + } } }