Обмен данными между сеансами пользователя windows с использованием файла MemoryMapped в c# - PullRequest
0 голосов
/ 08 мая 2020

Я хочу ограничить использование приложения одним сеансом пользователя. Эта часть отлично работает частично на основе этой топи c. Тем не менее, я также хочу дать отзыв второму пользователю и пользователю о том, кто использует экземпляр и когда он был запущен. Для этого я хочу использовать MemoryMappedFile (не в файловой системе, а в файле подкачки).

        private MemoryMappedFile StoreUsageInfo(UsageInfoData data)
        {
            var securitySettings = new MemoryMappedFileSecurity();
            securitySettings.AddAccessRule(new AccessRule<MemoryMappedFileRights>(new SecurityIdentifier(WellKnownSidType.WorldSid, null), MemoryMappedFileRights.FullControl, AccessControlType.Allow));

            var mmf = MemoryMappedFile.CreateNew($@"Global\{appGuid}", 1000, MemoryMappedFileAccess.ReadWrite, MemoryMappedFileOptions.DelayAllocatePages, securitySettings, HandleInheritability.Inheritable);

            using (MemoryMappedViewStream stream = mmf.CreateViewStream(0,0,MemoryMappedFileAccess.ReadWrite))
            {
                var formatter = new BinaryFormatter();
                formatter.Serialize(stream, data);
            }

            return mmf;
        }

        private UsageInfoData GetUsageInfo()
        {
            using (var mmf = MemoryMappedFile.OpenExisting($@"Global\{appGuid}", MemoryMappedFileRights.Read))
            using (var accessor = mmf.CreateViewAccessor(0, 1000, MemoryMappedFileAccess.Read))
            using (MemoryMappedViewStream stream = mmf.CreateViewStream(0, 0, MemoryMappedFileAccess.Read))
            {
                var formatter = new BinaryFormatter();

                return (UsageInfoData)formatter.Deserialize(stream);
            }
        }

Примечание: объект, возвращаемый методом StoreUsageInfo, удаляется при выходе из процесса.

Если первый экземпляр запускается администратором, второй экземпляр может читать данные, хранящиеся в файле с отображением памяти. Однако, если первый экземпляр запущен вызовом непривилегированного пользователя к CreateNew, выдает System.UnauthorizedAccessException: Access to the path is denied.

Согласно ответу от здесь и комментарию, требуется создание MMF SeCreateGlobalPrivilege привилегия, если не сохраняется (API вызывается с INVALID_HANDLE_VALUE для файла). Насколько я знаю, CreateNew должно быть именно в этом случае.

Предоставление привилегии «Создавать глобальные объекты» в локальной политике решает проблему. Комментарий неправильный или устаревший? Есть ли какой-либо другой аналогичный простой временный способ публикации данных, которые могут быть прочитаны во время сеанса пользователя?

...