Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "WinAPI";
Текущий архив: 2007.08.26;
Скачать: [xml.tar.bz2];

Вниз

CreateProcessAsUserW и ошибка ERROR_PIPE_NOT_CONNECTED   Найти похожие ветки 

 
Eraser ©   (2007-02-28 21:46) [0]

Имеется сервис, который работает с правами системы. Он отслеживает подключение терминальных сессий, при подключении новой терминальной сесии, внутри этой сесии создается процесс с правами, такими же как у сервиса. Код следующий:

var
 hToken, hNewToken: Cardinal;
 si: STARTUPINFOW;
 pi: PROCESS_INFORMATION;
 SessionId: Cardinal;
...
SessionId := WTSGetActiveConsoleSessionId;
...
   stSystemUserSession: // Текущая терминальная сессия с правами системы.
     begin
       if not OpenProcessToken(GetCurrentProcess,
         TOKEN_QUERY or TOKEN_DUPLICATE, hToken) then
       begin
          AppendLog("Error WTSStartProcess - OpenProcessToken " + IntToStr(GetLastError));
          Exit;
       end;
       if not DuplicateTokenEx(hToken, MAXIMUM_ALLOWED, nil, SecurityIdentification,
         TokenPrimary, hNewToken) then
       begin
         AppendLog("Error WTSStartProcess - DuplicateTokenEx " + IntToStr(GetLastError));
         Exit;
       end;
       if not SetTokenInformation(hNewToken,
         TokenSessionId, @SessionId, SizeOf(Cardinal)) then
       begin
          AppendLog("Error WTSStartProcess - SetTokenInformation " + IntToStr(GetLastError));
          Exit;
       end;
       // Запуск процесса.
       try
         si.lpDesktop := "";
         if CreateProcessAsUserW(hNewToken, nil, PWideChar(APath),
           nil, nil, false, 0, nil, nil, si, pi) then
         begin
           CloseHandle(pi.hProcess);
           CloseHandle(pi.hThread);
         end
         else
         begin
           AppendLog("Error WTSStartProcess - CreateProcessAsUserW " + IntToStr(GetLastError));
           Exit;
         end;
       finally
         CloseHandle(hToken);
         CloseHandle(hNewToken);
       end;
     end;


Теперь о проблеме.
Запускаем данный сервис в ОС WinXP, логиним первого пользователя (данный код не выполняем, т.к. первый пользователь в XP находится в 0 терм. сесии), делаем SwitchUser, логиним второго пользователя - данный код успешно отрабатывает, в 1 терминальной сессии запускается интересующий нас процесс с правами системы. Делаем LogOff этого второго пользователя (при этом создается еще одна терм. сессии, в которой отображается Logon экран после Logoff"а этого юзера) и, как говориться, баста хрю - функция CreateProcessAsUserW возвращает ошибку ERROR_PIPE_NOT_CONNECTED.

Самое удивительное то, что в Висте данный код работает всегда, проблема только в XP (в 2003 не проверял еще).

PS
пробовал CreateProcessAsUser (ANSI версию) - те же грабли.

PPS
Заранее спасибо знатокам внутренностей ОС!


 
Игорь Шевченко ©   (2007-02-28 22:11) [1]


> CreateProcessAsUserW возвращает ошибку ERROR_PIPE_NOT_CONNECTED


Не может соединиться с \\.\Pipe\TerminalServer\SystemExecSrvr\номер_сеанса
По этому соединению как раз и передается запрос на создание процесса в CreateProcessAsUser.

Насколько я могу судить, эта pipe создается WinLogon"ом, а вот в какой момент - сказать не могу. Весьма вероятно, когда пользователь войдет в систему в этой сессии.


 
Eraser ©   (2007-02-28 22:19) [2]

> [1] Игорь Шевченко ©   (28.02.07 22:11)


> Весьма вероятно, когда пользователь войдет в систему в этой
> сессии.


> а вот в какой момент

Пробовал ставить тайм-ауты вплоть до 10 секунд - эффекта 0.

> Весьма вероятно, когда пользователь войдет в систему в этой
> сессии

проблема в том, что пользователь может никогда не войти в эту терм. сессию, т.к. можно вернуться к 0 терм. сессии (выбрав 1 пользователя, который уже залогинен), тогда эта будет уничтожена. Да и каким-то образом все это работает в Висте и в XP у конкурентов. Может с переменными окружения что-то.. уже сталкивался с подобной проблемой, когда была похожая задача, но нужно было запускать процесс от имени текущего юзера, решилось изпользованием CreateEnvironmentBlock, но и ошибка тогда другая была и только в Висте.. В общем не знаю даже куда, как говориться, копать ))


 
Игорь Шевченко ©   (2007-02-28 22:30) [3]

Eraser ©   (28.02.07 22:19) [2]

(на всякий случай) - а какую функциональность надо реализовать, если не очень большой секрет, может, иным способом можно как-нибудь ?


 
Игорь Шевченко ©   (2007-02-28 22:31) [4]


> Самое удивительное то, что в Висте данный код работает всегда


На всякий случай - в Висте изменился механизм нотификаций WinLogon"а, а сабжевый pipe в XP создается в wlnotify.dll


 
Eraser ©   (2007-02-28 22:35) [5]

> [3] Игорь Шевченко ©   (28.02.07 22:30)

Нужно запускать программу именно с правами системы (даже прав админа мало) для перехвата изображения и эмуляции мыши/клавиатуры (удаленное администрирование) в т.ч. и на Logon экране. По-другому реализовать можно и до последнего времени оно и было реализовано - через winlogon notification packages, но тот способ менее удобен по нескольким веским причинам.
Да и повторюсь, конкуренты как-то реализовали все через сервис, значит это реально :) проблема скорее всего в какой-то мелочи...


 
Eraser ©   (2007-02-28 22:39) [6]

> [4] Игорь Шевченко ©   (28.02.07 22:31)

так ведь дело тут не в нотификации, нотификация то успешно приходит.


 
Eraser ©   (2007-03-01 23:54) [7]

> [1] Игорь Шевченко ©   (28.02.07 22:11)
>
> > CreateProcessAsUserW возвращает ошибку ERROR_PIPE_NOT_CONNECTED
>
>
> Не может соединиться с \\.\Pipe\TerminalServer\SystemExecSrvr\номер_сеанс
> а

Сразу после логоффа подсоединился к 1 пользователю (тот который в 0 терм. сессии) через RDP, и с пом. ProcessExplorer"а увидел, что во второй терм. сессии (там где в данный момент отображается логон-экран реальной терм. сессии) в процессе winlogon существует
\Device\NamedPipe\TerminalServer\SystemExecSrvr\2

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


 
Игорь Шевченко ©   (2007-03-02 10:04) [8]


> кстати посмотреть праметры безопасности этого пайпа не удалось,
>  видимо прав не хватило у процесс эксплорера


Может, прав не хватило и у процесса, который попытался соединиться с этим пайпом ?


 
Eraser ©   (2007-03-02 19:01) [9]

> [8] Игорь Шевченко ©   (02.03.07 10:04)

возможно, я об этом тоже думал.. т.к. ошибку 5 CreateProcessAsUser возвращает в том случае, если нет прав для запуска целевой программы, а не доступа к пайпу винлогона.
но права то у программы системные, на сколько мне известно, учетная запись System обладает максимальными правами.. или я ошибаюсь?
возможно какой-то привелегии нет, только какой неизвестно...


 
Игорь Шевченко ©   (2007-03-02 23:01) [10]

Eraser ©   (02.03.07 19:01) [9]

Pipe можно создать на какой-то момент (например, пока нет пользователя) с правами, когда никто, кроме создателя, не может ее открывать (это уже свободный полет мысли, разумеется, но desktop winlogon"а может быть недоступен даже учетной записи LocalSystem


 
Eraser ©   (2007-03-03 19:10) [11]

> [10] Игорь Шевченко ©   (02.03.07 23:01)

Dacl пайпа, как в момент когда CreateProcessAsUser корректно отрабатывает (т.е. когда к терм. сессии подключен пользователь), так и в момент, когда сессия находится в состоянии простоя, содержит 5 ACE"ов, содержимое их еще не смотрел (сегодня гляну), но скорее всего вряд ли они отличаются.
Еще одно наблюдение:
включаем компьютер, дожидаемся появления логон-экрана (есть 2 и более пользователя, FUS включен). Теперь подключаемся к какому-либо юзеру через RDP, при этом подключение происходит к 0 терм. сессии. Соответственно теперь через РДП process explorer"ом можно увидеть объекты winlogon"а. Так вот, когда винлогон в 0 терм. сесии у него вообще нету пайпа "\\.\Pipe\TerminalServer\SystemExecSrvr\номер_сеанса", тем не менее конкуренсткий софт каким-то образом создает процессы таким же образом, как и в описаном мной в 0 сообщении случае, при этом в запущенных процессах включены привелегии SE_ASSIGNPRIMARYTOKEN_NAME, SE_CREATE_TOKEN_NAME, SE_TAKE_OWNERSHIP_NAME.. остальные как и у других сервисов по-умолчанию. В случае же когда к терм. сесии подключен пользователь - привилегии такие же как и у самого сервиса, но в этом случае и у меня проблем нет.
Отсюда напрашивается вывод, что CreateProcessAsUser функциклирует не или не только через указанный пайп. Может подскажите, где можно подробнее почитать об устройстве данной функции, литература имеется, но при беглом просмотре не нашел ничего, за что можно было бы зацепиться.


 
Игорь Шевченко ©   (2007-03-03 23:22) [12]

Eraser ©   (03.03.07 19:10) [11]

Обращение к пайпу происходит только в случае, если сессия создателя отличается от сессии, в которой надо создать процесс. Сессия, в которой надо создать процесс, определяется по Token"у.


 
Eraser ©   (2007-03-04 00:31) [13]

> [12] Игорь Шевченко ©   (03.03.07 23:22)


> Обращение к пайпу происходит только в случае, если сессия
> создателя отличается от сессии, в которой надо создать процесс.

именно это я и имел ввиду, эта ошибка появляется даже когда текущей терм. сессией является 0 (но не залогинен ни один пользователь) и, к примеру, необходимо создать процесс в ней же, с использованием функции CreateProcessAsUser, при этом просто CreateProcess, в этом случае, справляется на ура..


 
Eraser ©   (2007-03-04 22:23) [14]

> [13] Eraser ©   (04.03.07 00:31)


> эта ошибка появляется даже когда текущей терм. сессией является
> 0 (но не залогинен ни один пользователь)

ошибся! в этом случае всё срабатывает!


 
Eraser ©   (2007-03-05 00:05) [15]

Убил процесс эксплорером этот пайп в винлогоне, у меня стало писать ошибку 2, т.е. файл не существует при CreateProcessAsUser, а вражеский софт как работал так и работает ((


 
Игорь Шевченко ©   (2007-03-05 11:31) [16]

Eraser ©   (05.03.07 00:05) [15]

Значит, вражеский софт не использует CreateProcessAsUser для создания процесса в другом сеансе.


 
Eraser ©   (2007-03-05 19:14) [17]

> [16] Игорь Шевченко ©   (05.03.07 11:31)

но внедрени в Винлогон и пакджи он тоже не использует )

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

а как можно еще запустить процесс в другом сеансе? можно ли подменить сеанс в токене уже запущенного процесса?


 
Игорь Шевченко ©   (2007-03-05 22:50) [18]

Eraser ©   (05.03.07 19:14) [17]

Взял бы уже 10 раз посмотрел бы, какие функции использует софт конкурентов :)
ApiMon, WinDbg, Tdump, наконец :)


 
Eraser ©   (2007-03-05 22:52) [19]

> [18] Игорь Шевченко ©   (05.03.07 22:50)

щас как раз скачиваю SoftICE )

> ApiMon, WinDbg

тоже гляну )


 
Eraser ©   (2007-03-05 22:55) [20]

> Взял бы уже 10 раз посмотрел бы

да там защиты куча от дебагеров, попробовал старым добрым win32ds - обломался, сейчас тяжелую артилерию подключу )


 
Eraser ©   (2007-03-07 01:11) [21]

Разорбался! :) нужно внежрять код в winlogon... буду реализовывать..


 
Германн ©   (2007-03-07 01:16) [22]


> нужно внежрять код в winlogon

Это что? Новый хакерский способ - внежрять код в...? :)


 
Eraser ©   (2007-03-07 01:27) [23]

> [22] Германн ©   (07.03.07 01:16)

он самый ))



Страницы: 1 вся ветка

Форум: "WinAPI";
Текущий архив: 2007.08.26;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.52 MB
Время: 0.051 c
2-1185996421
Мануха
2007-08-01 23:27
2007.08.26
chart


15-1185449901
Галинка
2007-07-26 15:38
2007.08.26
.pdf на ПДА


2-1185727193
mfender
2007-07-29 20:39
2007.08.26
TADOConnection. Запуск редактора строки подключения


4-1173117533
Альберт
2007-03-05 20:58
2007.08.26
почему не обновляется окно?


15-1185829929
DillerXX
2007-07-31 01:12
2007.08.26
Я сделал это! Никто не хочет померяться у кого меньше? ;)





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский