Форум: "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.054 c