Как реализовать разделяемую память в .NET?

У меня есть приложение C ++. NET и приложение C # .NET. Я бы хотел, чтобы они общались через общую память.

Как это возможно в .NET версии 2.0?

В основном хочу поделиться объектом очереди.


person Community    schedule 13.01.2009    source источник


Ответы (6)


Обновление: Привет, вот страница, которую я только что нашел, с полным внедрением.


Используя C ++ / CLI, довольно легко настроить разделяемую память в соответствии с обычным C ++ API (C ++ / CLI может взаимодействовать с управляемыми и собственными ссылками на HEAP / память). Затем UnmanagedMemoryStream можно использовать для предоставления объекта Stream C #.

Я не прикреплял файл .h, но вы можете легко вывести макет pmapped native typedef;). Вы также можете оценить возможное использование BufferedStream в зависимости от варианта использования вашего читателя / писателя. И код взят из проекта, который я больше не использую, поэтому я не могу вспомнить статус его регресса ошибки.

Вот класс C ++ / CLI, который устанавливает отображение файлов и предоставляет UnmanagedMemoryStream;

public ref class MemMapp
{
    public:
        __clrcall MemMapp(String^ file)  
        { 
            map = NULL;

            if(!File::Exists(file)) throw gcnew ApplicationException("Can not find file " + file);

            marshal_context^ x = gcnew marshal_context();
            const char *nname = x->marshal_as<const char*>(file);

            map = (pmapped) malloc(sizeof(mapped));
            ZeroMemory(map, sizeof(mapped));
            map->name = strdup(nname);
            InitMap(map);
        }
        void __clrcall MapBytes(long long loc, long length)
        {
            map->low = loc & 0xffffffff;
            map->high = (loc >> 32) & 0xffffffff;
            map->size = length & 0xffffffff;
            if(!GetMapForFile(map))
                throw gcnew ApplicationException("can not map range " + loc + " :" + length);

            if(map->size = 0)
                map->size = MAXMAX&0xffffffff;

        }
        UnmanagedMemoryStream ^View()
        { 
            return gcnew UnmanagedMemoryStream((unsigned char *) map->blok, map->size, map->size, FileAccess::Read); 
        }
        long long __clrcall FileSize()
        {
            DWORD high, low;
            long long rv;

            low = GetFileSize(map->hFile, &high);
            maxmax = high;
            maxmax << 32;
            maxmax += low;

            rv = high;
            rv << 32;
            rv = rv & low;
            return rv;
        }
        property unsigned int MinBufSiz { unsigned int get() { return map->dwbufz; } }
        property long long BufBase { long long get() { return (map->high << 32) + map->low; } }
        property long long BufLim { long long get() { return ((map->high << 32) + map->low) + map->size; } }
        property long long MAXMAX { long long get() { return maxmax; } }
        static MemMapp() { }
        __clrcall ~MemMapp() { if(map != NULL) { CloseMap(map); free(map->name); free(map); map = NULL; } }
    protected:
        __clrcall !MemMapp() { if(map != NULL) { CloseMap(map); free(map->name); free(map); map = NULL; } }
        pmapped map;
        long long maxmax;
};

Вот хотя бы CLoseMap ... Я только что нашел ... он не был скомпилирован с / CLR


bool CloseMap(pmapped map)
{
    if(map->blok != NULL) {
        UnmapViewOfFile(map->blok);
        map->blok = NULL;
    }
    if(map->hMap != INVALID_HANDLE_VALUE && map->hMap != NULL) {
        CloseHandle(map->hMap);
        map->hMap = INVALID_HANDLE_VALUE;
    }
    if(map->hFile != INVALID_HANDLE_VALUE && map->hFile != NULL) {
        CloseHandle(map->hFile);
        map->hFile = INVALID_HANDLE_VALUE;
    }
    return false;
}
person RandomNickName42    schedule 29.05.2009
comment
+1 .net 4 поддерживает файлы с отображением памяти msdn.microsoft .com / ru-ru / library / - person kenny; 31.12.2010

У ваших приложений есть несколько вариантов взаимодействия. Самыми популярными являются удаленное взаимодействие и конвейеры. Есть несколько примеров для обоих, и прежде чем выбрать один, вы должны рассмотреть плюсы и минусы, такие как переносимость. Вот несколько полезных ссылок:

Межпроцессное взаимодействие в .NET с использованием именованных каналов, часть 1

Межпроцессное взаимодействие в .NET с использованием именованных каналов, часть 2

.NET Remoting на простом английском языке

.NET Remoting с простым примером

person Diadistis    schedule 13.01.2009
comment
Это отличный ответ, и все, кроме вопроса, касалось общей памяти. - person Rick Minerich; 09.09.2010

Общая память - единственный вариант? Есть много способов взаимодействия двух .NET-процессов. Некоторые из них:

  • .NET Remoting Object - позволяет объектам взаимодействовать друг с другом в разных процессах. здесь.
  • Очередь сообщений Microsoft (MSMQ) - общая очередь сообщений между процессами. MSMQ будет работать как другая служба Windows.
person Gant    schedule 13.01.2009

У вас также есть альтернатива C ++ / CLI в виде импорта функций win32 в ваше приложение C #:

[DllImport ("kernel32.dll", SetLastError = true)]
  static extern IntPtr CreateFileMapping (IntPtr hFile,
                                          int lpAttributes,
                                          FileProtection flProtect,
                                          uint dwMaximumSizeHigh,
                                          uint dwMaximumSizeLow,
                                          string lpName);

  [DllImport ("kernel32.dll", SetLastError=true)]
  static extern IntPtr OpenFileMapping (FileRights dwDesiredAccess,
                                        bool bInheritHandle,
                                        string lpName);

  [DllImport ("kernel32.dll", SetLastError = true)]
  static extern IntPtr MapViewOfFile (IntPtr hFileMappingObject,
                                      FileRights dwDesiredAccess,
                                      uint dwFileOffsetHigh,
                                      uint dwFileOffsetLow,
                                      uint dwNumberOfBytesToMap);
  [DllImport ("Kernel32.dll")]
  static extern bool UnmapViewOfFile (IntPtr map);

  [DllImport ("kernel32.dll")]
  static extern int CloseHandle (IntPtr hObject);
person puikos    schedule 12.12.2011

Я полагаю, что .NET v2.0 не имеет встроенной поддержки разделяемой памяти. В лучшем случае мы можем PInvoke API CreateFileMapping и MapViewOfFile.

В моем сценарии IPC должен проходить на одной машине. Так что трубы - это самый быстрый вариант на данный момент.

Спасибо за ответы

person Community    schedule 13.01.2009

Взгляните на эту [ссылку]: http://www.albahari.com/nutshell/ch22.aspx в обертке общей памяти вы можете найти свой ответ.

person Esay    schedule 12.07.2016