23 data.assign(
size, 0x4e);
28 assert(idx < data.size());
29 assert(idam.empty() || (idx > idam.back()));
39 if ((it ==
end(idam)) || (*it != i2)) {
44 if ((it !=
end(idam)) && (*it == i2)) {
51 std::optional<RawTrack::Sector> RawTrack::decodeSectorImpl(
int idx)
const
56 if (
read(idx) != 0xFE)
return {};
62 addrCrc.init({0xA1, 0xA1, 0xA1, 0xFE});
64 sector.track =
read(idx++);
65 sector.head =
read(idx++);
66 sector.sector =
read(idx++);
67 sector.sizeCode =
read(idx++);
68 byte addrCrc1 =
read(idx++);
69 byte addrCrc2 =
read(idx++);
70 sector.addrCrcErr = (256 * addrCrc1 + addrCrc2) != addrCrc.getValue();
73 sector.deleted =
false;
74 sector.dataCrcErr =
true;
76 if (!sector.addrCrcErr) {
79 for (
auto i :
xrange(43)) {
83 if (
read(idx2 + j) != 0xA1)
break;
87 byte type =
read(idx2 + 3);
88 if (type !=
one_of(0xfb, 0xf8))
continue;
91 dataCrc.init({0xA1, 0xA1, 0xA1});
95 int dataIdx = idx2 + 4;
96 unsigned sectorSize = 128 << (sector.sizeCode & 7);
98 byte dataCrc1 =
read(dataIdx + sectorSize + 0);
99 byte dataCrc2 =
read(dataIdx + sectorSize + 1);
100 bool dataCrcErr = (256 * dataCrc1 + dataCrc2) != dataCrc.getValue();
103 sector.dataIdx = dataIdx;
104 sector.deleted = type == 0xf8;
105 sector.dataCrcErr = dataCrcErr;
115 vector<Sector> result;
116 for (
const auto& i : idam) {
117 if (
auto sector = decodeSectorImpl(i);
118 sector && (sector->dataIdx != -1)) {
119 result.push_back(*sector);
125 static vector<unsigned> rotateIdam(vector<unsigned> idam,
unsigned startIdx)
137 for (
auto& i : rotateIdam(idam, startIdx)) {
138 if (
auto sector = decodeSectorImpl(i)) {
148 for (
const auto& i : idam) {
149 if (
auto sector = decodeSectorImpl(i);
151 (sector->sector == sectorNum) &&
152 (sector->dataIdx != -1)) {
161 for (
auto [i, d] :
enumerate(destination)) {
176 if (
end <= data.size()) {
179 unsigned part = unsigned(data.size()) - start;
180 crc.
update(&data[start], part);
246 if ((
read(i - 3) != 0xA1) ||
247 (
read(i - 2) != 0xA1) ||
248 (
read(i - 1) != 0xA1) ||
249 (
read(i - 0) != 0xFE))
continue;
252 if (
auto sector = decodeSectorImpl(i);
253 sector && (sector->dataIdx != -1)) {
254 int d = sector->dataIdx;
255 if ((
read(d - 4) != 0xA1) ||
256 (
read(d - 3) != 0xA1) ||
257 (
read(d - 2) != 0xA1))
continue;
265 template<
typename Archive>
268 ar.serialize(
"idam", idam);
269 auto len = unsigned(data.size());
270 if (ar.versionAtLeast(version, 2)) {
271 ar.serialize(
"trackLength", len);
273 assert(ar.isLoader());
279 ar.serialize_blob(
"data", data.data(), data.size());
283 template<
typename Archive>
286 ar.serialize(
"addrIdx",
addrIdx,