Проблема с разрешениями при публикации в WMI под учетной записью сетевой службы - PullRequest
7 голосов
/ 03 февраля 2010

Я добавляю публикацию WMI в службу Windows на основе .net Framework 3.5, которая работает под учетной записью «сетевой службы».

Согласно документу , с которым я столкнулся на MSDN , учетная запись «сетевой службы» по умолчанию должна иметь разрешения на публикацию WMI. (" По умолчанию следующие пользователи и группы могут публиковать данные и события: ... Сетевая служба , ... ")

Однако, когда служба вызывает Instrumentation.Publish (myStatusClassInstance), она выдает исключение DirectoryNotFoundException;

System.IO.DirectoryNotFoundException was unhandled
Message: Could not find a part of the path 'C:\Windows\system32\WBEM\Framework\root\MyWMINamespace\MyService_SN__Version_1.0.3686.26280.cs'.

.. похоже, что System.Management.Instrumentation пытается сгенерировать код на лету, а при работе в сетевой службе выбирает каталог, для которого у сетевой службы нет разрешений.

Как лучше всего это исправить? Могу ли я переопределить целевой каталог code-gen в app.config или в коде? Я не хочу возиться с разрешениями файловой системы при развертывании службы ...

Обновление : я думаю, что это «особенность», когда старый код FX вступает в противоречие с новыми настройками безопасности в Win7. Внутри себя управляемые классы WMI извлекают каталог установки WMI из реестра и используют его в качестве пути вывода для сгенерированного кода. К сожалению, многим пользователям не разрешено (или предполагается) писать что-то под% SystemRoot% ... ... Я подал ошибку подключения ( # 530392 ), чтобы посмотреть, сможет ли MSFT внести ясность и / или предоставить исправление или обходной путь.

Обновление 2: Я предполагаю, что для обычных учетных записей пользователей это не проблема, потому что виртуализация UAC включится и сохранит файлы в другом месте. Однако, очевидно, учетная запись «сетевой службы» не покрывается виртуализацией UAC. (?)

Обновление 3: Добавлена ​​награда 550pt. Простые ограничения: служба Windows на основе .net framework 3.5, работающая как сетевая служба, должна иметь возможность публиковать данные через WMI с использованием System.Management.Instrumentation в Win7 и Win2008 [RTM & R2] с разрешениями / параметрами безопасности по умолчанию и без обращения к модификация фреймворка внутренними / приватными членами с помощью отражения. «Из коробки», но чистые решения приветствуются. Откроет второй связанный bounty-Q в качестве заполнителя для другого 550pt, если SO позволяет.

Обновление вознаграждения: Я намерен удвоить вознаграждение за этот вопрос путем повторного ручного вопроса, который будет служить заполнителем вознаграждения:
https://stackoverflow.com/questions/2208341/bounty-placeholder (<- По-видимому, это было запрещено, поэтому вопрос о заполнителях был закрыт полицией этикета SO.) </p>

Обновление 4: Это становится все лучше и лучше. Я заметил, что installutil записывал недостающие файлы в c: \ windows \ syswow64 ... и т.д ..., поэтому я понял, что для установки службы я использовал 32-разрядную версию installutil, но служба работала как 64-битный процесс. Очевидным побочным эффектом было то, что код, сгенерированный во время работы installutil, оказался в syswow64 (32-разрядный системный каталог), а служба искала его в 64-разрядном системном каталоге (system32). (<- не по теме, но мне очень нравится, как MSFT удалось переключаться между именами там ... :)). </p>

Поэтому я попытался установить службу с 64-разрядной версией installutil. Это с треском провалилось из-за ошибок разрешения в пути% sysroot% \ wbem \ framework ... etc ... Затем я перекомпилировал сервис как x86 и зарегистрировал его снова, используя 32-битную версию installutil. Это привело к совершенно новому исключению:

System.Exception: The code generated for the instrumented assembly failed to compile.
   at System.Management.Instrumentation.InstrumentedAssembly..ctor(Assembly assembly, SchemaNaming naming)
   at System.Management.Instrumentation.Instrumentation.Initialize(Assembly assembly)
   at System.Management.Instrumentation.Instrumentation.GetInstrumentedAssembly(Assembly assembly)
   at System.Management.Instrumentation.Instrumentation.GetPublishFunction(Type type)
   at System.Management.Instrumentation.Instrumentation.Publish(Object instanceData)
   at SomeService.InstanceClass.PublishApp(String name) in e:\work\clientname\SomeService\SomeService\WMIProvider.cs:line 44
   at SomeService.SomeServiceService..ctor() in e:\work\clientname\SomeService\SomeService\SomeServiceService.cs:line 26
   at SomeService.Program.Main() in e:\work\clientname\SomeService\SomeService\Program.cs:line 17

... все ближе ...

Ответы [ 3 ]

2 голосов
/ 10 февраля 2010

Проверяли ли вы свою сборку с помощью installutil ? Это должно дать вам журнал проблем установки. (Но так как вы не можете запустить его как учетную запись сетевой службы, она может не отображать проблему, с которой вы столкнулись.)

Кроме того, вы уверены, что эта служба должна работать под учетной записью сетевой службы?

Из-за риска уязвимости при запуске служб Windows в привилегированных учетных записях Microsoft создала эти специальные учетные записи служб с некоторыми ограничениями, которые были усилены в Vista и Win7. Начиная с Vista, Microsoft ограничивала количество служб, работающих под этой учетной записью, в пользу менее привилегированных (см. эту статью ). Учетная запись сетевой службы (также называемая «NT AUTHORITY \ NETWORK SERVICE») может получать доступ к сети (действуя как учетная запись локального компьютера PCNAME $), но у нее ограничены права на локальном компьютере (в отличие от учетной записи локальной системы).

Вы проверили разрешения безопасности WMI для ветви, которую использует ваша сборка? Запустите wmimgmt.msc и закопайте ... Когда я сделал быструю проверку некоторых случайных веток, я увидел, что учетная запись сетевой службы не имеет прав на запись.

Наконец, я бы предложил использовать Sysinternals 'ProcMon , который позволил бы вам фильтровать только этот процесс и проверять наличие ошибок «Отказано в доступе» в настройках файла или реестра. Этот инструмент за многие годы решил для меня много проблем.

2 голосов
/ 10 февраля 2010

Я считаю, что проблема не в публикации данных, а в регистрации такого типа в WMI в первый раз.

Если вы изучите код System.Management.Instrumentation в рефлекторе или другом дизассемблере, то увидите, что сборка, которая собирается опубликовать, не была зарегистрирована, тогда код попытается зарегистрируйте сборку и сохраните информацию о сборке в специально названном подкаталоге в папке установки WBEM.

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

1 голос
/ 12 февраля 2010

Не уверен, подняли ли вы его или кого-то еще, но, пожалуйста, посмотрите: http://connect.microsoft.com/VisualStudio/feedback/details/530392/wmi-publishing-fails-on-permission-error-please-provide-a-way-to-override-codepath-in-system-management-instrumentation-schemanaming-in-app-config-web-config

Это может помочь вам лучше понять основную причину проблемы

...