简体   繁体   中英

low level C++ style i/o in C# for reading FAT32

I am working on reading the FAT32 entry of the hard disk and so far have been successful in reading the entries by making use of the CreateFile , ReadFile , and SetFilePointer APIs. Here is my code (written in C#) so far.

---The DLL IMPORTS-----

[DllImport("kernel32.dll", SetLastError = true)]
        static extern IntPtr CreateFile(string lpFileName, Int32 dwDesiredAccess,
            Int32 dwShareMode, Int32 lpSecurityAttributes, Int32 dwCreationDisposition,
            Int32 dwFlagsAndAttributes, IntPtr hTemplateFile);

        [DllImport("kernel32.dll")]
        static extern bool ReadFile(IntPtr hFile, byte[] lpBuffer,
           uint nNumberOfBytesToRead, out uint lpNumberOfBytesRead, uint lpOverlapped);

        [DllImport("kernel32.dll")]
        extern static int SetFilePointer(IntPtr hFile, int lDistanceToMove, int lpDistanceToMoveHigh, uint dwMoveMethod);

        [DllImport("kernel32.dll")]
        extern static Boolean CloseHandle(IntPtr hObject);

------CODE----Will Work in any .NET Application---------

        int ret, nread;
        IntPtr handle;
        int s = 512;
        byte[] readbuffer = new byte[512];

    IntPtr ptr = CreateFile(@"\\.\F:", -1073741824, 3, 0, 3, 128, IntPtr.Zero);
 if (ptr != System.IntPtr.Zero)
            {
                int i = 100;
                int ret = SetFilePointer(ptr, 0, 0, 0);
                ret = SetFilePointer(ptr, 4194304, 0, 1);
                while (true)
                {
                    byte[] inp = new byte[512];
                    uint read = 0;
                    if (ret != -1)
                    {
                        ReadFile(ptr, inp, 512, out read, 0);
                        for (int k = 0; k < 16; k++)
                        {
                            string s = ASCIIEncoding.ASCII.GetString(inp, k*32, 11);
                            if (inp[k*32] == 0xE5)
                            {
                                MessageBox.Show(s);
                            }
                        }
                        //ret = SetFilePointer(ptr, 512, 0, 1);
                    }

                }
            }

The code above reads the F:\\ drive and for trial purposes I have made it to read the first File Directory Cluster and query through each file entry and display the file name if it has been deleted.

However I want to make it to a full-blown application, for which I will have to frequently use the byte array and map it to the specified data structures according to the FAT32 Specification.

How can I efficiently use the byte array into which I am reading the data? I have tried the same code using filestream and binaryreader and it works, however now suppose I have a C Structure something like

struct bios_data
{
byte id[3];
char name[11];
byte sectorpercluster[2];
...
}

I want to have a similar data structure in C# and when I read data to a byte array I want to map it to the structure. I tried many options but didn't get a complete solution. I tried making a class and do serialization too but that also didn't work. I have around 3 more structures like theese which I will be using as I read the data from the FAT entry. How can I best achieve the desired results?

If you want to read binary data directly into structs, C-style, this article may interest you. He wrote an unmanaged wrapper around the C stdio functions and interoperates with it. I have tried it - it does work quite well. It is nice to read directly into a struct in C#, and it is fast. You can just do:

unsafe 
{ 
 fmp3.Read<MyStruct>(&myStructVar); 
}

这个问题中,我给出了如何在字节数组和结构之间进行转换的答案。

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM