Вопрос
При вызове InitializeSecurityContext
, какое значение я передаю параметру TargetName
?
Пересмотренный фон
Iвызываю функцию InitializeSecurityContext
:
InitializeSecurityContextA(
@pAS.hcred, //[in] credentials
phContext, //[in] optional] Context handle structure
pszTargetName, //[in, optional] Target name
0, //[in] context requirements
0, //[in] reserved1, must be zero
SECURITY_NATIVE_DREP, //[in] target data representation
pInput, //[in] optional] SecBufferDescription
0, //[in] reserved2, must be zero
@pAS.hctxt, //[in, out] pointer to context handle structure
@OutBuffDesc, //[in, out] pointer to SecBufferDesc
ContextAttributes, //[out] context attributes
@lifetime); //[out] expiration timestamp
Что мне передать pszTargetName
?
Я пробовал
null
: InitializeSecurityContextA(@pAS.hcred, phContext, null, ...);
""
: InitializeSecurityContextA(@pAS.hcred, phContext, "", ...);
"spn/HOSTNAME"
:InitializeSecurityContextA(@pAS.hcred, phContext, "spn/HOSTNAME", ...);
spn/HOSTNAME.DOMAIN.COM
: InitializeSecurityContextA(@pAS.hcred, phContext, "spn/HOSTNAME.DOMAIN.COM", ...);
"cargocult/PROGRAMMING"
: InitializeSecurityContextA(@pAS.hcred, phContext, "cargocult/PROGRAMMING", ...);
"http/TFS.DOMAIN.COM"
: InitializeSecurityContextA(@pAS.hcred, phContext, "http/TFS.DOMAIN.COM", ...);
"http/HOSTNAME"
: InitializeSecurityContextA(@pAS.hcred, phContext, "http/HOSTNAME", ...);
"qwertyasdf"
: InitializeSecurityContextA(@pAS.hcred, phContext, "qwertyasdf", ...);
"AuthSamp"
: InitializeSecurityContextA(@pAS.hcred, phContext, "AuthSamp", ...);
Все они либо терпят неудачу, либо переходят на NTLM.
Примечание : Моя машина подключена к домену, но домен не с именем domain.com
, или даже hostname.domain.com
, или даже qwertyasdf
.Поэтому я не удивлен, что эти попытки провалились.Но люди говорили, что попробуйте что-то вроде http/HOSTNAME
, поэтому я вставил http/HOSTNAME
.
Фон
InitializeSecurityContext
(переговоры) имеет функцию необязательный TargetName
параметр:
pszTargetName [in, необязательно]
Указатель на строку с нулем в конце, которая указывает имя участника службы(SPN) или контекст безопасности сервера назначения.
Приложения должны предоставить действительный SPN, чтобы помочь смягчить атаки повторного воспроизведения.
Что это должно быть?
Дополнительные сведения
Я пытаюсь проверить набор учетных данных пользователя, например:
Boolean ValidateCredentials(String username, String password, String domain)
{
...
}
Для проверки набора учетных данных пользователя необходимо использовать API SSPI.Первая функция для вызова - InitializeSecurityContext
.Одним из параметров InitializeSecurityContext
является "TargetName" string.
Я пытался оставить его null , но Application Verifier запускает точку останова, выписывая ошибку:
ОСТАНОВКА ВЕРЬЕРА 00005003: pid 0xF08:
InitializeSecurityContext использует целевую или недействительную цель для службы Kerberos.
Пожалуйста, смотрите значение pszTargetName для pszTargetNameцель.
00000000: не используется.
00000000: не
На этом этапе полезно помнить, что поставщик Negotiate
попытается использовать Kerberos
, ноотступление к NTLM
.В случае Negotiate
, Kerberos
или NTLM
параметр TargetName
задокументирован как :
Имя участника службы (SPN) или контекст безопасности конечного сервера.
Но что тогда мне передавать?
я попытался сделать то, что делает статья базы знаний SSPI, ничего (т.е. передать NULL
):
ss = _InitializeSecurityContext(
&pAS->hcred,
pAS->fInitialized ? &pAS->hctxt : NULL,
NULL, //<-------pszTargetName
0,
0,
SECURITY_NATIVE_DREP,
pAS->fInitialized ? &sbdIn : NULL,
0,
&pAS->hctxt,
&sbdOut,
&fContextAttr,
&tsExpiry);
Но ничего (т.е. NULL
) не работает.
Примечание: Статья KB была массово переписана в 2007 году. В своем первоначальном воплощении 1999 года они передали "AuthSamp"
в качестве цели, но это также не удалось.
Bonus Chatter:
имя участника службы
(SPN) Имя, по которому клиент однозначно идентифицирует экземпляр службы.Если вы устанавливаете несколько экземпляров службы на компьютерах по всему лесу, у каждого экземпляра должен быть свой собственный SPN.У данного экземпляра службы может быть несколько SPN, если есть несколько имен, которые клиенты могут использовать для аутентификации
контекст безопасности
Атрибуты или правила безопасности, которые действуют в настоящее время.Например, текущий пользователь вошел в систему на компьютере или персональный идентификационный номер, введенный пользователем смарт-карты.Для SSPI контекст безопасности - это непрозрачная структура данных, которая содержит данные безопасности, относящиеся к соединению, такие как ключ сеанса или указание продолжительности сеанса.
Бонус Chatter 2
Из документации для верификатора приложения:
Плагин Verifier обнаруживает следующие ошибки:
Пакет NTLM напрямую указывается в вызове AcquireCredentialsHandle (или более высокий уровень API оболочки).
Целевое имя в вызове InitializeSecurityContext - NULL.
Целевое имя в вызове InitializeSecurityContext не является правильно сформированным доменным именем в стиле SPN, UPN или NetBIOS.
Последние два случая заставят Negotiate вернуться к NTLM либо напрямую (первый случай), либо косвенно (контроллер домена вернет ошибку «принципал не найден» во втором случае)ведение переговоров к отступлению).
Плагин также регистрирует предупреждения при обнаружении перехода на NTLM;например, когда SPN не найден контроллером домена.Они регистрируются только как предупреждения, поскольку они часто являются законными случаями - например, при аутентификации в системе, которая не присоединена к домену.
В моем случае домен я являюсьпроверка на соответствие null
(так как я не знаю доменное имя машины, или даже если является доменом).Но результаты будут такими же, если жестко закодировать доменное имя моей машины разработки.
Обновление 3
Значения pszTargetName , которые вызывают ошибку AppVerifier, но вход в систему завершается успешно :
null
""
"AuthSamp"
"qwertyasdf"
- * имя домена, с которым я проверяю (например,
"avatopia.com"
) - * имя домена, к которому присоединен компьютер (например,
"avatopia.com"
) - * имя домена, в котором находится учетная запись пользователя (например,
"avatopia.com"
)
Значения pszTargetName , которые не вызывают ошибку AppVerifier, но входят в систему не удается :
"http/HOSTNAME"
"http/TFS.DOMAIN.COM"
"frob/GROBBER"
"cargocult/PROGRAMMING"
"spn/HOSTNAME"
"spn/HOSTNAME.DOMAIN.COM"
Значения pszTargetname , которые не вызывают ошибку AppVerifier, и вход в систему завершается успешно:
Обновление 4
WЧто я пытаюсь сделать: выяснить, если имя пользователя / пароль действительны.
- У меня есть имя пользователя: например,
"ian"
- У меня есть пароль: например,
"pass1"
Теперь есть еще один недостаток, что учетная записьian
может быть локальной учетной записью или domain учетной записью.И вам нужно решить, является ли ian
локальной или доменной учетной записью, прежде чем вы сможете спросить.Это связано с тем, что ian
может иметь двух учетных записей:
ian
в домене stackoverflow.com
ian
на локальном компьютере
Поэтому мне нужно указать, хочу ли я:
- задать конкретный домен (например,
stackoverflow.com
) или - задать локальный компьютер (который я 'll представляет как
"."
)
Теперь мы можем создать перекрестную ссылку:
Username Password Domain Machine on domain? Validate as
======== ======== ================= ================== ==============
iboyd pass1 . No Local account
iboyd pass1 (empty) No Local account
iboyd pass1 stackoverflow.com No Domain account
iboyd pass1 . Yes Local account
iboyd pass1 (empty) Yes Domain account
iboyd pass1 stackoverflow.com Yes Domain account
Обновление 5
Это может помочь объяснить, что я пытаюсь сделать, тогда, может быть, как сделать это станет легче.Допустим, я захожу в случайное офисное здание в центре города, захожу в случайную кабину и набираю случайное имя пользователя и пароль:
Я собираюсь попытаться войти вдомен TURBOENCABULATOR
.я указал, что хочу попробовать пройти аутентификацию на домене TURBOENCABULATOR
, указав в качестве префикса моего имени пользователя:
TURBOENCABULATOR\ian
Примечание: Я очень сомневаюсь, что в сети есть домен с именем turboencabulator, поскольку само название происходит только от от автоматизации Rockwell .Попытка входа в систему почти , безусловно, не удастся.Но как Windows проверяет их?
Как Windows пытается проверить эти учетные данные?Как Windows проверяет учетные данные:
- Имя пользователя : ian
- Пароль : pass1
- Домен : TURBOENCABULATOR
Делает Windows использовать Интерфейс пакета поддержки безопасности ? Если Windows использует Согласовать или Kerberos для аутентификации, что Windows передается в качестве параметра pszTarget
?Почти наверняка введенные мной учетные данные не будут действительными.Как Windows определит, действительны ли они?Какой API будет Windows вызывать для проверки учетных данных?
Windows может проверять учетные данные. Я хочу также проверить учетные данные.
Возможно, вместо того, чтобы пытаться подключиться к домену TURBOENCABULATOR
, я пытаюсь подключиться к домену turboencabulator.com
, предварительно добавивдомен для моего имени пользователя как turboencabulator.com\ian
:
Тот же вопрос применим.Как Windows проверяет учетные данные?Я хочу сделать то, что делает Windows.Предполагая, что Windows использует Kerberos для авторизации, что Windows передает в качестве параметра pszTargetName
в SSPI?
Возможно, вместо попытки подключиться к домену turboencabulator.com
, я пытаюсь подключиться к домену turboencabulator.net
:
Обратите внимание, что в этом примере я добавил имя домена к моему имени пользователя, а не , добавив it.
Возможно, вместо того, чтобы пытаться подключиться к домену turboencabulator.net
, я пытаюсь проверить пользователя как локальную (машинную) учетную запись, поставив перед моим именем пользователя .\
как:
Как Windows проверяет имя пользователя и пароль в локальной базе данных учетных записей?Использует ли он SSPI с пакетом Negotiate ?Если да, то какое значение он передает как pszTargetName
?
Люди говорят о веб-серверах, http, сервере Team Foundation.Я действительно не знаю, откуда они это получают.Или они говорят о редактировании пользователя в активной директории, чтобы убедиться, что что-то присутствует - я не понимаю, почему мне нужно что-либо редактировать: Windows ничего не редактирует.
Что TargetName
я использовал при вызове InitializeSecurityContext
для проверки набора учетных данных?
Бонус Chatter
Вот глава из документации Application Verifier о том, почему они имеютпроверка, если кто-то по ошибке использует NTLM:
Почему необходим плагин NTLM
NTLM - это устаревший протокол аутентификации с недостатками, которые могут поставить под угрозу безопасность приложений и операционной системы.система.Наиболее важным недостатком является отсутствие проверки подлинности сервера, что может позволить злоумышленнику обманом заставить пользователей подключиться к поддельному серверу.Как следствие отсутствия аутентификации на сервере, приложения, использующие NTLM, также могут быть уязвимы к типу атаки, известной как атака «отражения».Последнее позволяет злоумышленнику перехватить сеанс аутентификации пользователя на легитимном сервере и использовать его для аутентификации злоумышленника на компьютере пользователя.Уязвимости NTLM и способы их использования являются целью увеличения исследовательской активности в сообществе безопасности.
Хотя Kerberos был доступен в течение многих лет, многие приложения до сих пор написаны для использования только NTLM.Это излишне снижает безопасность приложений.Однако Kerberos не может заменить NTLM во всех сценариях - главным образом в тех, где клиент должен пройти аутентификацию в системах, которые не присоединены к домену (домашняя сеть, возможно, является наиболее распространенной из них).Пакет безопасности Negotiate обеспечивает обратно-совместимый компромисс, который использует Kerberos всякий раз, когда это возможно, и возвращается к NTLM только тогда, когда нет другой возможности.Переключение кода для использования Negotiate вместо NTLM значительно повысит безопасность для наших клиентов, в то же время предоставляя лишь небольшое количество приложений или вообще не совместимыхностей,. Договариваться само собой не серебряная пуля - есть
случаи, когда злоумышленник может принудительно перейти на NTLM, но это
значительно сложнее в эксплуатации. Тем не менее, один немедленный
улучшение заключается в том, что приложения, написанные для правильного использования, ведут переговоры
автоматически защищены от атак отражения NTLM.
В качестве последнего слова предостережения против использования NTLM: в будущем
версии Windows можно будет отключить использование NTLM на
операционная система. Если приложения имеют жесткую зависимость от NTLM
они просто не смогут аутентифицироваться, когда NTLM отключен.
Как работает плагин
Штекер Verifier обнаруживает следующие ошибки:
Пакет NTLM указывается непосредственно в вызове AcquireCredentialsHandle (или API-оболочки более высокого уровня).
Целевое имя в вызове InitializeSecurityContext равно NULL.
Целевое имя в вызове InitializeSecurityContext не является правильно сформированным доменным именем в стиле SPN, UPN или NetBIOS.
Последние два случая заставят Negotiate вернуться к NTLM либо напрямую (первый случай), либо косвенно (контроллер домена вернет ошибку «принципал не найден» во втором случае, в результате чего Negotiate будет откатан).
Плагин также регистрирует предупреждения при обнаружении перехода на NTLM; например, когда SPN не найден контроллером домена. Они регистрируются только как предупреждения, поскольку они часто являются законными случаями, например, при аутентификации в системе, которая не присоединена к домену.
NTLM Остановки
5000 - Приложение явно выбрало пакет NTLM
Серьезность - Ошибка
Приложение или подсистема явно выбирают NTLM вместо Negotiate при вызове AcquireCredentialsHandle. Даже если клиент и сервер могут пройти аутентификацию с использованием Kerberos, это предотвращается явным выбором NTLM.
Как исправить эту ошибку
Исправление этой ошибки - вместо пакета NTLM выбрать пакет согласования. Как это сделать, будет зависеть от конкретной сетевой подсистемы, используемой клиентом или сервером. Некоторые примеры приведены ниже. Вам следует обратиться к документации по конкретной библиотеке или набору API, который вы используете.
APIs(parameter) Used by Application Incorrect Value Correct Value
===================================== =============== ========================
AcquireCredentialsHandle (pszPackage) “NTLM” NEGOSSP_NAME “Negotiate”
Смотри также