32/64bit sample code


// Updated 05/19/06:  32/64bit sample code


using System;


using System.Collections.Generic;


using System.Text;


 


namespace PlatformPointer


{


    class Test


    {


        static int Main(string[] args)


        {


            if (args.Length != 1)


            {


                System.Console.WriteLine("Usage : ReadFile <FileName>");


                return 1;


            }


 


            if (!System.IO.File.Exists(args[0]))


            {


                System.Console.WriteLine("File " + args[0] + " not found.");


                return 1;


            }


            Console.BackgroundColor = ConsoleColor.Blue;


            Console.ForegroundColor = ConsoleColor.White;


            Console.Title = "C# platform pointer sample";


            // The size of a pointer or handle on this platform, measured in bytes.


            // The value of this property is 4 on a 32-bit platform, and 8 on a 64-bit platform.


            if (System.IntPtr.Size == 4)


                Console.WriteLine("Running on a 32-bit platform");


            if (System.IntPtr.Size == 8)


                Console.WriteLine("Running on a 64-bit platform");


            Console.ResetColor();


            //


            byte[] buffer = new byte[128];


            FileReader fr = new FileReader();


            if (fr.Open(args[0]))


            {


                // Assume that an ASCII file is being read.


                System.Text.ASCIIEncoding Encoding = new System.Text.ASCIIEncoding();


 


                int bytesRead;


                do


                {


                    bytesRead = fr.Read(buffer, 0, buffer.Length);


                    string content = Encoding.GetString(buffer, 0, bytesRead);


                    System.Console.Write("{0}", content);


                }


                while (bytesRead > 0);


                fr.Close();


                Console.SetCursorPosition(0, 0);


                return 0;


            }


            else


            {


                System.Console.WriteLine("Failed to open requested file");


                return 1;


            }


        }   // Main()


    }   // class Test


 


    // Windows Readfile sample


    class FileReader


    {


        const uint GENERIC_READ = 0x80000000;


        const uint OPEN_EXISTING = 3;


        // Platform specific pointer or handle


        System.IntPtr handle;


        // External native windows dll call


        // Note the unsafe keyword for code that requires a pointer (a native code concept)


        [System.Runtime.InteropServices.DllImport("kernel32", SetLastError = true)]


        static extern unsafe System.IntPtr CreateFile


        (


            string FileName,          // file name


            uint DesiredAccess,       // access mode


            uint ShareMode,           // share mode


            System.IntPtr SecurityAttributes,  // Security Attributes


            uint CreationDisposition, // how to create


            uint FlagsAndAttributes,  // file attributes


            System.IntPtr hTemplateFile         // handle to template file


        );


 


        [System.Runtime.InteropServices.DllImport("kernel32", SetLastError = true)]


        static extern unsafe bool ReadFile


        (


            System.IntPtr hFile,      // handle to file


            void* pBuffer,            // data buffer


            int NumberOfBytesToRead,  // number of bytes to read


            int* pNumberOfBytesRead,  // number of bytes read


            System.IntPtr Overlapped            // overlapped buffer


        );


 


        [System.Runtime.InteropServices.DllImport("kernel32", SetLastError = true)]


        static extern unsafe bool CloseHandle


        (


            System.IntPtr hObject // handle to object


        );


 


        public bool Open(string FileName)


        {


            // open the existing file for reading


            // The handle return value is an IntPtr, platform (32/64bit) agnostic


            handle = CreateFile     // See extern CreateFile


            (


                FileName,


                GENERIC_READ,


                0,


                System.IntPtr.Zero,


                OPEN_EXISTING,


                0,


                System.IntPtr.Zero


            );


 


            if (handle != System.IntPtr.Zero)


            {


                return true;


            }


            else


            {


                return false;


            }


        }   // class FileReader


 


        public unsafe int Read(byte[] buffer, int index, int count)


        {


            int n = 0;


            /*


             Note the fixed keyword.


             The byte array is a managed type that is passed to unmanaged code, as such the byte[]


             is subject to garbage collection by the CLR which means the memory location of the byte array


             could change and cause an unexpected behavior in the native code.  The fixed keyword is used


             to get a pointer to memory and mark it so that the GC will not move it.


             * At the end of the fixed block the memory returns to a state that the GC can collect.


            */


            fixed (byte* p = buffer)


            {


                if (!ReadFile(handle, p + index, count, &n, System.IntPtr.Zero))


                {


                    return 0;


                }


            }


            return n;


        }   // Read()


 


        public bool Close()


        {


            return CloseHandle(handle);


        }   // Close()


    }   // class FileReader


}   // namespace PlatformPointer

Comments (3)
  1. This was my first webcast, so please be patient through the beginning.&amp;nbsp; It gets much better there…

  2. I want to thank Josh Williams from the CLR team, for pointing out a couple bugs in my sample code.&amp;nbsp;…

Comments are closed.

Skip to main content