Eliminate the broken tpi system for a simple drive/format type field.

This commit is contained in:
David Given
2023-10-29 21:10:14 +01:00
parent ff1fb761f2
commit 533b217c8f
86 changed files with 1831 additions and 798 deletions

View File

@@ -1,6 +1,6 @@
CC = gcc
CXX = g++ -std=c++17
CFLAGS = -g -Os
CFLAGS = -g -O0
LDFLAGS =
OBJ = .obj

View File

@@ -67,28 +67,32 @@ static uint8_t b(uint32_t field, uint8_t pos)
static uint8_t eccNextBit(uint32_t ecc, uint8_t data_bit)
{
// This is 0x81932080 which is 0x0104C981 with reversed bits
return b(ecc, 7) ^ b(ecc, 13) ^ b(ecc, 16) ^ b(ecc, 17) ^ b(ecc, 20)
^ b(ecc, 23) ^ b(ecc, 24) ^ b(ecc, 31) ^ data_bit;
return b(ecc, 7) ^ b(ecc, 13) ^ b(ecc, 16) ^ b(ecc, 17) ^ b(ecc, 20) ^
b(ecc, 23) ^ b(ecc, 24) ^ b(ecc, 31) ^ data_bit;
}
uint32_t vectorGraphicEcc(const Bytes& bytes)
{
uint32_t e = 0;
Bytes payloadBytes = bytes.slice(0, bytes.size()-4);
Bytes payloadBytes = bytes.slice(0, bytes.size() - 4);
ByteReader payload(payloadBytes);
while (!payload.eof()) {
while (!payload.eof())
{
uint8_t byte = payload.read_8();
for (int i = 0; i < 8; i++) {
for (int i = 0; i < 8; i++)
{
e = (e << 1) | eccNextBit(e, byte >> 7);
byte <<= 1;
}
}
Bytes trailerBytes = bytes.slice(bytes.size()-4);
Bytes trailerBytes = bytes.slice(bytes.size() - 4);
ByteReader trailer(trailerBytes);
uint32_t res = e;
while (!trailer.eof()) {
while (!trailer.eof())
{
uint8_t byte = trailer.read_8();
for (int i = 0; i < 8; i++) {
for (int i = 0; i < 8; i++)
{
res = (res << 1) | eccNextBit(e, byte >> 7);
e <<= 1;
byte <<= 1;
@@ -101,13 +105,15 @@ uint32_t vectorGraphicEcc(const Bytes& bytes)
static bool vectorGraphicEccFix(Bytes& bytes, uint32_t syndrome)
{
uint32_t ecc = syndrome;
int pos = (MICROPOLIS_ENCODED_SECTOR_SIZE-5)*8+7;
int pos = (MICROPOLIS_ENCODED_SECTOR_SIZE - 5) * 8 + 7;
bool aligned = false;
while ((ecc & 0xff000000) == 0) {
while ((ecc & 0xff000000) == 0)
{
pos += 8;
ecc <<= 8;
}
for (; pos >= 0; pos--) {
for (; pos >= 0; pos--)
{
bool bit = ecc & 1;
ecc >>= 1;
if (bit)
@@ -119,7 +125,7 @@ static bool vectorGraphicEccFix(Bytes& bytes, uint32_t syndrome)
}
if (pos < 0)
return false;
bytes[pos/8] ^= ecc >> 16;
bytes[pos / 8] ^= ecc >> 16;
return true;
}
@@ -199,9 +205,11 @@ public:
bool eccPresent = bytes[274] == 0xaa;
uint32_t ecc = 0;
if (_config.ecc_type() == MicropolisDecoderProto::VECTOR && eccPresent) {
if (_config.ecc_type() == MicropolisDecoderProto::VECTOR && eccPresent)
{
ecc = vectorGraphicEcc(bytes.slice(0, 274));
if (ecc != 0) {
if (ecc != 0)
{
vectorGraphicEccFix(bytes, ecc);
ecc = vectorGraphicEcc(bytes.slice(0, 274));
}

View File

@@ -49,7 +49,8 @@ static void write_sector(std::vector<bool>& bits,
uint8_t eccPresent = 0;
uint32_t ecc = 0;
if (eccType == MicropolisEncoderProto::VECTOR) {
if (eccType == MicropolisEncoderProto::VECTOR)
{
eccPresent = 0xaa;
ecc = vectorGraphicEcc(sectorData + Bytes(4));
}
@@ -98,23 +99,25 @@ public:
unsigned prev_cursor = 0;
unsigned cursor = 0;
for (const auto& sectorData : sectors) {
for (const auto& sectorData : sectors)
{
indexes.push_back(cursor);
prev_cursor = cursor;
write_sector(bits, cursor, sectorData, _config.ecc_type());
}
indexes.push_back(prev_cursor + (cursor - prev_cursor)/2);
indexes.push_back(prev_cursor + (cursor - prev_cursor) / 2);
indexes.push_back(cursor);
if (cursor != bits.size())
error("track data mismatched length");
std::unique_ptr<Fluxmap> fluxmap(new Fluxmap);
nanoseconds_t clockPeriod = calculatePhysicalClockPeriod(
_config.clock_period_us() * 1e3,
_config.rotational_period_ms() * 1e6);
nanoseconds_t clockPeriod =
calculatePhysicalClockPeriod(_config.clock_period_us() * 1e3,
_config.rotational_period_ms() * 1e6);
auto pos = bits.begin();
for (int i = 1; i < indexes.size(); i++) {
for (int i = 1; i < indexes.size(); i++)
{
auto end = bits.begin() + indexes[i];
fluxmap->appendBits(std::vector<bool>(pos, end), clockPeriod);
fluxmap->appendIndex();

View File

@@ -224,53 +224,53 @@ if not glob("../fluxengine-testdata/data"):
print("fluxengine-testdata not found; skipping corpus tests")
else:
corpus = [
("agat", "", "--drive.tpi=96"),
("amiga", "", "--drive.tpi=135"),
("apple2", "", "--140 --drive.tpi=96"),
("atarist", "", "--360 --drive.tpi=135"),
("atarist", "", "--370 --drive.tpi=135"),
("atarist", "", "--400 --drive.tpi=135"),
("atarist", "", "--410 --drive.tpi=135"),
("atarist", "", "--720 --drive.tpi=135"),
("atarist", "", "--740 --drive.tpi=135"),
("atarist", "", "--800 --drive.tpi=135"),
("atarist", "", "--820 --drive.tpi=135"),
("agat", "", ""),
("amiga", "", ""),
("apple2", "", "--140 40track_drive"),
("atarist", "", "--360"),
("atarist", "", "--370"),
("atarist", "", "--400"),
("atarist", "", "--410"),
("atarist", "", "--720"),
("atarist", "", "--740"),
("atarist", "", "--800"),
("atarist", "", "--820"),
("bk", "", ""),
("brother", "", "--120 --drive.tpi=135"),
("brother", "", "--240 --drive.tpi=135"),
("brother", "", "--120 40track_drive"),
("brother", "", "--240"),
(
"commodore",
"scripts/commodore1541_test.textpb",
"--171 --drive.tpi=96",
"--171 40track_drive",
),
(
"commodore",
"scripts/commodore1541_test.textpb",
"--192 --drive.tpi=96",
"--192 40track_drive",
),
("commodore", "", "--800 --drive.tpi=135"),
("commodore", "", "--1620 --drive.tpi=135"),
("hplif", "", "--264 --drive.tpi=135"),
("hplif", "", "--608 --drive.tpi=135"),
("hplif", "", "--616 --drive.tpi=135"),
("hplif", "", "--770 --drive.tpi=135"),
("ibm", "", "--1200 --drive.tpi=96"),
("ibm", "", "--1232 --drive.tpi=96"),
("ibm", "", "--1440 --drive.tpi=135"),
("ibm", "", "--1680 --drive.tpi=135"),
("ibm", "", "--180 --drive.tpi=96"),
("ibm", "", "--160 --drive.tpi=96"),
("ibm", "", "--320 --drive.tpi=96"),
("ibm", "", "--360 --drive.tpi=96"),
("ibm", "", "--720_96 --drive.tpi=96"),
("ibm", "", "--720_135 --drive.tpi=135"),
("mac", "scripts/mac400_test.textpb", "--400 --drive.tpi=135"),
("mac", "scripts/mac800_test.textpb", "--800 --drive.tpi=135"),
("n88basic", "", "--drive.tpi=96"),
("rx50", "", "--drive.tpi=96"),
("tids990", "", "--drive.tpi=48"),
("victor9k", "", "--612 --drive.tpi=96"),
("victor9k", "", "--1224 --drive.tpi=96"),
("commodore", "", "--800"),
("commodore", "", "--1620"),
("hplif", "", "--264"),
("hplif", "", "--608"),
("hplif", "", "--616"),
("hplif", "", "--770"),
("ibm", "", "--1200"),
("ibm", "", "--1232"),
("ibm", "", "--1440"),
("ibm", "", "--1680"),
("ibm", "", "--180 40track_drive"),
("ibm", "", "--160 40track_drive"),
("ibm", "", "--320 40track_drive"),
("ibm", "", "--360 40track_drive"),
("ibm", "", "--720_96"),
("ibm", "", "--720_135"),
("mac", "scripts/mac400_test.textpb", "--400"),
("mac", "scripts/mac800_test.textpb", "--800"),
("n88basic", "", ""),
("rx50", "", ""),
("tids990", "", ""),
("victor9k", "", "--612"),
("victor9k", "", "--1224"),
]
for c in corpus:
@@ -285,11 +285,11 @@ else:
+ c[0]
+ " "
+ format
+ " {ins[0]} "
+ " {ins[0]} '"
+ c[1]
+ " "
+ "' '"
+ c[2]
+ ">/dev/null"
+ "' $(dir {outs[0]}) > /dev/null"
],
label="CORPUSTEST",
)

View File

@@ -19,7 +19,7 @@ proto(
"./usb/usb.proto",
"./vfs/vfs.proto",
],
deps=[".+common_proto"],
deps=[".+common_proto", "+fl2_proto"],
)
protocc(name="config_proto_lib", srcs=[".+config_proto", "arch+arch_proto"])

View File

@@ -172,7 +172,6 @@ ConfigProto* Config::combined()
/* First apply any standalone options. */
std::set<std::string> options = _appliedOptions;
std::set<const OptionPrerequisiteProto*> prereqs;
for (const auto& option : _baseConfig.option())
{
if (options.find(option.name()) != options.end())

View File

@@ -52,7 +52,8 @@ class InapplicableValueException : public ErrorException
public:
InapplicableValueException():
ErrorException("selected format cannot be used here")
{}
{
}
};
struct FluxConstructor

View File

@@ -1,8 +1,9 @@
syntax = "proto2";
import "lib/common.proto";
import "lib/fl2.proto";
// Next: 17
// Next: 15
message DriveProto
{
optional int32 drive = 1
@@ -11,32 +12,30 @@ message DriveProto
[ default = INDEXMODE_DRIVE, (help) = "index pulse source" ];
optional int32 hard_sector_count = 3
[ default = 0, (help) = "number of hard sectors on disk" ];
optional double hard_sector_threshold_ns = 16
optional double hard_sector_threshold_ns = 4
[ default = 0, (help) = "index pulses longer than this interval are "
"considered sector markers; shorter indicates an true index marker" ];
optional bool high_density = 4
optional bool high_density = 5
[ default = true, (help) = "set if this is a high density disk" ];
optional bool sync_with_index = 5
optional bool sync_with_index = 6
[ default = false, (help) = "start reading at index mark" ];
optional double revolutions = 6
optional double revolutions = 7
[ default = 1.2, (help) = "number of revolutions to read" ];
optional int32 tracks = 7
optional int32 tracks = 8
[ default = 81, (help) = "Number of tracks supported by drive" ];
optional int32 heads = 8
optional int32 heads = 9
[ default = 2, (help) = "Number of heads supported by drive" ];
optional int32 head_bias = 9 [
optional int32 head_bias = 10 [
default = 0,
(help) = "Bias to apply to the head position (in tracks)"
];
optional int32 group_offset = 14 [
optional int32 group_offset = 11 [
default = 0,
(help) = "When writing groups, erase all tracks except this one in each group"
];
optional int32 head_width = 10
[ default = 1, (help) = "Width of the head (in tracks)" ];
optional float tpi = 11 [ default = 0, (help) = "TPI of drive; 0 disables all track mapping" ];
optional double rotational_period_ms = 12
optional DriveType drive_type = 12 [ default = DRIVETYPE_UNKNOWN, (help) = "Type of drive" ];
optional double rotational_period_ms = 13
[ default = 0, (help) = "Rotational period of the drive in milliseconds (0 to autodetect)"];
enum ErrorBehaviour {
@@ -45,7 +44,7 @@ message DriveProto
RECALIBRATE = 2;
}
optional ErrorBehaviour error_behaviour = 15
optional ErrorBehaviour error_behaviour = 14
[ default = JIGGLE, (help) = "what to do when an error occurs during reads" ];
}

View File

@@ -15,11 +15,28 @@ message TrackFluxProto {
repeated bytes flux = 3;
}
enum DriveType {
DRIVETYPE_UNKNOWN = 0;
DRIVETYPE_40TRACK = 1;
DRIVETYPE_80TRACK = 2;
DRIVETYPE_APPLE2 = 3;
}
enum FormatType {
FORMATTYPE_UNKNOWN = 0;
FORMATTYPE_40TRACK = 1;
FORMATTYPE_80TRACK = 2;
}
// NEXT: 8
message FluxFileProto {
optional int32 magic = 1;
optional FluxFileVersion version = 2;
repeated TrackFluxProto track = 3;
optional double rotational_period_ms = 4;
optional int32 tpi = 5;
optional DriveType drive_type = 6 [default = DRIVETYPE_UNKNOWN];
optional FormatType format_type = 7 [default = FORMATTYPE_UNKNOWN];
reserved 5;
}

View File

@@ -45,7 +45,8 @@ public:
proto.set_rotational_period_ms(
globalConfig()->drive().rotational_period_ms());
proto.set_tpi(globalConfig()->drive().tpi());
proto.set_drive_type(globalConfig()->drive().drive_type());
proto.set_format_type(globalConfig()->layout().format_type());
saveFl2File(_filename, proto);
}

View File

@@ -55,7 +55,7 @@ public:
_fileheader.start_track = strackno(minTrack, minSide);
_fileheader.end_track = strackno(maxTrack, maxSide);
_fileheader.flags = SCP_FLAG_INDEXED;
if (globalConfig()->drive().tpi() != 48)
if (globalConfig()->drive().drive_type() != DRIVETYPE_40TRACK)
_fileheader.flags |= SCP_FLAG_96TPI;
_fileheader.cell_width = 0;
if ((minSide == 0) && (maxSide == 0))

View File

@@ -80,13 +80,14 @@ public:
/* 5.25" with quarter stepping. */
_extraConfig.mutable_drive()->set_tracks(160);
_extraConfig.mutable_drive()->set_heads(1);
_extraConfig.mutable_drive()->set_head_width(4);
_extraConfig.mutable_drive()->set_tpi(48 * 4);
_extraConfig.mutable_drive()->set_drive_type(
DRIVETYPE_APPLE2);
}
else
{
/* 3.5". */
_extraConfig.mutable_drive()->set_tpi(135);
_extraConfig.mutable_drive()->set_drive_type(
DRIVETYPE_80TRACK);
}
Bytes stream = findChunk("STRM");

View File

@@ -39,8 +39,8 @@ public:
_extraConfig.mutable_drive()->set_rotational_period_ms(
_proto.rotational_period_ms());
if (_proto.has_tpi())
_extraConfig.mutable_drive()->set_tpi(_proto.tpi());
if (_proto.has_drive_type())
_extraConfig.mutable_drive()->set_drive_type(_proto.drive_type());
}
public:

View File

@@ -42,8 +42,9 @@ public:
(_header.file_id[2] != 'P'))
error("input not a SCP file");
int tpi = (_header.flags & SCP_FLAG_96TPI) ? 96 : 48;
_extraConfig.mutable_drive()->set_tpi(tpi);
_extraConfig.mutable_drive()->set_drive_type(
(_header.flags & SCP_FLAG_96TPI) ? DRIVETYPE_80TRACK
: DRIVETYPE_40TRACK);
_resolution = 25 * (_header.resolution + 1);
int startSide = (_header.heads == 2) ? 1 : 0;

View File

@@ -61,13 +61,13 @@ public:
if (mediaFlag == 0x20)
{
_extraConfig.mutable_drive()->set_high_density(true);
_extraConfig.mutable_layout()->set_tpi(96);
_extraConfig.mutable_layout()->set_format_type(FORMATTYPE_80TRACK);
}
else
{
clockRate = 300;
_extraConfig.mutable_drive()->set_high_density(false);
_extraConfig.mutable_layout()->set_tpi(48);
_extraConfig.mutable_layout()->set_format_type(FORMATTYPE_40TRACK);
}
auto layout = _extraConfig.mutable_layout();

View File

@@ -58,7 +58,7 @@ public:
log("NFD: HD 1.2MB mode");
log("NFD: forcing hign density mode");
_extraConfig.mutable_drive()->set_high_density(true);
_extraConfig.mutable_layout()->set_tpi(96);
_extraConfig.mutable_layout()->set_format_type(FORMATTYPE_80TRACK);
std::unique_ptr<Image> image(new Image);
for (int track = 0; track < 163; track++)

View File

@@ -2,34 +2,49 @@
#include "lib/layout.h"
#include "lib/proto.h"
#include "lib/logger.h"
bool approximatelyEqual(float a, float b, float epsilon)
{
return fabs(a - b) <= ((fabs(a) < fabs(b) ? fabs(b) : fabs(a)) * epsilon);
}
#include "lib/fl2.h"
static unsigned getTrackStep()
{
if (globalConfig()->layout().tpi() == 0)
error("no layout TPI set");
if (globalConfig()->drive().tpi() == 0)
return 1;
auto format_type = globalConfig()->layout().format_type();
auto drive_type = globalConfig()->drive().drive_type();
if (globalConfig()->layout().tpi() == 0.0)
error("layout TPI is zero; this shouldn't happen?");
switch (format_type)
{
case FORMATTYPE_40TRACK:
switch (drive_type)
{
case DRIVETYPE_40TRACK:
return 1;
float trackStepFactor =
globalConfig()->drive().tpi() / globalConfig()->layout().tpi();
case DRIVETYPE_80TRACK:
return 2;
if (!approximatelyEqual(trackStepFactor, round(trackStepFactor), 0.001))
error(
"this drive can't handle this image, because the drive TPI doesn't "
"divide neatly into the layout TPI");
if (trackStepFactor < 0.999)
error(
"this drive can't handle this image, because the head is too big");
case DRIVETYPE_APPLE2:
return 4;
}
return round(trackStepFactor);
case FORMATTYPE_80TRACK:
switch (drive_type)
{
case DRIVETYPE_40TRACK:
error(
"you can't write an 80 track image to a 40 track "
"drive");
case DRIVETYPE_80TRACK:
return 1;
case DRIVETYPE_APPLE2:
error(
"you can't write an 80 track image to an Apple II "
"drive");
}
}
warning(
"don't know the drive and format types; performing 1:1 track mapping");
return 1;
}
unsigned Layout::remapTrackPhysicalToLogical(unsigned ptrack)
@@ -237,3 +252,15 @@ std::shared_ptr<const TrackInfo> Layout::getLayoutOfTrackPhysical(
return getLayoutOfTrack(remapTrackPhysicalToLogical(physicalTrack),
remapSidePhysicalToLogical(physicalSide));
}
int Layout::getHeadWidth()
{
switch (globalConfig()->drive().drive_type())
{
case DRIVETYPE_APPLE2:
return 4;
default:
return 1;
}
}

View File

@@ -52,6 +52,9 @@ public:
/* Expand a SectorList into the actual sector IDs. */
static std::vector<unsigned> expandSectorList(
const SectorListProto& sectorsProto);
/* Return the head width of the current drive. */
static int getHeadWidth();
};
class TrackInfo

View File

@@ -1,6 +1,7 @@
syntax = "proto2";
import "lib/common.proto";
import "lib/fl2.proto";
message SectorListProto
{
@@ -57,5 +58,6 @@ message LayoutProto
[ default = CHS, (help) = "the order of sectors in the filesystem" ];
optional bool swap_sides = 5
[ default = false, (help) = "the sides are inverted on this disk" ];
optional float tpi = 6 [ (help) = "TPI of image; if 0, use TPI of drive" ];
optional FormatType format_type = 6
[ default = FORMATTYPE_UNKNOWN, (help) = "Format type of image" ];
}

View File

@@ -288,8 +288,7 @@ std::string getProtoFieldValue(ProtoField& protoField)
case google::protobuf::FieldDescriptor::TYPE_ENUM:
{
const auto* enumvalue = reflection->GetEnum(*message, field);
const auto* enumfield = field->enum_type();
return enumfield->name();
return enumvalue->name();
}
case google::protobuf::FieldDescriptor::TYPE_MESSAGE:

View File

@@ -218,7 +218,7 @@ ReadResult readGroup(FluxSourceIteratorHolder& fluxSourceIteratorHolder,
ReadResult result = BAD_AND_CAN_NOT_RETRY;
for (unsigned offset = 0; offset < trackInfo->groupSize;
offset += globalConfig()->drive().head_width())
offset += Layout::getHeadWidth())
{
auto& fluxSourceIterator = fluxSourceIteratorHolder.getIterator(
trackInfo->physicalTrack + offset, trackInfo->physicalSide);
@@ -274,7 +274,7 @@ void writeTracks(FluxSink& fluxSink,
for (;;)
{
for (int offset = 0; offset < trackInfo->groupSize;
offset += globalConfig()->drive().head_width())
offset += Layout::getHeadWidth())
{
unsigned physicalTrack = trackInfo->physicalTrack + offset;

View File

@@ -76,7 +76,7 @@ public:
"your FluxEngine firmware is at version {} but the client is "
"for version {}; please upgrade",
version,
(int) FLUXENGINE_PROTOCOL_VERSION);
(int)FLUXENGINE_PROTOCOL_VERSION);
}
private:

View File

@@ -214,7 +214,7 @@ private:
_directoryBlock = rbr.read_be32();
rbr.skip(4);
_directorySize = rbr.read_be32();
rbr.skip(4);
rbr.skip(4);
unsigned tracks = rbr.read_be32();
unsigned heads = rbr.read_be32();
unsigned sectors = rbr.read_be32();

View File

@@ -69,10 +69,10 @@ private:
void putBlock(RolandFsFilesystem* fs, uint8_t offset, uint8_t block)
{
if (blocks.size() <= offset)
blocks.resize(offset+1);
blocks.resize(offset + 1);
blocks[offset] = block;
length = (offset+1) * fs->_blockSectors * fs->_sectorSize;
length = (offset + 1) * fs->_blockSectors * fs->_sectorSize;
attributes[Filesystem::LENGTH] = std::to_string(length);
}
@@ -84,7 +84,7 @@ private:
if (!blocknumber)
break;
putBlock(fs, offset+i, blocknumber);
putBlock(fs, offset + i, blocknumber);
}
}
@@ -336,7 +336,7 @@ private:
else
de = it->second;
de->putBlocks(this, extent*16, direntBytes);
de->putBlocks(this, extent * 16, direntBytes);
}
}

View File

@@ -12,7 +12,7 @@ class Encoder;
class SectorInterface
{
public:
virtual ~SectorInterface() {}
virtual ~SectorInterface() {}
public:
virtual std::shared_ptr<const Sector> get(

View File

@@ -281,9 +281,10 @@ Bytes Filesystem::getSector(unsigned track, unsigned side, unsigned sector)
Bytes Filesystem::getLogicalSector(uint32_t number, uint32_t count)
{
if ((number + count) > _locations.size())
throw BadFilesystemException(
fmt::format("invalid filesystem: sector {} is out of bounds ({} maximum)",
number + count - 1, _locations.size()));
throw BadFilesystemException(fmt::format(
"invalid filesystem: sector {} is out of bounds ({} maximum)",
number + count - 1,
_locations.size()));
Bytes data;
ByteWriter bw(data);

View File

@@ -1,22 +1,21 @@
#!/bin/sh
set -e
format=$1
tmp=/tmp/$$-$format
srcfile=$tmp.src.img
fluxfile=$tmp.$2
destfile=$tmp.dest.img
fluxengine=$3
shift
shift
shift
format="$1"
ext="$2"
fluxengine="$3"
script="$4"
flags="$5"
dir="$6"
trap "rm -f $srcfile $fluxfile $destfile" EXIT
srcfile=$dir.$format.src.img
fluxfile=$dir.$format.$ext
destfile=$dir.$format.dest.img
dd if=/dev/urandom of=$srcfile bs=1048576 count=2 2>&1
$fluxengine write $format -i $srcfile -d $fluxfile --drive.rotational_period_ms=200 "$@"
$fluxengine read $format -s $fluxfile -o $destfile --drive.rotational_period_ms=200 "$@"
$fluxengine write $format -i $srcfile -d $fluxfile --drive.rotational_period_ms=200 $flags
$fluxengine read $format -s $fluxfile -o $destfile --drive.rotational_period_ms=200 $flags
if [ ! -s $destfile ]; then
echo "Zero length output file!" >&2
exit 1

View File

@@ -246,8 +246,7 @@ static void draw_x_graticules(Agg2D& painter,
int mainAnalyseDriveResponse(int argc, const char* argv[])
{
globalConfig().overrides()->mutable_flux_source()->set_type(
FLUXTYPE_DRIVE);
globalConfig().overrides()->mutable_flux_source()->set_type(FLUXTYPE_DRIVE);
flags.parseFlagsWithConfigFiles(argc, argv, {});
if (globalConfig()->flux_sink().type() != FLUXTYPE_DRIVE)

View File

@@ -131,8 +131,7 @@ static nanoseconds_t guessClock(const Fluxmap& fluxmap)
int mainInspect(int argc, const char* argv[])
{
globalConfig().overrides()->mutable_flux_source()->set_type(
FLUXTYPE_DRIVE);
globalConfig().overrides()->mutable_flux_source()->set_type(FLUXTYPE_DRIVE);
flags.parseFlagsWithConfigFiles(argc, argv, {});
auto& fluxSource = globalConfig().getFluxSource();

View File

@@ -57,8 +57,8 @@ int mainLs(int argc, const char* argv[])
quote(dirent->filename),
maxlen + 2,
dirent->length,
dirent->mode,
dirent->attributes[Filesystem::CTIME]);
dirent->mode,
dirent->attributes[Filesystem::CTIME]);
total += dirent->length;
}
fmt::print("({} files, {} bytes)\n", files.size(), total);

View File

@@ -53,8 +53,7 @@ int mainRawRead(int argc, const char* argv[])
if (argc == 1)
showProfiles("rawread", formats);
globalConfig().overrides()->mutable_flux_source()->set_type(
FLUXTYPE_DRIVE);
globalConfig().overrides()->mutable_flux_source()->set_type(FLUXTYPE_DRIVE);
flags.parseFlagsWithConfigFiles(argc, argv, formats);
if (globalConfig()->flux_sink().type() == FLUXTYPE_DRIVE)

View File

@@ -59,8 +59,7 @@ int mainRawWrite(int argc, const char* argv[])
if (argc == 1)
showProfiles("rawwrite", formats);
globalConfig().overrides()->mutable_flux_sink()->set_type(
FLUXTYPE_DRIVE);
globalConfig().overrides()->mutable_flux_sink()->set_type(FLUXTYPE_DRIVE);
flags.parseFlagsWithConfigFiles(argc, argv, formats);
if (globalConfig()->flux_source().type() == FLUXTYPE_DRIVE)

View File

@@ -16,8 +16,7 @@ fluxengine read ibm --180 40track_drive
drive {
tracks: 40
head_width: 1
tpi: 48
drive_type: DRIVETYPE_40TRACK
}

View File

@@ -42,7 +42,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -62,7 +62,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 1
layoutdata {
@@ -82,7 +82,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -102,7 +102,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -123,7 +123,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -78,7 +78,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
}
}
@@ -91,7 +91,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
}
}

View File

@@ -51,7 +51,7 @@ decoder {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 1
layoutdata {

View File

@@ -32,7 +32,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -40,7 +40,7 @@ image_writer {
}
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -82,7 +82,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
}
}
@@ -94,7 +94,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
}
}

View File

@@ -73,7 +73,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 35
sides: 1
layoutdata {
@@ -93,7 +93,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
order: HCS

View File

@@ -24,8 +24,7 @@ usb {
drive {
tracks: 160
heads: 1
head_width: 4
tpi: 192
drive_type: DRIVETYPE_APPLE2
}

View File

@@ -51,7 +51,7 @@ decoder {
}
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
}
option_group {

View File

@@ -28,7 +28,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -141,7 +141,7 @@ option_group {
config {
layout {
tpi: 67.5
format_type: FORMATTYPE_40TRACK
tracks: 39
sides: 1
layoutdata {
@@ -162,7 +162,7 @@ option_group {
drive {
head_bias: 0
group_offset: 1
group_offset: 0
}
filesystem {
@@ -178,7 +178,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 1
layoutdata {

View File

@@ -76,7 +76,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 35
sides: 1
layoutdata {
@@ -132,7 +132,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -188,7 +188,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
swap_sides: true
@@ -230,7 +230,7 @@ option_group {
config {
layout {
tpi: 100
format_type: FORMATTYPE_80TRACK
sides: 2
tracks: 77
layoutdata {
@@ -282,7 +282,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 81
sides: 2
swap_sides: true

View File

@@ -41,7 +41,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 2
layoutdata {

View File

@@ -15,7 +15,7 @@ image_writer {
}
layout {
tpi: 67.5
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 2
layoutdata {

View File

@@ -50,7 +50,7 @@ decoder {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 1
layoutdata {

View File

@@ -51,7 +51,7 @@ decoder {
}
layout {
tpi: 67.5
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {

View File

@@ -46,7 +46,7 @@ filesystem {
}
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
}
option_group {

View File

@@ -110,7 +110,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
}
}
}
@@ -121,7 +121,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -150,7 +150,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -179,7 +179,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 2
layoutdata {
@@ -208,7 +208,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 2
layoutdata {
@@ -237,7 +237,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -266,7 +266,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -295,7 +295,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -324,7 +324,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 2
layoutdata {
@@ -353,7 +353,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {
@@ -382,7 +382,7 @@ option_group {
config {
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -15,7 +15,7 @@ image_writer {
}
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 35
sides: 2
layoutdata {

View File

@@ -70,7 +70,7 @@ image_writer {
}
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -142,7 +142,7 @@ option_group {
config {
layout {
tpi: 50
format_type: FORMATTYPE_40TRACK
tracks: 35
sides: 1
}
@@ -156,7 +156,7 @@ option_group {
config {
layout {
tpi: 50
format_type: FORMATTYPE_40TRACK
tracks: 35
sides: 2
}
@@ -169,7 +169,7 @@ option_group {
config {
layout {
tpi: 100
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 1
}
@@ -182,7 +182,7 @@ option_group {
config {
layout {
tpi: 100
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 2
}

View File

@@ -41,7 +41,7 @@ image_writer {
layout {
tracks: 70
sides: 1
tpi: 135
format_type: FORMATTYPE_80TRACK
layoutdata {
sector_size: 512
physical {

View File

@@ -83,7 +83,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
}
@@ -96,7 +96,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 2
}
@@ -109,7 +109,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 1
}
@@ -123,7 +123,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
}

View File

@@ -28,7 +28,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 2
layoutdata {

View File

@@ -44,7 +44,7 @@ image_writer {
}
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
layoutdata {
physical {
start_sector: 0

View File

@@ -35,7 +35,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
order: HCS

View File

@@ -46,7 +46,7 @@ image_writer {
}
layout {
tpi: 135
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 1
layoutdata {

View File

@@ -25,7 +25,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 1
layoutdata {

View File

@@ -33,7 +33,7 @@ image_writer {
}
layout {
tpi: 100
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 1
layoutdata {

View File

@@ -40,7 +40,7 @@ image_writer {
}
layout {
tpi: 48
format_type: FORMATTYPE_80TRACK
tracks: 77
sides: 2
layoutdata {

View File

@@ -27,7 +27,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -59,7 +59,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 1
layoutdata {
@@ -91,7 +91,7 @@ option_group {
config {
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 40
sides: 2
layoutdata {
@@ -124,7 +124,7 @@ option_group {
config {
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -59,7 +59,7 @@ image_writer {
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 80
sides: 2
layoutdata {

View File

@@ -45,7 +45,7 @@ decoder {
}
layout {
tpi: 48
format_type: FORMATTYPE_40TRACK
tracks: 77
sides: 1
layoutdata {

View File

@@ -244,12 +244,12 @@ private:
uint32_t usedBlocks = std::stoul(
metadata.at(Filesystem::USED_BLOCKS));
if (!totalBlocks)
throw std::out_of_range("no disk usage data");
if (!totalBlocks)
throw std::out_of_range("no disk usage data");
diskSpaceGauge->Enable();
diskSpaceGauge->SetRange(totalBlocks);
diskSpaceGauge->SetValue(usedBlocks);
diskSpaceGauge->Enable();
diskSpaceGauge->SetRange(totalBlocks);
diskSpaceGauge->SetValue(usedBlocks);
}
catch (const std::out_of_range& e)
{

View File

@@ -1,6 +0,0 @@
comment: '3.5" 40 track 67.5tpi'
drive {
tpi: 67.5
}

View File

@@ -1,6 +0,0 @@
comment: '3.5" 80 track 135tpi'
drive {
tpi: 135
}

View File

@@ -1,6 +0,0 @@
comment: '5.25" 40 track 48tpi'
drive {
tpi: 48
}

View File

@@ -1,6 +0,0 @@
comment: '5.25" 40 track 50tpi (Micropolis Mod-I)'
drive {
tpi: 50
}

View File

@@ -1,6 +0,0 @@
comment: '5.25" 80 track 96tpi'
drive {
tpi: 96
}

View File

@@ -1,6 +0,0 @@
comment: '5.25" 80 track 100tpi (Micropolis Mod-II)'
drive {
tpi: 100
}

View File

@@ -1,6 +0,0 @@
comment: '8" 38 track 32tpi'
drive {
tpi: 32
}

View File

@@ -1,6 +0,0 @@
comment: '8" 77 track 48tpi'
drive {
tpi: 48
}

View File

@@ -9,7 +9,6 @@ usb {
drive {
tracks: 160
heads: 1
head_width: 4
tpi: 192
drive_type: DRIVETYPE_APPLE2
}

View File

@@ -3,14 +3,8 @@ from build.c import cxxlibrary
from scripts.build import protoencode
drivetypes = [
"35_40",
"35_80",
"525_40M",
"525_40",
"525_80M",
"525_80",
"8_38",
"8_77",
"40track",
"80track",
"apple2",
]

View File

File diff suppressed because it is too large Load Diff

View File

@@ -239,12 +239,12 @@ public:
{
if (_selectedFluxFormat)
{
if (_selectedFluxFormat->sink)
_selectedFluxFormat->sink(_selectedFluxFilename,
globalConfig().overrides()->mutable_flux_sink());
if (_selectedFluxFormat->source)
_selectedFluxFormat->source(_selectedFluxFilename,
globalConfig().overrides()->mutable_flux_source());
if (_selectedFluxFormat->sink)
_selectedFluxFormat->sink(_selectedFluxFilename,
globalConfig().overrides()->mutable_flux_sink());
if (_selectedFluxFormat->source)
_selectedFluxFormat->source(_selectedFluxFilename,
globalConfig().overrides()->mutable_flux_source());
}
break;
}

View File

File diff suppressed because it is too large Load Diff

View File

@@ -53,19 +53,19 @@ private:
bool FluxEngineApp::OnInit()
{
try
{
wxImage::AddHandler(new wxPNGHandler());
Bind(EXEC_EVENT_TYPE, &FluxEngineApp::OnExec, this);
_mainWindow = CreateMainWindow();
_mainWindow->Show(true);
return true;
}
catch (const ErrorException* e)
{
fmt::print(stderr, "Exception on startup: {}\n", e->message);
exit(1);
}
try
{
wxImage::AddHandler(new wxPNGHandler());
Bind(EXEC_EVENT_TYPE, &FluxEngineApp::OnExec, this);
_mainWindow = CreateMainWindow();
_mainWindow->Show(true);
return true;
}
catch (const ErrorException* e)
{
fmt::print(stderr, "Exception on startup: {}\n", e->message);
exit(1);
}
}
wxThread::ExitCode FluxEngineApp::Entry()

View File

@@ -83,8 +83,8 @@ static void validateConfigWithOptions(std::string baseConfigName,
{
/* All configs must have a tpi. */
if (!config.layout().has_tpi())
configError("{}{}: no layout.tpi set", baseConfigName, options);
if (!config.layout().has_format_type())
configError("{}{}: no layout.format_type set", baseConfigName, options);
}
static void validateToplevelConfig(std::string name)

View File

@@ -119,11 +119,11 @@ int main(void)
{
const std::string text = R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 10
sides: 1
layoutdata {

View File

@@ -22,11 +22,11 @@ static void test_physical_sectors()
globalConfig().clear();
globalConfig().readBaseConfig(R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 2
layoutdata {
@@ -55,11 +55,11 @@ static void test_logical_sectors()
globalConfig().clear();
globalConfig().readBaseConfig(R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 2
layoutdata {
@@ -94,11 +94,11 @@ static void test_both_sectors()
globalConfig().clear();
globalConfig().readBaseConfig(R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 2
layoutdata {
@@ -133,11 +133,11 @@ static void test_skew()
globalConfig().clear();
globalConfig().readBaseConfig(R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
layout {
tpi: 96
format_type: FORMATTYPE_80TRACK
tracks: 78
sides: 2
layoutdata {

View File

@@ -23,15 +23,15 @@ static void test_option_validity()
globalConfig().clear();
globalConfig().readBaseConfig(R"M(
drive {
tpi: 96
drive_type: DRIVETYPE_80TRACK
}
option {
name: "option1"
prerequisite: {
key: "drive.tpi"
value: "96"
key: "drive.drive_type"
value: "DRIVETYPE_80TRACK"
}
}
@@ -39,8 +39,8 @@ static void test_option_validity()
name: "option2"
prerequisite: {
key: "drive.tpi"
value: "95"
key: "drive.drive_type"
value: "DRIVETYPE_40TRACK"
}
}
@@ -48,8 +48,8 @@ static void test_option_validity()
name: "option3"
prerequisite: {
key: "drive.tpi"
value: ["0", "96"]
key: "drive.drive_type"
value: ["DRIVETYPE_UNKNOWN", "DRIVETYPE_80TRACK"]
}
}
)M");