Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Opening a Memory Mapped File causes FileNotFoundException when deployed in IIS

Following the code example from this website, I created a windows console application that creates a mapped memory file:

        using (var file = MemoryMappedFile.CreateNew("myFile", 24))
        {
            var bytes = new byte[24];
            for (var i = 0; i < bytes.Length; i++)
                bytes[i] = (byte)(65 + i);

            using (var writer = file.CreateViewAccessor(0, bytes.Length))
            {
                writer.WriteArray<byte>(0, bytes, 0, bytes.Length);
            }
            Console.WriteLine("Run memory mapped file reader before exit");
            Console.WriteLine("Press any key to exit ...");
            Console.ReadLine();
        }

in a new asp.net web application I read the MMF using the code:

 protected void Page_Load(object sender, EventArgs e)
    {
        string sOutput = "";

        using (var file = MemoryMappedFile.OpenExisting("myFile"))
        {
            using (var reader = file.CreateViewAccessor(0, 24))
            {
                var bytes = new byte[24];
                reader.ReadArray<byte>(0, bytes, 0, bytes.Length);

                for (var i = 0; i < bytes.Length; i++)
                    sOutput += (char)bytes[i] + " ";

            }
        }

        Response.Write(sOutput);
    }

In the development IIS Express the file is read as expected and the page displays the data from the mapped memory file.

However, When deployed to IIS I get the exception System.IO.FileNotFoundException at the locationMemoryMappedFile.OpenExisting("myFile")

I tried changing the app pool identity to the same as the one running the MMF console application but this does didn't work.

like image 275
SausageFingers Avatar asked Dec 03 '13 23:12

SausageFingers


1 Answers

Add "Global\\" prefix to the mapName. That is the only way it worked for me. When we try to access shared memory created in the first process it runs in a different security context and shared memory objects are not visible unless they are created in the global namespace.

This is the code that worked for me. I used CreateOrOpen in a WinForm application and I used OpenExisting in an IIS process:

mSec = new MemoryMappedFileSecurity();
mSec.AddAccessRule(new AccessRule<MemoryMappedFileRights>(new SecurityIdentifier(WellKnownSidType.WorldSid, null), MemoryMappedFileRights.FullControl, AccessControlType.Allow));

mmf = MemoryMappedFile.CreateOrOpen("Global\\\MmfName", 100, MemoryMappedFileAccess.ReadWrite, MemoryMappedFileOptions.None, mSec, HandleInheritability.Inheritable);

mmf = MemoryMappedFile.OpenExisting("Global\\\MmfName");
like image 107
Toma Tacescu Avatar answered Sep 20 '22 15:09

Toma Tacescu