Skip to content

Commit 06a3af2

Browse files
committed
Add filesystem sector offsets to the disk layout structure.
1 parent 0558d95 commit 06a3af2

File tree

5 files changed

+152
-22
lines changed

5 files changed

+152
-22
lines changed

lib/algorithms/readerwriter.cc

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -238,8 +238,9 @@ static std::set<std::shared_ptr<const Sector>> collectSectors(
238238

239239
for (const auto& sector : track_sectors)
240240
{
241-
key_t sectorid = {
242-
sector->logicalCylinder, sector->logicalHead, sector->logicalSector};
241+
key_t sectorid = {sector->logicalCylinder,
242+
sector->logicalHead,
243+
sector->logicalSector};
243244
sectors.insert({sectorid, sector});
244245
}
245246

@@ -300,8 +301,10 @@ BadSectorsState combineRecordAndSectors(TrackFlux& trackFlux,
300301

301302
for (unsigned sectorId : trackLayout->naturalSectorOrder)
302303
{
303-
auto sector = std::make_shared<Sector>(trackLayout, LogicalLocation{
304-
trackLayout->logicalCylinder, trackLayout->logicalHead, sectorId});
304+
auto sector = std::make_shared<Sector>(trackLayout,
305+
LogicalLocation{trackLayout->logicalCylinder,
306+
trackLayout->logicalHead,
307+
sectorId});
305308

306309
sector->status = Sector::MISSING;
307310
track_sectors.insert(sector);
@@ -406,7 +409,8 @@ void writeTracks(FluxSink& fluxSink,
406409
for (int offset = 0; offset < trackInfo->groupSize;
407410
offset += Layout::getHeadWidth())
408411
{
409-
unsigned physicalCylinder = trackInfo->physicalCylinder + offset;
412+
unsigned physicalCylinder =
413+
trackInfo->physicalCylinder + offset;
410414

411415
log(BeginWriteOperationLogMessage{
412416
physicalCylinder, trackInfo->physicalHead});

lib/data/layout.cc

Lines changed: 44 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -129,47 +129,46 @@ Layout::LayoutBounds Layout::getBounds(
129129
return r;
130130
}
131131

132-
std::vector<std::pair<int, int>> Layout::getTrackOrdering(
132+
std::vector<std::pair<unsigned, unsigned>> getTrackOrdering(
133+
const ConfigProto& config,
133134
LayoutProto::Order ordering,
134-
unsigned guessedCylinders,
135-
unsigned guessedHeads)
135+
unsigned tracks,
136+
unsigned sides)
136137
{
137-
auto layout = globalConfig()->layout();
138-
int tracks = layout.has_tracks() ? layout.tracks() : guessedCylinders;
139-
int sides = layout.has_sides() ? layout.sides() : guessedHeads;
138+
auto layout = config.layout();
140139

141-
std::vector<std::pair<int, int>> trackList;
140+
std::vector<std::pair<unsigned, unsigned>> trackList;
142141
switch (ordering)
143142
{
144143
case LayoutProto::CHS:
145144
{
146-
for (int track = 0; track < tracks; track++)
145+
for (unsigned track = 0; track < tracks; track++)
147146
{
148-
for (int side = 0; side < sides; side++)
147+
for (unsigned side = 0; side < sides; side++)
149148
trackList.push_back(std::make_pair(track, side));
150149
}
151150
break;
152151
}
153152

154153
case LayoutProto::HCS:
155154
{
156-
for (int side = 0; side < sides; side++)
155+
for (unsigned side = 0; side < sides; side++)
157156
{
158-
for (int track = 0; track < tracks; track++)
157+
for (unsigned track = 0; track < tracks; track++)
159158
trackList.push_back(std::make_pair(track, side));
160159
}
161160
break;
162161
}
163162

164163
case LayoutProto::HCS_RH1:
165164
{
166-
for (int side = 0; side < sides; side++)
165+
for (unsigned side = 0; side < sides; side++)
167166
{
168167
if (side == 0)
169-
for (int track = 0; track < tracks; track++)
168+
for (unsigned track = 0; track < tracks; track++)
170169
trackList.push_back(std::make_pair(track, side));
171170
if (side == 1)
172-
for (int track = tracks; track >= 0; track--)
171+
for (unsigned track = tracks; track >= 0; track--)
173172
trackList.push_back(std::make_pair(track - 1, side));
174173
}
175174
break;
@@ -182,6 +181,18 @@ std::vector<std::pair<int, int>> Layout::getTrackOrdering(
182181
return trackList;
183182
}
184183

184+
std::vector<std::pair<unsigned, unsigned>> Layout::getTrackOrdering(
185+
LayoutProto::Order ordering,
186+
unsigned guessedCylinders,
187+
unsigned guessedHeads)
188+
{
189+
auto& layout = globalConfig()->layout();
190+
return ::getTrackOrdering(globalConfig(),
191+
ordering,
192+
layout.has_tracks() ? layout.tracks() : guessedCylinders,
193+
layout.has_sides() ? layout.sides() : guessedHeads);
194+
}
195+
185196
std::vector<unsigned> Layout::expandSectorList(
186197
const SectorListProto& sectorsProto)
187198
{
@@ -388,6 +399,7 @@ DiskLayout::DiskLayout(const ConfigProto& config)
388399

389400
auto layoutdata =
390401
getLayoutData(logicalCylinder, logicalHead, globalConfig());
402+
ltl->sectorSize = layoutdata.sector_size();
391403
ltl->diskSectorOrder =
392404
Layout::expandSectorList(layoutdata.physical());
393405
ltl->naturalSectorOrder = ltl->diskSectorOrder;
@@ -436,6 +448,24 @@ DiskLayout::DiskLayout(const ConfigProto& config)
436448
ptl->logicalTrackLayout = findOrDefault(
437449
layoutByLogicalLocation, {logicalCylinder, logicalHead});
438450
}
451+
452+
unsigned sectorOffset = 0;
453+
for (auto [logicalCylinder, logicalHead] : getTrackOrdering(config,
454+
config.layout().filesystem_track_order(),
455+
numLogicalCylinders,
456+
numLogicalHeads))
457+
{
458+
const auto& ltl =
459+
layoutByLogicalLocation[{logicalCylinder, logicalHead}];
460+
for (unsigned lid : ltl->filesystemSectorOrder)
461+
{
462+
LogicalLocation logicalLocation = {
463+
logicalCylinder, logicalHead, lid};
464+
logicalLocationsBySectorOffset[sectorOffset] = logicalLocation;
465+
sectorOffsetByLogicalLocation[logicalLocation] = sectorOffset;
466+
sectorOffset += ltl->sectorSize;
467+
}
468+
}
439469
}
440470

441471
static Layout::LayoutBounds getBounds(std::ranges::view auto keys)

lib/data/layout.h

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -47,9 +47,9 @@ class Layout
4747
};
4848
static LayoutBounds getBounds(const std::vector<CylinderHead>& locations);
4949

50-
/* Returns a series of <track, side> pairs representing the filesystem
51-
* ordering of the disk, in logical numbers. */
52-
static std::vector<std::pair<int, int>> getTrackOrdering(
50+
/* Returns a series of logical <track, side> pairs representing the
51+
* filesystem ordering of the disk, in logical numbers. */
52+
static std::vector<std::pair<unsigned, unsigned>> getTrackOrdering(
5353
LayoutProto::Order ordering,
5454
unsigned guessedCylinders = 0,
5555
unsigned guessedHeads = 0);
@@ -157,6 +157,8 @@ class DiskLayout
157157
layoutByLogicalLocation;
158158
std::vector<CylinderHeadSector> physicalLocationsInFilesystemOrder;
159159
std::vector<LogicalLocation> logicalLocationsInFilesystemOrder;
160+
std::map<unsigned, LogicalLocation> logicalLocationsBySectorOffset;
161+
std::map<LogicalLocation, unsigned> sectorOffsetByLogicalLocation;
160162

161163
public:
162164
unsigned remapCylinderPhysicalToLogical(unsigned physicalCylinder) const

lib/data/locations.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,12 @@ struct LogicalLocation
3232
}
3333
};
3434

35+
inline std::ostream& operator<<(std::ostream& stream, LogicalLocation location)
36+
{
37+
stream << (std::string)location;
38+
return stream;
39+
}
40+
3541
extern std::vector<CylinderHead> parseCylinderHeadsString(const std::string& s);
3642
extern std::string convertCylinderHeadsToString(
3743
const std::vector<CylinderHead>& chs);

tests/layout.cc

Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,24 @@
44
#include "lib/config/config.pb.h"
55
#include "lib/config/proto.h"
66
#include "lib/data/layout.h"
7+
#include "lib/data/locations.h"
78
#include "snowhouse/snowhouse.h"
89
#include <google/protobuf/text_format.h>
910
#include <regex>
1011

1112
using namespace snowhouse;
1213

14+
template <typename F, typename S>
15+
struct snowhouse::Stringizer<std::pair<F, S>>
16+
{
17+
static std::string ToString(const std::pair<F, S>& a)
18+
{
19+
std::stringstream stream;
20+
stream << '(' << a.first << ", " << a.second << ')';
21+
return stream.str();
22+
}
23+
};
24+
1325
static std::string cleanup(const std::string& s)
1426
{
1527
auto outs = std::regex_replace(s, std::regex("[ \t\n]+"), " ");
@@ -254,11 +266,87 @@ static void test_bounds()
254266
Equals(Layout::LayoutBounds{0, 3, 0, 1}));
255267
}
256268

269+
template <typename K, typename V>
270+
static std::vector<std::pair<K, V>> toVector(const std::map<K, V>& map)
271+
{
272+
return std::vector<std::pair<K, V>>(map.begin(), map.end());
273+
}
274+
275+
static void test_sectoroffsets()
276+
{
277+
globalConfig().clear();
278+
globalConfig().readBaseConfig(R"M(
279+
drive {
280+
drive_type: DRIVETYPE_80TRACK
281+
}
282+
283+
layout {
284+
format_type: FORMATTYPE_80TRACK
285+
tracks: 2
286+
sides: 2
287+
layoutdata {
288+
sector_size: 256
289+
physical {
290+
start_sector: 0
291+
count: 4
292+
}
293+
filesystem {
294+
start_sector: 0
295+
count: 4
296+
skew: 2
297+
}
298+
}
299+
}
300+
)M");
301+
302+
auto diskLayout = createDiskLayout();
303+
AssertThat(diskLayout->groupSize, Equals(1));
304+
AssertThat(diskLayout->logicalLocationsBySectorOffset,
305+
EqualsContainer(decltype(diskLayout->logicalLocationsBySectorOffset){
306+
{0, {0, 0, 0}},
307+
{256, {0, 0, 2}},
308+
{512, {0, 0, 1}},
309+
{768, {0, 0, 3}},
310+
{1024, {0, 1, 0}},
311+
{1280, {0, 1, 2}},
312+
{1536, {0, 1, 1}},
313+
{1792, {0, 1, 3}},
314+
{2048, {1, 0, 0}},
315+
{2304, {1, 0, 2}},
316+
{2560, {1, 0, 1}},
317+
{2816, {1, 0, 3}},
318+
{3072, {1, 1, 0}},
319+
{3328, {1, 1, 2}},
320+
{3584, {1, 1, 1}},
321+
{3840, {1, 1, 3}}
322+
}));
323+
AssertThat(diskLayout->sectorOffsetByLogicalLocation,
324+
EqualsContainer(decltype(diskLayout->sectorOffsetByLogicalLocation){
325+
{{0, 0, 0}, 0 },
326+
{{0, 0, 1}, 512 },
327+
{{0, 0, 2}, 256 },
328+
{{0, 0, 3}, 768 },
329+
{{0, 1, 0}, 1024},
330+
{{0, 1, 1}, 1536},
331+
{{0, 1, 2}, 1280},
332+
{{0, 1, 3}, 1792},
333+
{{1, 0, 0}, 2048},
334+
{{1, 0, 1}, 2560},
335+
{{1, 0, 2}, 2304},
336+
{{1, 0, 3}, 2816},
337+
{{1, 1, 0}, 3072},
338+
{{1, 1, 1}, 3584},
339+
{{1, 1, 2}, 3328},
340+
{{1, 1, 3}, 3840}
341+
}));
342+
}
343+
257344
int main(int argc, const char* argv[])
258345
{
259346
test_physical_sectors();
260347
test_logical_sectors();
261348
test_both_sectors();
262349
test_skew();
263350
test_bounds();
351+
test_sectoroffsets();
264352
}

0 commit comments

Comments
 (0)