2016-01-19 2 views
1

Я пытаюсь создать MemoryMappedFile для процесса с высокой степенью целостности, а затем открыть тот же файл с дочерним процессом с низкой целостностью и использовать эту общую память для IPC. Нет реального файла на диске (с использованием MemoryMappedFile.CreateNew).Получение доступа к MemoryMappedFile из процесса с низкой целостностью

Моя проблема заключается в том, что процесс с низкой целостностью не может открыть общую память, выбрасывая это: «System.UnauthorizedAccessException: доступ к пути запрещен». Я не удивлен, что это так, учитывая, что мне нужен доступ на запись из процесса с низкой целостностью, но как вы предоставляете ему доступ?

Вот мой код:


Средний процесс целостности:

MemoryMappedFileSecurity security = new MemoryMappedFileSecurity(); 
var file = MemoryMappedFile.CreateNew("test", 4096, MemoryMappedFileAccess.ReadWrite, MemoryMappedFileOptions.None, security, HandleInheritability.Inheritable); 

var view = file.CreateViewAccessor(); 
view.Write(0, true); 

процесс Низкая Целостность:

try 
{ 
    MemoryMappedFile file = MemoryMappedFile.OpenExisting("test", MemoryMappedFileRights.ReadWrite); 
    var view = file.CreateViewAccessor(); 
    var v = view.ReadBoolean(0); 
    Log.Info("MAPPED: " + v); 
} 
catch (Exception e) 
{ 
    Log.Info("Error: " + e); 
} 

работает хорошо, если оба процесса работают в среде целостности. После прочтения this, я попытался установить строку SDDL на процесс средней целостности, как это:

security.SetSecurityDescriptorSddlForm("S:(ML;;NW;;;LW)"); 

Но это дает мне еще одно исключение, на этот раз, когда создается отображенный файл памяти: «System.IO.IOException: A требуемая привилегия не удерживается клиентом ». Не совсем уверен, что это правильный способ сделать это в любом случае, я не совсем понимаю, как примеры Win32/C++ переходят на C# ...

Кто-нибудь знает об этом больше?

+0

Для изменения обязательного уровня целостности существующего объекта вам потребуется SeRelabelPrivilege. Если вы работаете с правами администратора, вы должны иметь возможность включить SeRelabelPrivilege, чтобы внести изменения. Если нет, я думаю, вам нужно будет указать уровень целостности при создании объекта. –

+0

... или вы можете отменить процесс и выполнить процесс с низкой целостностью, чтобы создать сопоставление памяти, а процесс среды-целостности открыть его. –

+0

Ах, право, но работа с правами администратора для меня не вариант :(Я думал, что я указываю уровень целостности при создании объекта (объект безопасности переходит в MemoryMappedFile.CreateNew в процессе целостности среды). С другой стороны, этот второй вариант, о котором вы говорили, может работать, я попробую его сегодня вечером. Спасибо! – Ollhak

ответ

1

Хорошо, получил рабочее решение. Были две проблемы:

  1. Попутный пустой объект MemoryMappedFileSecurity к MemoryMappedFile.CreateNew() сделал переведенный памяти недоступной даже тот же самый процесс. Это объясняет мою ошибку в моем комментарии («System.UnauthorizedAccessException: доступ к пути запрещен»).

  2. На самом деле я не смог получить security.SetSecurityDescriptorSddlForm (и хотя Google выявил несколько других попыток, никто из них не работал для меня). Вместо этого я использовал это решение: https://stackoverflow.com/a/14424623/5105846. Насколько я могу судить, он делает то же самое, но вместо этого использует PInvoke. Поэтому я просто позвонил InterProcessSecurity.SetLowIntegrityLevel(file.SafeMemoryMappedFileHandle), и он сделал его доступным из дочернего процесса с низкой целостностью. Успех!

Не идеальное решение, но работающий - это все, что мне нужно сейчас. Спасибо Гарри за вашу помощь!

+0

Увлекательный; что * не устанавливает уровень целостности во время создания. Вы передаете дескриптор, поэтому объект уже существует, что означает, что мое первоначальное предположение было ошибочным. (Я должен был подумать, чтобы попробовать это в собственном коде.) Чернила, если я могу понять, как класс .NET генерирует ошибку «требуемой привилегии»! Но пока у вас есть решение, я не думаю, что это действительно важно. +1. :-) –