API сеанса Windows не загружаются вовремя на Windows XP и способы обойти это - PullRequest
2 голосов
/ 29 октября 2011

Я пишу приложение-службу, которое должно перечислять все текущие сеансы пользователей и получать их идентификаторы сеансов, а затем посмотреть, какие процессы выполняются для какого сеанса. Я использую WTSEnumerateSessions() API, а также WTSQuerySessionInformation() для получения информации о сеансе. К сожалению, эти WTS API очень ненадежны.

На компьютере с Windows XP с отключенным быстрым переключением пользователей или на компьютере с XP, подключенным к домену, эти API-интерфейсы не доступны сразу. Они могут не работать с кодом ошибки RPC_S_INVALID_BINDING или 1702 в течение нескольких минут после загрузки Windows XP и запуска моей службы.

Я не смог найти никакой официальной документации, объясняющей, как справиться с таким ограничением. Единственный доступный через поисковик - это дождаться загрузки службы терминалов, что, конечно, возможно, но становится болью ОСНОВНОЙ в реализации **.

Так что, если бы кто-то мог ответить на следующее, я был бы признателен:

  1. Существуют ли альтернативные API для работы с данными, относящимися к сеансу, которые являются более надежными, чем эти WTS? Мне в основном нужно видеть текущие сеансы на компьютере, получать имя пользователя и статус сеанса. Также перечислите процессы с идентификаторами сеансов для каждого процесса. (Я знаю, что это возможно, поскольку GINA или экран входа в систему могут проделать все это до загрузки служб терминалов.)
  2. Существует ли 100% гарантия того, что API-интерфейсы класса WTS (такие как WTSEnumerateSessions(), WTSQuerySessionInformation() и WTSEnumerateProcesses()) будут загружаться до , когда мой сервис запускается на любой версия машины с Windows Vista / Windows 7?

Обратите внимание на и любые условия, которые ОЧЕНЬ важны.

Ответы [ 3 ]

4 голосов
/ 29 октября 2011

Другим API, который может быть полезен для вас, являются LsaEnumerateLogonSessions и LsaGetLogonSessionData SECURITY_LOGON_SESSION_DATA с полем Session.См. пример кода и этот .Чтобы получить информацию о сеансе процесса, вы можете использовать GetTokenInformation с TokenSessionId в качестве параметра.Для перечисления процессов вы можете использовать NtQuerySystemInformation (см. Мой старый ответ ).

3 голосов
/ 29 октября 2011

Здесь предлагается несколько решений здесь . В итоге:

  1. Убедитесь, что «TermSrv» запущен (через зависимости, запуск / ожидание вручную и т. Д.).
  2. Подождите, пока будет установлено событие "Global \ TermSrvReadyEvent".
1 голос
/ 29 октября 2011

Я думаю, что # 2, о котором вы спрашиваете, гарантированно в Vista / 7, поскольку эти API должны функционировать для создания любого процесса в любой сессии> 0.

...