Index 扉へ 首頁
人類の品種・宇宙人・系外銀河など
Read/Write Disk のソースコードです (C# & win32)
0   商湯      2026年2月5日 木 10:23
Read/Write Disk のソースコードです (C# & win32)

Download source files:
http://www.jkofsp.net/files/

<Form1.cs>

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.IO;
using System.Threading;

namespace ReadWriteDisk
{
   public partial class Form1 : Form
   {
       [DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)]
       static extern IntPtr CreateFile(string fileName, uint desiredAccess, uint shareMode, uint securityAttributes, uint creationDisposition, uint flagsAndAttributes, uint templateFile);

       [DllImport("kernel32.dll", SetLastError = true)]
       static extern int ReadFile(IntPtr hFile, byte[] lpBuffer, uint nNumberOfBytesToRead, out uint lpNumberOfBytesRead, ref OVERLAPPED lpOverlapped);

       [DllImport("kernel32.dll", SetLastError = true)]
       static extern int WriteFile(IntPtr hFile, byte[] lpBuffer, uint nNumberOfBytesToWrite, out uint lpNumberOfBytesWritten, ref OVERLAPPED lpOverlapped);

       [DllImport("kernel32.dll", SetLastError = true)]
       static extern int CloseHandle(IntPtr hObject);

       readonly IntPtr INVALID_HANDLE_VALUE = new IntPtr(-1);

       static class DESIREDACCESS
       {
           public const uint GENERIC_READ = 0x80000000;
           public const uint GENERIC_WRITE = 0x40000000;
           public const uint GENERIC_EXECUTE = 0x20000000;
           public const uint GENERIC_ALL = 0x10000000;
       }
       /// <summary>
       /// Sharing mode of the file or object
       ///</summary>
       static class SHAREMODE
       {
           public const uint FILE_SHARE_READ = 0x00000001;
           public const uint FILE_SHARE_WRITE = 0x00000002;
           public const uint FILE_SHARE_DELETE = 0x00000004;
       }
       /// <summary>
       /// Action to take on files that exist, and which action to take when files do not exist.
       /// </summary>
       static class CREATIONDISPOSITION
       {
           public const uint CREATE_NEW = 1;
           public const uint CREATE_ALWAYS = 2;
           public const uint OPEN_EXISTING = 3;
           public const uint OPEN_ALWAYS = 4;
           public const uint TRUNCATE_EXISTING = 5;
       }
       /// <summary>
       /// File attributes and flags for the file.
       /// </summary>
       static class FLAGSANDATTRIBUTES
       {
           public const uint FILE_FLAG_WRITE_THROUGH = 0x80000000;
           public const uint FILE_FLAG_OVERLAPPED = 0x40000000;
           public const uint FILE_FLAG_NO_BUFFERING = 0x20000000;
           public const uint FILE_FLAG_RANDOM_ACCESS = 0x10000000;
           public const uint FILE_FLAG_SEQUENTIAL_SCAN = 0x08000000;
           public const uint FILE_FLAG_DELETE_ON_CLOSE = 0x04000000;
           public const uint FILE_FLAG_BACKUP_SEMANTICS = 0x02000000;
           public const uint FILE_FLAG_POSIX_SEMANTICS = 0x01000000;
           public const uint FILE_FLAG_OPEN_REPARSE_POINT = 0x00200000;
           public const uint FILE_FLAG_OPEN_NO_RECALL = 0x00100000;
           public const uint FILE_FLAG_FIRST_PIPE_INSTANCE = 0x00080000;
       }

       struct OVERLAPPED
       {
           public uint Internal;
           public uint InternalHigh;
           public uint Offset;
           public uint OffsetHigh;
           public uint hEvent;
       }

       uint Status = 0, NumStatus = 0;
       uint SubStatus = 0, NumSubStatus = 0;

       public Form1()
       {
           InitializeComponent();
       }

       IntPtr CreateForRead(byte number)
       {
           IntPtr handle = CreateFile("\\\\.\\PHYSICALDRIVE" + number.ToString(),
              DESIREDACCESS.GENERIC_READ,
              SHAREMODE.FILE_SHARE_READ | SHAREMODE.FILE_SHARE_WRITE,
              0,
              CREATIONDISPOSITION.OPEN_EXISTING,
              0,
              0);

           if (handle == INVALID_HANDLE_VALUE)
               throw new Exception();

           return handle;
       }

       byte[] ReadSectors(IntPtr handle, uint offsetSector, ushort numSectors)
       {
           if (numSectors > 1024)
               throw new Exception();

           uint size = 512u * numSectors;
           byte[] buffer = new byte[size];

           uint _size;

           ulong offset = 512 * (ulong)offsetSector;
           OVERLAPPED over = new OVERLAPPED();
           over.Offset = (uint)(offset & 0xFFFFFFFF);
           over.OffsetHigh = (uint)((offset & 0xFFFFFFFF00000000) >> 32);

           if (ReadFile(handle, buffer, size, out _size, ref over) == 0)
           {
               CloseHandle(handle);
               throw new Exception();
           }

           return buffer;
       }

       IntPtr CreateForWrite(byte number)
       {
           IntPtr handle = CreateFile("\\\\.\\PHYSICALDRIVE" + number.ToString(),
               DESIREDACCESS.GENERIC_WRITE,
               SHAREMODE.FILE_SHARE_WRITE,
               0,
               CREATIONDISPOSITION.OPEN_EXISTING,
               0,
               0);

           if (handle == INVALID_HANDLE_VALUE)
               throw new Exception();

           return handle;
       }

       void WriteSectors(IntPtr handle, uint offsetSector, ushort numSectors, byte[] buffer)
       {
           if (numSectors > 1024)
               throw new Exception();

           uint size = 512u * numSectors;
           if (buffer.Length != size)
               throw new Exception();

           uint _size;

           ulong offset = 512 * (ulong)offsetSector;
           OVERLAPPED over = new OVERLAPPED();
           over.Offset = (uint)(offset & 0xFFFFFFFF);
           over.OffsetHigh = (uint)((offset & 0xFFFFFFFF00000000) >> 32);

           if (WriteFile(handle, buffer, size, out _size, ref over) == 0)
           {
               CloseHandle(handle);
               throw new Exception();
           }
       }

       class SubFile
       {
           public string FileName;
           public uint FileID;
       }

       class DirNode
       {
           public string DirName;
           public LinkedList<DirNode> SubDirs;
           public LinkedList<SubFile> SubFiles;
       }

       void MyWriteSizedString(BinaryWriter w, string str)
       {
           if (str.Length > UInt16.MaxValue)
               throw new Exception();

           w.Write((UInt16)str.Length);
           if (str.Length > 0)
               w.Write((char[])str.ToCharArray());
       }

       string MyReadSizedString(BinaryReader r)
       {
           ushort size = r.ReadUInt16();
           return size == 0 ? "" : new string(r.ReadChars(size));
       }

       void OutputDirStream(DirNode node, BinaryWriter w)
       {
           if (w.BaseStream is MemoryStream == false)
               throw new Exception();

           MyWriteSizedString(w, node.DirName);

           if (node.SubDirs.Count > UInt16.MaxValue)
               throw new Exception();
           w.Write((UInt16)node.SubDirs.Count);
           if (node.SubDirs.Count > 0)
           {
               foreach (DirNode d in node.SubDirs)
               {
                   OutputDirStream(d, w);
               }
           }

           if (node.SubFiles.Count > UInt16.MaxValue)
               throw new Exception();
           w.Write((UInt16)node.SubFiles.Count);
           if (node.SubFiles.Count > 0)
           {
               foreach (SubFile f in node.SubFiles)
               {
                   MyWriteSizedString(w, f.FileName);
                   w.Write((UInt32)f.FileID);
               }
           }
       }

       void InputDirStream(BinaryReader r, DirNode node)
       {
           if (r.BaseStream is MemoryStream == false)
               throw new Exception();

           node.DirName = MyReadSizedString(r);

           UInt16 numSubDirs = r.ReadUInt16();
           node.SubDirs = new LinkedList<DirNode>();
           if (numSubDirs > 0)
           {
               for (UInt16 i = 0; i < numSubDirs; i++)
               {
                   DirNode tmp = new DirNode();
                   node.SubDirs.AddLast(tmp);
                   InputDirStream(r, tmp);
               }
           }

           UInt16 numSubFiles = r.ReadUInt16();
           node.SubFiles = new LinkedList<SubFile>();
           if (numSubFiles > 0)
           {
               for (UInt16 i = 0; i < numSubFiles; i++)
               {
                   SubFile tmp = new SubFile();
                   node.SubFiles.AddLast(tmp);
                   tmp.FileName = MyReadSizedString(r);
                   tmp.FileID = r.ReadUInt32();
               }
           }
       }

       byte[] ReadDirStreamFromDisk(IntPtr handle, uint offsetSector)
       {
           byte[] bufLen = ReadSectors(handle, offsetSector, 1);
           uint len = BitConverter.ToUInt32(bufLen, 0);

           uint numAllSectors = (uint)len % (uint)512u == 0 ? (uint)len / (uint)512u : (uint)len / (uint)512 + 1;
           List<byte> bytes = new List<byte>((int)numAllSectors * 512);

           NumSubStatus = NumStatus = numAllSectors;
           SubStatus = Status = 0;

           for (uint i = 0; i < numAllSectors; i += 1024)
           {
               SubStatus = Status = i;

               if (numAllSectors - i >= 1024)
               {
                   bytes.AddRange(ReadSectors(handle, offsetSector + 1 + i, 1024));
               }
               else
               {
                   bytes.AddRange(ReadSectors(handle, offsetSector + 1 + i, (ushort)(numAllSectors - i)));
               }
           }

           NumSubStatus = NumStatus = 0;
           SubStatus = Status = 0;

           byte[] _bytes = new byte[len];
           bytes.CopyTo(0, _bytes, 0, (int)len);

           return _bytes;
       }

       void WriteDirStreamToDisk(IntPtr handle, uint offsetSector, byte[] bytes)
       {
           byte[] bufLen = new byte[512];
           BitConverter.GetBytes((UInt32)bytes.Length).CopyTo(bufLen, 0);

           WriteSectors(handle, offsetSector, 1, bufLen);

           List<byte[]> _bytes = new List<byte[]>();

           for (int i = 0; i < bytes.Length; i += 512 * 1024)
           {
               if (bytes.Length - i >= 512 * 1024)
               {
                   byte[] tmp = new byte[512 * 1024];
                   Array.Copy(bytes, i, tmp, 0, 512 * 1024);
                   _bytes.Add(tmp);
               }
               else
               {
                   int tSize = bytes.Length - i;
                   int _tSize = (int)tSize % (int)512 == 0 ? (int)tSize / (int)512 : ((int)tSize / (int)512) * 512 + 512;
                   byte[] tmp = new byte[_tSize];
                   Array.Copy(bytes, bytes.Length - tSize, tmp, 0, tSize);
                   _bytes.Add(tmp);
               }
           }

           NumSubStatus = NumStatus = (uint)_bytes.Count;
           SubStatus = Status = 0;

           for (int i = 0; i < _bytes.Count; i++)
           {
               SubStatus = Status = (uint)i;

               WriteSectors(handle, offsetSector + 1 + (uint)(i * 1024), (ushort)(_bytes[i].Length / 512), _bytes[i]);
           }

           NumSubStatus = NumStatus = 0;
           SubStatus = Status = 0;
       }

       void CreateTree(DirectoryInfo mainDirInfo, out DirNode root, out List<string> files)
       {
           root = new DirNode();
           root.DirName = "";

           files = new List<string>();

           root.SubDirs = new LinkedList<DirNode>();
           DirectoryInfo[] dirInfos = mainDirInfo.GetDirectories();
           if (dirInfos.Length > 0)
           {
               foreach (DirectoryInfo d in dirInfos)
               {
                   DirNode tmp = new DirNode();
                   root.SubDirs.AddLast(tmp);
                   CreateTreeRec(d, tmp, files);
               }
           }

           root.SubFiles = new LinkedList<SubFile>();
           FileInfo[] fileInfos = mainDirInfo.GetFiles();
           if (fileInfos.Length > 0)
           {
               foreach (FileInfo f in fileInfos)
               {
                   SubFile tmp = new SubFile();
                   root.SubFiles.AddLast(tmp);
                   tmp.FileName = f.Name;
                   files.Add(f.FullName);
                   tmp.FileID = (uint)(files.Count - 1);
               }
           }
       }

       void CreateTreeRec(DirectoryInfo dirInfo, DirNode node, List<string> files)
       {
           node.DirName = dirInfo.Name;

           node.SubDirs = new LinkedList<DirNode>();
           DirectoryInfo[] dirInfos = dirInfo.GetDirectories();
           if (dirInfos.Length > 0)
           {
               foreach (DirectoryInfo d in dirInfos)
               {
                   DirNode tmp = new DirNode();
                   node.SubDirs.AddLast(tmp);
                   CreateTreeRec(d, tmp, files);
               }
           }

           node.SubFiles = new LinkedList<SubFile>();
           FileInfo[] fileInfos = dirInfo.GetFiles();
           if (fileInfos.Length > 0)
           {
               foreach (FileInfo f in fileInfos)
               {
                   SubFile tmp = new SubFile();
                   node.SubFiles.AddLast(tmp);
                   tmp.FileName = f.Name;
                   files.Add(f.FullName);
                   tmp.FileID = (uint)(files.Count - 1);
               }
           }
       }

       struct FileDesc
       {
           public uint OffsetSector;
           public uint NumSectors;
           public ushort SizeLastSector;
       }

       void MakeAll(IntPtr handle, List<string> files, byte[] dirStream)
       {
           uint numFiles = (uint)files.Count;

           uint offsetSectorFileCount = 2;
           uint offsetSectorOfOffsetSectorDirStream = offsetSectorFileCount + 1;
           uint offsetSectorFileTable = offsetSectorOfOffsetSectorDirStream + 1;
           uint offsetSectorFiles = offsetSectorFileTable + numFiles;

           FileDesc[] fileTable = new FileDesc[numFiles];

           FileInfo _fileInfo = new FileInfo(files[0]);

           fileTable[0].OffsetSector = offsetSectorFiles;
           fileTable[0].SizeLastSector = (ushort)(_fileInfo.Length % 512 == 0 ? 512 : (_fileInfo.Length % 512));
           fileTable[0].NumSectors = (uint)(_fileInfo.Length / 512 + (fileTable[0].SizeLastSector == 512 ? 0 : 1));

           for (int i = 1; i < numFiles; i++)
           {
               FileInfo fileInfo = new FileInfo(files[i]);

               fileTable[i].OffsetSector = fileTable[i - 1].OffsetSector + fileTable[i - 1].NumSectors;
               fileTable[i].SizeLastSector = (ushort)(fileInfo.Length % 512 == 0 ? 512 : (fileInfo.Length % 512));
               fileTable[i].NumSectors = (uint)(fileInfo.Length / 512 + (fileTable[i].SizeLastSector == 512 ? 0 : 1));
           }

           uint offsetSectorDirStream = fileTable[numFiles - 1].OffsetSector + fileTable[numFiles - 1].NumSectors;

           List<byte[]> bytes = new List<byte[]>();

           byte[] bytesFileCount = new byte[512];
           BitConverter.GetBytes(numFiles).CopyTo(bytesFileCount, 0);
           bytes.Add(bytesFileCount);

           byte[] bytesOffsetSectorDirStream = new byte[512];
           BitConverter.GetBytes(offsetSectorDirStream).CopyTo(bytesOffsetSectorDirStream, 0);
           bytes.Add(bytesOffsetSectorDirStream);

           for (int i = 0; i < numFiles; i++)
           {
               byte[] bytesFileDesc = new byte[512];
               BitConverter.GetBytes((UInt32)fileTable[i].OffsetSector).CopyTo(bytesFileDesc, 0);
               BitConverter.GetBytes((UInt32)fileTable[i].NumSectors).CopyTo(bytesFileDesc, 4);
               BitConverter.GetBytes((UInt16)fileTable[i].SizeLastSector).CopyTo(bytesFileDesc, 8);
               bytes.Add(bytesFileDesc);
           }

           List<byte[]> _bytes = new List<byte[]>();

           for (int i = 0; i < bytes.Count; i += 1024)
           {
               if (bytes.Count - i >= 1024)
               {
                   byte[] tmp = new byte[512 * 1024];
                   for (int j = 0; j < 1024; j++)
                       bytes[i + j].CopyTo(tmp, j * 512);
                   _bytes.Add(tmp);
               }
               else
               {
                   byte[] tmp = new byte[512 * (bytes.Count - i)];
                   for (int j = 0; j < bytes.Count - i; j++)
                       bytes[i + j].CopyTo(tmp, j * 512);
                   _bytes.Add(tmp);
               }
           }

           NumStatus = 1 + numFiles;
           Status = 0;

           NumSubStatus = (uint)_bytes.Count;
           SubStatus = 0;

           for (int i = 0; i < _bytes.Count; i++)
           {
               SubStatus = (uint)i;

               WriteSectors(handle, offsetSectorFileCount + (uint)(i * 1024), (ushort)(_bytes[i].Length / 512), _bytes[i]);
           }

           for (int i = 0; i < numFiles; i++)
           {
               Status = (uint)(1 + i);

               FileStream fs = new FileStream(files[i], FileMode.Open, FileAccess.Read, FileShare.Read);
               BinaryReader r = new BinaryReader(fs);

               NumSubStatus = fileTable[i].NumSectors;
               SubStatus = 0;

               for (int j = 0; j < fileTable[i].NumSectors; j += 1024)
               {
                   SubStatus = (uint)j;

                   if (fileTable[i].NumSectors - j > 1024)
                   {
                       byte[] buffer = r.ReadBytes(512 * 1024);
                       WriteSectors(handle, fileTable[i].OffsetSector + (uint)j, 1024, buffer);
                   }
                   else if (fileTable[i].NumSectors - j == 1024)
                   {
                       byte[] _buffer = r.ReadBytes(512 * 1023 + fileTable[i].SizeLastSector);
                       byte[] buffer = new byte[512 * 1024];
                       _buffer.CopyTo(buffer, 0);
                       WriteSectors(handle, fileTable[i].OffsetSector + (uint)j, 1024, buffer);
                   }
                   else
                   {
                       byte[] _buffer = r.ReadBytes((int)((fileTable[i].NumSectors - j - 1) * 512 + fileTable[i].SizeLastSector));
                       if (fs.Position != fs.Length)
                           throw new Exception();
                       byte[] buffer = new byte[(fileTable[i].NumSectors - j) * 512];
                       _buffer.CopyTo(buffer, 0);
                       WriteSectors(handle, fileTable[i].OffsetSector + (uint)j, (ushort)(buffer.Length / 512), buffer);
                   }
               }

               r.Close();
           }

           NumSubStatus = NumStatus = 0;
           SubStatus = Status = 0;

           WriteDirStreamToDisk(handle, offsetSectorDirStream, dirStream);
       }

       uint GetOffsetSectorDirStream(IntPtr handle)
       {
           uint offsetSectorFileCount = 2;
           uint offsetSectorOfOffsetSectorDirStream = offsetSectorFileCount + 1;
           //uint offsetSectorFileTable = offsetSectorOfOffsetSectorDirStream + 1;

           byte[] bytes = ReadSectors(handle, offsetSectorOfOffsetSectorDirStream, 1);

           for (int i = 4; i < bytes.Length; i++)
               if (bytes[i] != 0)
                   throw new Exception();

           return BitConverter.ToUInt32(bytes, 0);
       }

       void GetFile(IntPtr handle, uint fileID, DirectoryInfo dirInfoSaveTo, string fileNameSaveTo, bool overwrite)
       {
           uint offsetSectorFileCount = 2;
           uint offsetSectorOfOffsetSectorDirStream = offsetSectorFileCount + 1;
           uint offsetSectorFileTable = offsetSectorOfOffsetSectorDirStream + 1;

           byte[] bytes = ReadSectors(handle, offsetSectorFileTable + fileID, 1);

           for (int i = 12; i < bytes.Length; i++)
               if (bytes[i] != 0)
                   throw new Exception();

           FileDesc fileDesc = new FileDesc();
           fileDesc.OffsetSector = BitConverter.ToUInt32(bytes, 0);
           fileDesc.NumSectors = BitConverter.ToUInt32(bytes, 4);
           fileDesc.SizeLastSector = BitConverter.ToUInt16(bytes, 8);

           FileStream fs = new FileStream(dirInfoSaveTo.FullName + '\\' + fileNameSaveTo, overwrite ? FileMode.Create : FileMode.CreateNew, FileAccess.Write, FileShare.None);
           BinaryWriter w = new BinaryWriter(fs);

           NumSubStatus = NumStatus = fileDesc.NumSectors;
           SubStatus = Status = 0;

           for (int i = 0; i < fileDesc.NumSectors; i += 1024)
           {
               SubStatus = Status = (uint)i;

               if (fileDesc.NumSectors - i > 1024)
               {
                   byte[] buffer = ReadSectors(handle, fileDesc.OffsetSector + (uint)i, 1024);
                   w.Write(buffer);
               }
               else if (fileDesc.NumSectors - i == 1024)
               {
                   byte[] buffer = ReadSectors(handle, fileDesc.OffsetSector + (uint)i, 1024);
                   w.Write(buffer, 0, 1023 * 512 + fileDesc.SizeLastSector);
               }
               else
               {
                   byte[] buffer = ReadSectors(handle, fileDesc.OffsetSector + (uint)i, (ushort)(fileDesc.NumSectors - i));
                   w.Write(buffer, 0, buffer.Length - 512 + fileDesc.SizeLastSector);
               }
           }

           NumSubStatus = NumStatus = 0;
           SubStatus = Status = 0;

           w.Close();
       }

       void FormatQuick(IntPtr handle)
       {
           byte[] bytes = new byte[512 * 2];
           for (int i = 0; i < bytes.Length; i++)
               bytes[i] = 0x88;

           WriteSectors(handle, 0, 2, bytes);
       }

       bool CheckFormat(IntPtr handle)
       {
           byte[] bytes = ReadSectors(handle, 0, 2);

           foreach (byte b in bytes)
               if (b != 0x88)
                   return false;

           return true;
       }

       private void button1_Click(object sender, EventArgs e)
       {
           byte number;
           try
           {
               number = byte.Parse(textBox3.Text);
           }
           catch (Exception)
           {
               MessageBox.Show("Invalid HDD number!");
               return;
           }

           DirectoryInfo path;
           try
           {
               path = new DirectoryInfo(textBox1.Text);
           }
           catch (Exception)
           {
               MessageBox.Show("Path is not found!");
               return;
           }

           IntPtr handle_;
           try
           {
               handle_ = CreateForRead(number);
           }
           catch (Exception)
           {
               MessageBox.Show("HDD is not found!");
               return;
           }

           bool b = CheckFormat(handle_);
           CloseHandle(handle_);

           if (!b)
           {
               MessageBox.Show("Unsupported HDD format!");
               return;
           }

           MemoryStream ms = new MemoryStream();
           BinaryWriter w = new BinaryWriter(ms);

           DirNode root;
           List<string> files;
           CreateTree(path, out root, out files);

           OutputDirStream(root, w);

           byte[] bytes = ms.ToArray();
           ms.Close();

           IntPtr handle = CreateForWrite(number);

           button1.Enabled = button2.Enabled = button3.Enabled = button4.Enabled = false;
           bool flag = false;
           Thread thread = new Thread(delegate()
           {
               try
               {
                   MakeAll(handle, files, bytes);
                   flag = true;
               }
               catch (Exception)
               {
                   flag = false;
               }
           });
           thread.Start();
           while (thread.ThreadState == ThreadState.Running)
           {
               Application.DoEvents();

               progressBar1.Minimum = 0;
               progressBar1.Maximum = NumStatus == 0 ? 0 : (int)(NumStatus - 1);
               try
               {
                   progressBar1.Value = (int)Status;
               }
               catch (Exception) { }

               progressBar2.Minimum = 0;
               progressBar2.Maximum = NumSubStatus == 0 ? 0 : (int)(NumSubStatus - 1);
               try
               {
                   progressBar2.Value = (int)SubStatus;
               }
               catch (Exception) { }
           }
           button1.Enabled = button2.Enabled = button3.Enabled = button4.Enabled = true;
           
           CloseHandle(handle);

           MessageBox.Show(flag ? "Done!" : "Failed!");
       }

       void ShowDirs(DirNode node, TreeNodeCollection viewNodes)
       {
           if (node.SubDirs.Count > 0)
           {
               foreach (DirNode d in node.SubDirs)
               {
                   TreeNode tmp = new TreeNode();
                   tmp.Text = d.DirName + "    <DIR>";
                   tmp.Tag = null;
                   viewNodes.Add(tmp);

                   ShowDirs(d, tmp.Nodes);
               }
           }
           
           if (node.SubFiles.Count > 0)
           {
               foreach (SubFile f in node.SubFiles)
               {
                   TreeNode tmp = new TreeNode();
                   tmp.Text = f.FileName;
                   tmp.Tag = f.FileID;
                   viewNodes.Add(tmp);
               }
           }
       }

       private void button2_Click(object sender, EventArgs e)
       {
           byte number;
           try
           {
               number = byte.Parse(textBox4.Text);
           }
           catch (Exception)
           {
               MessageBox.Show("Invalid HDD number!");
               return;
           }

           IntPtr handle_;
           try
           {
               handle_ = CreateForRead(number);
           }
           catch (Exception)
           {
               MessageBox.Show("HDD is not found!");
               return;
           }

           bool b = CheckFormat(handle_);
           CloseHandle(handle_);

           if (!b)
           {
               MessageBox.Show("Unsupported HDD format!");
               return;
           }

           IntPtr handle = CreateForRead(number);
           DirNode root = new DirNode();
           InputDirStream(new BinaryReader(new MemoryStream(ReadDirStreamFromDisk(handle, GetOffsetSectorDirStream(handle)))), root);
           CloseHandle(handle);

           treeView1.Nodes.Clear();
           ShowDirs(root, treeView1.Nodes);

           treeView1.Tag = number;

           MessageBox.Show("Done!");
       }

       private void button3_Click(object sender, EventArgs e)
       {
           if (treeView1.SelectedNode == null || treeView1.SelectedNode.Tag == null)
           {
               MessageBox.Show("No file is selected!");
               return;
           }

           byte number = (byte)treeView1.Tag;
           textBox4.Text = number.ToString();

           DirectoryInfo path;
           try
           {
               path = new DirectoryInfo(textBox2.Text);
           }
           catch (Exception)
           {
               MessageBox.Show("Path is not found!");
               return;
           }

           IntPtr handle_;
           try
           {
               handle_ = CreateForRead(number);
           }
           catch (Exception)
           {
               MessageBox.Show("HDD is not found!");
               return;
           }

           bool b = CheckFormat(handle_);
           CloseHandle(handle_);

           if (!b)
           {
               MessageBox.Show("Unsupported HDD format!");
               return;
           }

           IntPtr handle = CreateForRead(number);

           button1.Enabled = button2.Enabled = button3.Enabled = button4.Enabled = false;
           uint fileID = (uint)treeView1.SelectedNode.Tag;
           string fileNameSaveTo = treeView1.SelectedNode.Text;
           bool overwrite = checkBox1.Checked;
           bool flag = false;
           Thread thread = new Thread(delegate()
           {
               try
               {
                   GetFile(handle, fileID, path, fileNameSaveTo, overwrite);
                   flag = true;
               }
               catch (Exception)
               {
                   flag = false;
               }
           });
           thread.Start();
           while (thread.ThreadState == ThreadState.Running)
           {
               Application.DoEvents();

               progressBar1.Minimum = 0;
               progressBar1.Maximum = NumStatus == 0 ? 0 : (int)(NumStatus - 1);
               try
               {
                   progressBar1.Value = (int)Status;
               }
               catch (Exception) { }

               progressBar2.Minimum = 0;
               progressBar2.Maximum = NumSubStatus == 0 ? 0 : (int)(NumSubStatus - 1);
               try
               {
                   progressBar2.Value = (int)SubStatus;
               }
               catch (Exception) { }
           }
           button1.Enabled = button2.Enabled = button3.Enabled = button4.Enabled = true;

           CloseHandle(handle);

           MessageBox.Show(flag ? "Done!" : "Failed!");
       }

       private void button4_Click(object sender, EventArgs e)
       {
           byte number;
           try
           {
               number = byte.Parse(textBox5.Text);
           }
           catch (Exception)
           {
               MessageBox.Show("Invalid HDD number!");
               return;
           }

           IntPtr handle_;
           try
           {
               handle_ = CreateForRead(number);
           }
           catch (Exception)
           {
               MessageBox.Show("HDD is not found!");
               return;
           }

           bool b = CheckFormat(handle_);
           CloseHandle(handle_);

           if (b)
           {
               MessageBox.Show("Already formatted!");
               return;
           }
           else
           {
               if (MessageBox.Show("Not formatted, format now?", "Format", MessageBoxButtons.OKCancel) == DialogResult.OK)
               {
                   IntPtr handle = CreateForWrite(number);
                   FormatQuick(handle);
                   CloseHandle(handle);

                   MessageBox.Show("Done!");
               }
           }
       }
   }
}
1   商湯      2026年2月5日 木 10:26
<Form1.Designer.cs>

namespace ReadWriteDisk
{
   partial class Form1
   {
       /// <summary>
       /// 必要なデザイナ変数です。
       /// </summary>
       private System.ComponentModel.IContainer components = null;

       /// <summary>
       /// 使用中のリソースをすべてクリーンアップします。
       /// </summary>
       /// <param name="disposing">マネージ リソースが破棄される場合 true、破棄されない場合は false です。</param>
       protected override void Dispose(bool disposing)
       {
           if (disposing && (components != null))
           {
               components.Dispose();
           }
           base.Dispose(disposing);
       }

       #region Windows フォーム デザイナで生成されたコード

       /// <summary>
       /// デザイナ サポートに必要なメソッドです。このメソッドの内容を
       /// コード エディタで変更しないでください。
       /// </summary>
       private void InitializeComponent()
       {
           this.button1 = new System.Windows.Forms.Button();
           this.textBox1 = new System.Windows.Forms.TextBox();
           this.button2 = new System.Windows.Forms.Button();
           this.textBox2 = new System.Windows.Forms.TextBox();
           this.progressBar1 = new System.Windows.Forms.ProgressBar();
           this.progressBar2 = new System.Windows.Forms.ProgressBar();
           this.textBox3 = new System.Windows.Forms.TextBox();
           this.textBox4 = new System.Windows.Forms.TextBox();
           this.label1 = new System.Windows.Forms.Label();
           this.label2 = new System.Windows.Forms.Label();
           this.label3 = new System.Windows.Forms.Label();
           this.label4 = new System.Windows.Forms.Label();
           this.treeView1 = new System.Windows.Forms.TreeView();
           this.label5 = new System.Windows.Forms.Label();
           this.button3 = new System.Windows.Forms.Button();
           this.textBox5 = new System.Windows.Forms.TextBox();
           this.label6 = new System.Windows.Forms.Label();
           this.label7 = new System.Windows.Forms.Label();
           this.button4 = new System.Windows.Forms.Button();
           this.checkBox1 = new System.Windows.Forms.CheckBox();
           this.SuspendLayout();
           //
           // button1
           //
           this.button1.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
           this.button1.Location = new System.Drawing.Point(321, 68);
           this.button1.Name = "button1";
           this.button1.Size = new System.Drawing.Size(75, 23);
           this.button1.TabIndex = 0;
           this.button1.Text = "Write to";
           this.button1.UseVisualStyleBackColor = true;
           this.button1.Click += new System.EventHandler(this.button1_Click);
           //
           // textBox1
           //
           this.textBox1.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left)
                       | System.Windows.Forms.AnchorStyles.Right)));
           this.textBox1.Location = new System.Drawing.Point(46, 70);
           this.textBox1.Name = "textBox1";
           this.textBox1.ScrollBars = System.Windows.Forms.ScrollBars.Vertical;
           this.textBox1.Size = new System.Drawing.Size(269, 19);
           this.textBox1.TabIndex = 1;
           //
           // button2
           //
           this.button2.Location = new System.Drawing.Point(122, 93);
           this.button2.Name = "button2";
           this.button2.Size = new System.Drawing.Size(75, 23);
           this.button2.TabIndex = 2;
           this.button2.Text = "Show Dirs";
           this.button2.UseVisualStyleBackColor = true;
           this.button2.Click += new System.EventHandler(this.button2_Click);
           //
           // textBox2
           //
           this.textBox2.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left)
                       | System.Windows.Forms.AnchorStyles.Right)));
           this.textBox2.Location = new System.Drawing.Point(127, 122);
           this.textBox2.Name = "textBox2";
           this.textBox2.Size = new System.Drawing.Size(300, 19);
           this.textBox2.TabIndex = 3;
           //
           // progressBar1
           //
           this.progressBar1.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left)
                       | System.Windows.Forms.AnchorStyles.Right)));
           this.progressBar1.Location = new System.Drawing.Point(79, 12);
           this.progressBar1.Name = "progressBar1";
           this.progressBar1.Size = new System.Drawing.Size(427, 23);
           this.progressBar1.TabIndex = 4;
           //
           // progressBar2
           //
           this.progressBar2.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Left)
                       | System.Windows.Forms.AnchorStyles.Right)));
           this.progressBar2.Location = new System.Drawing.Point(79, 41);
           this.progressBar2.Name = "progressBar2";
           this.progressBar2.Size = new System.Drawing.Size(427, 23);
           this.progressBar2.TabIndex = 5;
           //
           // textBox3
           //
           this.textBox3.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
           this.textBox3.Location = new System.Drawing.Point(457, 70);
           this.textBox3.Name = "textBox3";
           this.textBox3.Size = new System.Drawing.Size(49, 19);
           this.textBox3.TabIndex = 6;
           //
           // textBox4
           //
           this.textBox4.Location = new System.Drawing.Point(67, 95);
           this.textBox4.Name = "textBox4";
           this.textBox4.Size = new System.Drawing.Size(49, 19);
           this.textBox4.TabIndex = 7;
           //
           // label1
           //
           this.label1.AutoSize = true;
           this.label1.Location = new System.Drawing.Point(12, 73);
           this.label1.Name = "label1";
           this.label1.Size = new System.Drawing.Size(28, 12);
           this.label1.TabIndex = 8;
           this.label1.Text = "Path";
           //
           // label2
           //
           this.label2.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
           this.label2.AutoSize = true;
           this.label2.Location = new System.Drawing.Point(402, 73);
           this.label2.Name = "label2";
           this.label2.Size = new System.Drawing.Size(49, 12);
           this.label2.TabIndex = 9;
           this.label2.Text = "HDD No.";
           //
           // label3
           //
           this.label3.AutoSize = true;
           this.label3.Location = new System.Drawing.Point(12, 17);
           this.label3.Name = "label3";
           this.label3.Size = new System.Drawing.Size(38, 12);
           this.label3.TabIndex = 10;
           this.label3.Text = "Status";
           //
           // label4
           //
           this.label4.AutoSize = true;
           this.label4.Location = new System.Drawing.Point(10, 46);
           this.label4.Name = "label4";
           this.label4.Size = new System.Drawing.Size(61, 12);
           this.label4.TabIndex = 11;
           this.label4.Text = "Sub Status";
           //
           // treeView1
           //
           this.treeView1.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
                       | System.Windows.Forms.AnchorStyles.Left)
                       | System.Windows.Forms.AnchorStyles.Right)));
           this.treeView1.Location = new System.Drawing.Point(12, 152);
           this.treeView1.Name = "treeView1";
           this.treeView1.Size = new System.Drawing.Size(494, 437);
           this.treeView1.TabIndex = 12;
2   商湯      2026年2月5日 木 10:26
           //
           // label5
           //
           this.label5.AutoSize = true;
           this.label5.Location = new System.Drawing.Point(93, 125);
           this.label5.Name = "label5";
           this.label5.Size = new System.Drawing.Size(28, 12);
           this.label5.TabIndex = 13;
           this.label5.Text = "Path";
           //
           // button3
           //
           this.button3.Location = new System.Drawing.Point(12, 120);
           this.button3.Name = "button3";
           this.button3.Size = new System.Drawing.Size(75, 23);
           this.button3.TabIndex = 14;
           this.button3.Text = "Save to";
           this.button3.UseVisualStyleBackColor = true;
           this.button3.Click += new System.EventHandler(this.button3_Click);
           //
           // textBox5
           //
           this.textBox5.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
           this.textBox5.Location = new System.Drawing.Point(67, 597);
           this.textBox5.Name = "textBox5";
           this.textBox5.Size = new System.Drawing.Size(49, 19);
           this.textBox5.TabIndex = 15;
           //
           // label6
           //
           this.label6.AutoSize = true;
           this.label6.Location = new System.Drawing.Point(12, 98);
           this.label6.Name = "label6";
           this.label6.Size = new System.Drawing.Size(49, 12);
           this.label6.TabIndex = 16;
           this.label6.Text = "HDD No.";
           //
           // label7
           //
           this.label7.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
           this.label7.AutoSize = true;
           this.label7.Location = new System.Drawing.Point(15, 600);
           this.label7.Name = "label7";
           this.label7.Size = new System.Drawing.Size(49, 12);
           this.label7.TabIndex = 17;
           this.label7.Text = "HDD No.";
           //
           // button4
           //
           this.button4.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
           this.button4.Location = new System.Drawing.Point(122, 595);
           this.button4.Name = "button4";
           this.button4.Size = new System.Drawing.Size(75, 23);
           this.button4.TabIndex = 18;
           this.button4.Text = "Format";
           this.button4.UseVisualStyleBackColor = true;
           this.button4.Click += new System.EventHandler(this.button4_Click);
           //
           // checkBox1
           //
           this.checkBox1.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
           this.checkBox1.AutoSize = true;
           this.checkBox1.Location = new System.Drawing.Point(433, 124);
           this.checkBox1.Name = "checkBox1";
           this.checkBox1.Size = new System.Drawing.Size(73, 16);
           this.checkBox1.TabIndex = 19;
           this.checkBox1.Text = "Overwrite";
           this.checkBox1.UseVisualStyleBackColor = true;
           //
           // Form1
           //
           this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);
           this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
           this.ClientSize = new System.Drawing.Size(518, 628);
           this.Controls.Add(this.checkBox1);
           this.Controls.Add(this.button4);
           this.Controls.Add(this.label7);
           this.Controls.Add(this.label6);
           this.Controls.Add(this.textBox5);
           this.Controls.Add(this.button3);
           this.Controls.Add(this.label5);
           this.Controls.Add(this.treeView1);
           this.Controls.Add(this.label4);
           this.Controls.Add(this.label3);
           this.Controls.Add(this.label2);
           this.Controls.Add(this.label1);
           this.Controls.Add(this.textBox4);
           this.Controls.Add(this.textBox3);
           this.Controls.Add(this.progressBar2);
           this.Controls.Add(this.progressBar1);
           this.Controls.Add(this.textBox2);
           this.Controls.Add(this.button2);
           this.Controls.Add(this.textBox1);
           this.Controls.Add(this.button1);
           this.Name = "Form1";
           this.Text = "Form1";
           this.ResumeLayout(false);
           this.PerformLayout();

       }

       #endregion

       private System.Windows.Forms.Button button1;
       private System.Windows.Forms.TextBox textBox1;
       private System.Windows.Forms.Button button2;
       private System.Windows.Forms.TextBox textBox2;
       private System.Windows.Forms.ProgressBar progressBar1;
       private System.Windows.Forms.ProgressBar progressBar2;
       private System.Windows.Forms.TextBox textBox3;
       private System.Windows.Forms.TextBox textBox4;
       private System.Windows.Forms.Label label1;
       private System.Windows.Forms.Label label2;
       private System.Windows.Forms.Label label3;
       private System.Windows.Forms.Label label4;
       private System.Windows.Forms.TreeView treeView1;
       private System.Windows.Forms.Label label5;
       private System.Windows.Forms.Button button3;
       private System.Windows.Forms.TextBox textBox5;
       private System.Windows.Forms.Label label6;
       private System.Windows.Forms.Label label7;
       private System.Windows.Forms.Button button4;
       private System.Windows.Forms.CheckBox checkBox1;
   }
}

名前      編集用パスワード(省略可)    パスワードの記憶
数式 αβγ IPA http:// 画像 B I U 上 下
(添付ファイルは http://www.jkofsp.net/up/ にアップロードしてください)