openMSX
DirAsDSK.hh
Go to the documentation of this file.
1 #ifndef DIRASDSK_HH
2 #define DIRASDSK_HH
3 
4 #include "SectorBasedDisk.hh"
5 #include "DiskImageUtils.hh"
6 #include "FileOperations.hh"
7 #include "EmuTime.hh"
8 #include "hash_map.hh"
9 #include <utility>
10 
11 namespace openmsx {
12 
13 class DiskChanger;
14 class CliComm;
15 
16 class DirAsDSK final : public SectorBasedDisk
17 {
18 public:
21 
22 public:
23  DirAsDSK(DiskChanger& diskChanger, CliComm& cliComm,
24  const Filename& hostDir, SyncMode syncMode,
25  BootSectorType bootSectorType);
26 
27  // SectorBasedDisk
28  void readSectorImpl (size_t sector, SectorBuffer& buf) override;
29  void writeSectorImpl(size_t sector, const SectorBuffer& buf) override;
30  [[nodiscard]] bool isWriteProtectedImpl() const override;
31  [[nodiscard]] bool hasChanged() const override;
32  void checkCaches() override;
33 
34 private:
35  struct DirIndex {
36  DirIndex() = default;
37  DirIndex(unsigned sector_, unsigned idx_)
38  : sector(sector_), idx(idx_) {}
39  [[nodiscard]] constexpr bool operator==(const DirIndex&) const = default;
40 
41  unsigned sector;
42  unsigned idx;
43  };
44  struct HashDirIndex {
45  auto operator()(const DirIndex& d) const {
46  std::hash<unsigned> subHasher;
47  return 31 * subHasher(d.sector)
48  + subHasher(d.idx);
49  }
50  };
51  struct MapDir {
52  std::string hostName; // path relative to 'hostDir'
53  // The following two are used to detect changes in the host
54  // file compared to the last host->virtual-disk sync.
55  time_t mtime; // Modification time of host file at the time of
56  // the last sync.
57  size_t filesize; // Host file size, normally the same as msx
58  // filesize, except when the host file was
59  // truncated.
60  };
61 
62  [[nodiscard]] SectorBuffer* fat();
63  [[nodiscard]] SectorBuffer* fat2();
64  [[nodiscard]] MSXDirEntry& msxDir(DirIndex dirIndex);
65  void writeFATSector (unsigned sector, const SectorBuffer& buf);
66  void writeDIRSector (unsigned sector, DirIndex dirDirIndex,
67  const SectorBuffer& buf);
68  void writeDataSector(unsigned sector, const SectorBuffer& buf);
69  void writeDIREntry(DirIndex dirIndex, DirIndex dirDirIndex,
70  const MSXDirEntry& newEntry);
71  void syncWithHost();
72  void checkDeletedHostFiles();
73  void deleteMSXFile(DirIndex dirIndex);
74  void deleteMSXFilesInDir(unsigned msxDirSector);
75  void freeFATChain(unsigned cluster);
76  void addNewHostFiles(const std::string& hostSubDir, unsigned msxDirSector);
77  void addNewDirectory(const std::string& hostSubDir, const std::string& hostName,
78  unsigned msxDirSector, FileOperations::Stat& fst);
79  void addNewHostFile(const std::string& hostSubDir, const std::string& hostName,
80  unsigned msxDirSector, FileOperations::Stat& fst);
81  [[nodiscard]] DirIndex fillMSXDirEntry(
82  const std::string& hostSubDir, const std::string& hostName,
83  unsigned msxDirSector);
84  [[nodiscard]] DirIndex getFreeDirEntry(unsigned msxDirSector);
85  [[nodiscard]] DirIndex findHostFileInDSK(std::string_view hostName);
86  [[nodiscard]] bool checkFileUsedInDSK(std::string_view hostName);
87  [[nodiscard]] unsigned nextMsxDirSector(unsigned sector);
88  [[nodiscard]] bool checkMSXFileExists(const std::string& msxfilename,
89  unsigned msxDirSector);
90  void checkModifiedHostFiles();
91  void setMSXTimeStamp(DirIndex dirIndex, FileOperations::Stat& fst);
92  void importHostFile(DirIndex dirIndex, FileOperations::Stat& fst);
93  void exportToHost(DirIndex dirIndex, DirIndex dirDirIndex);
94  void exportToHostDir (DirIndex dirIndex, const std::string& hostName);
95  void exportToHostFile(DirIndex dirIndex, const std::string& hostName);
96  [[nodiscard]] unsigned findNextFreeCluster(unsigned cluster);
97  [[nodiscard]] unsigned findFirstFreeCluster();
98  [[nodiscard]] unsigned getFreeCluster();
99  [[nodiscard]] unsigned readFAT(unsigned cluster);
100  void writeFAT12(unsigned cluster, unsigned val);
101  void exportFileFromFATChange(unsigned cluster, SectorBuffer* oldFAT);
102  std::pair<unsigned, unsigned> getChainStart(unsigned cluster);
103  [[nodiscard]] bool isDirSector(unsigned sector, DirIndex& dirDirIndex);
104  bool getDirEntryForCluster(unsigned cluster,
105  DirIndex& dirIndex, DirIndex& dirDirIndex);
106  [[nodiscard]] DirIndex getDirEntryForCluster(unsigned cluster);
107  void unmapHostFiles(unsigned msxDirSector);
108  template<typename FUNC> bool scanMsxDirs(
109  FUNC func, unsigned msxDirSector);
110  friend struct NullScanner;
111  friend struct DirScanner;
112  friend struct IsDirSector;
113  friend struct DirEntryForCluster;
114  friend struct UnmapHostFiles;
115 
116  // internal helper functions
117  [[nodiscard]] unsigned readFATHelper(const SectorBuffer* fat, unsigned cluster) const;
118  void writeFATHelper(SectorBuffer* fat, unsigned cluster, unsigned val) const;
119  [[nodiscard]] unsigned clusterToSector(unsigned cluster) const;
120  [[nodiscard]] std::pair<unsigned, unsigned> sectorToClusterOffset(unsigned sector) const;
121  [[nodiscard]] unsigned sectorToCluster(unsigned sector) const;
122 
123 private:
124  DiskChanger& diskChanger; // used to query time / report disk change
125  CliComm& cliComm; // TODO don't use CliComm to report errors/warnings
126  const std::string hostDir;
127  const SyncMode syncMode;
128 
129  EmuTime lastAccess; // last time there was a sector read/write
130 
131  // For each directory entry that has a mapped host file/directory we
132  // store the name, last modification time and size of the corresponding
133  // host file/dir.
135  MapDirs mapDirs;
136 
137  // format parameters which depend on single/double sided
138  // varying root parameters
139  const unsigned nofSectors;
140  const unsigned nofSectorsPerFat;
141  // parameters that depend on these and thus also vary
142  const unsigned firstSector2ndFAT;
143  const unsigned firstDirSector;
144  const unsigned firstDataSector;
145  const unsigned maxCluster; // First cluster number that can NOT be used anymore.
146 
147  // Storage for the whole virtual disk.
148  std::vector<SectorBuffer> sectors;
149 };
150 
151 } // namespace openmsx
152 
153 #endif
void writeSectorImpl(size_t sector, const SectorBuffer &buf) override
Definition: DirAsDSK.cc:891
bool isWriteProtectedImpl() const override
Definition: DirAsDSK.cc:326
DirAsDSK(DiskChanger &diskChanger, CliComm &cliComm, const Filename &hostDir, SyncMode syncMode, BootSectorType bootSectorType)
Definition: DirAsDSK.cc:259
void checkCaches() override
Definition: DirAsDSK.cc:341
void readSectorImpl(size_t sector, SectorBuffer &buf) override
Definition: DirAsDSK.cc:360
bool hasChanged() const override
Has the content of this disk changed, by some other means than the MSX writing to the disk.
Definition: DirAsDSK.cc:331
This class represents a filename.
Definition: Filename.hh:18
Abstract class for disk images that only represent the logical sector information (so not the raw tra...
This file implemented 3 utility functions:
Definition: Autofire.cc:9
bool operator==(const Event &x, const Event &y)
Definition: Event.cc:11