1 using System;
  2 using System.Collections;
  3 using System.IO;
  4 
  5 namespace cmsx.kernel
  6 {
  7     public const uint DRIVE_UNKNOWN = 0u;
  8     public const uint DRIVE_NO_ROOT_DIR = 1u;
  9     public const uint DRIVE_REMOVABLE = 2u;
 10     public const uint DRIVE_FIXED = 3u;
 11     public const uint DRIVE_REMOTE = 4u;
 12     public const uint DRIVE_CDROM = 5u;
 13     public const uint DRIVE_RAMDISK = 6u;
 14 
 15     public class MountTable
 16     {
 17         static MountTable() : instance(new MountTable())
 18         {
 19         }
 20         public static nothrow MountTable& Instance()
 21         {
 22             return *instance;
 23         }
 24         public FileSystem* GetFileSystem(int fsNumber) const
 25         {
 26             int fileSystemIndex = GetFileSystemIndex(fsNumber);
 27             if (fileSystemIndex < 0 || fileSystemIndex >= fileSystems.Count())
 28             {
 29                 throw SystemError(EINVAL"invalid file system number");
 30             }
 31             return fileSystems[fileSystemIndex].Get();
 32         }
 33         public FileSystem* GetMountedFileSystem(const string& dirPathconst INodeKey& mountDirKey) const
 34         {
 35             for (UniquePtr<FileSystem>& fs : fileSystems)
 36             {
 37                 if (fs->HasMountDirKey(mountDirKey))
 38                 {
 39                     if (Log())
 40                     {
 41                         LogMessage("fs.mountTable""getmountedfilesystem.fs=" + fs->Name());
 42                     }
 43                     return fs.Get();
 44                 }
 45             }
 46             throw SystemError(EFAIL"file system mounted on directory '" + dirPath + "' not found");
 47         }
 48         private MountTable()
 49         {
 50         }
 51         public void Init()
 52         {
 53             if (Log())
 54             {
 55                 LogMessage("fs.mountTable""init");
 56             }
 57             string cmajorRootDir = RtGetEnvironmentVariable("CMAJOR_ROOT");
 58             if (cmajorRootDir.IsEmpty())
 59             {
 60                 throw Exception("CMAJOR_ROOT environment variable not set. Please set it to contain /path/to/cmajor directory");
 61             }
 62             string cmsxDir = Path.Combine(Path.Combine(cmajorRootDir"projects")"cmsx");
 63             fileSystems.Add(UniquePtr<FileSystem>(new RootFileSystem(0)));
 64             char[4096] logicalDrivesBuf;
 65             bool retval = OsGetLogicalDrives(&logicalDrivesBuf[0]cast<int>(logicalDrivesBuf.Length()));
 66             if (!retval)
 67             {
 68                 throw SystemError(EFAIL"could not get logical drives from system");
 69             }
 70             int fileSystemIndex = 1;
 71             string logicalDrivesStr = &logicalDrivesBuf[0];
 72             List<string> logicalDrives = logicalDrivesStr.Split(';');
 73             for (const string& drive : logicalDrives)
 74             {
 75                 uint driveType = OsGetDriveType(drive.Chars());
 76                 if (driveType == DRIVE_FIXED)
 77                 {
 78                     string hostPath = GetFullPath(drive);
 79                     string mountDirPath = "/mnt/" + ToLower(hostPath.Substring(01));
 80                     HostFileSystem* hostFileSystem = new HostFileSystem(fileSystemIndex++hostPathmountDirPath);
 81                     fileSystems.Add(UniquePtr<FileSystem>(hostFileSystem));
 82                 }
 83             }
 84             string cmajorRootHostPath = GetFullPath(cmajorRootDir);
 85             string cmajorMountDirPath = "/mnt/cmajor";
 86             HostFileSystem* cmajorHostFileSystem = new HostFileSystem(fileSystemIndex++cmajorRootHostPathcmajorMountDirPath);
 87             fileSystems.Add(UniquePtr<FileSystem>(cmajorHostFileSystem));
 88             string cmsxHostPath = GetFullPath(cmsxDir);
 89             string cmsxMountDirPath = "/mnt/cmsx";
 90             HostFileSystem* cmsxHostFileSystem = new HostFileSystem(fileSystemIndex++cmsxHostPathcmsxMountDirPath);
 91             fileSystems.Add(UniquePtr<FileSystem>(cmsxHostFileSystem));
 92             InitializeFileSystems();
 93         }
 94         public void Flush()
 95         {
 96             for (UniquePtr<FileSystem>& fs : fileSystems)
 97             {
 98                 fs->GetBlockManager()->Flush();
 99             }
100         }
101         private void InitializeFileSystems()
102         {
103             for (UniquePtr<FileSystem>& fs : fileSystems)
104             {
105                 fs->Init();
106             }
107         }
108         private static UniquePtr<MountTable> instance;
109         private List<UniquePtr<FileSystem>> fileSystems;
110     }
111 
112     public nothrow MountTable& GetMountTable()
113     {
114         return MountTable.Instance();
115     }
116 }