[sspi,negotiate] improve /auth-pkg-list parsing

* add 'none' keyword to allow disabling all methods, selectively
  enabling by adding
* improve option description
* fix reading of ini file settings
This commit is contained in:
akallabeth
2025-08-29 11:45:14 +02:00
parent a1749ef5f0
commit 3a34545a75
2 changed files with 37 additions and 12 deletions

View File

@@ -66,8 +66,11 @@ static const COMMAND_LINE_ARGUMENT_A global_cmd_args[] = {
"Audio output mode" },
{ "auth-only", COMMAND_LINE_VALUE_BOOL, NULL, BoolValueFalse, NULL, -1, NULL,
"Authenticate only" },
{ "auth-pkg-list", COMMAND_LINE_VALUE_REQUIRED, "<!ntlm,kerberos>", NULL, NULL, -1, NULL,
"Authentication package filter (comma-separated list, use '!' to exclude)" },
{ "auth-pkg-list", COMMAND_LINE_VALUE_REQUIRED, "[[none],]<!ntlm,kerberos,!u2u>", NULL, NULL,
-1, NULL,
"Authentication package filter (comma-separated list, use '!' to disable). By default "
"all methods are enabled. Use explicit 'none' as first argument to disable all methods, "
"selectively enabling only the ones following." },
{ "authentication", COMMAND_LINE_VALUE_BOOL, NULL, BoolValueTrue, NULL, -1, NULL,
"Authentication (experimental)" },
{ "auto-reconnect", COMMAND_LINE_VALUE_BOOL, NULL, BoolValueFalse, NULL, -1, NULL,

View File

@@ -41,6 +41,11 @@
static const char NEGO_REG_KEY[] =
"Software\\" WINPR_VENDOR_STRING "\\" WINPR_PRODUCT_STRING "\\SSPI\\Negotiate";
static const char PACKAGE_NAME_DISABLE_ALL[] = "none";
static const char PACKAGE_NAME_NTLM[] = "ntlm";
static const char PACKAGE_NAME_KERBEROS[] = "kerberos";
static const char PACKAGE_NAME_KERBEROS_U2U[] = "u2u";
typedef struct
{
const TCHAR* name;
@@ -252,18 +257,18 @@ static BOOL negotiate_get_dword(HKEY hKey, const char* subkey, DWORD* pdwValue)
static BOOL negotiate_get_config_from_auth_package_list(void* pAuthData, BOOL* kerberos, BOOL* ntlm,
BOOL* u2u)
{
BOOL rc = FALSE;
char* tok_ctx = NULL;
char* tok_ptr = NULL;
char* PackageList = NULL;
if (!sspi_CopyAuthPackageListA((const SEC_WINNT_AUTH_IDENTITY_INFO*)pAuthData, &PackageList))
return FALSE;
tok_ptr = strtok_s(PackageList, ",", &tok_ctx);
char* tok_ptr = strtok_s(PackageList, ",", &tok_ctx);
while (tok_ptr)
{
char* PackageName = tok_ptr;
const char* PackageName = tok_ptr;
BOOL PackageInclude = TRUE;
if (PackageName[0] == '!')
@@ -272,28 +277,42 @@ static BOOL negotiate_get_config_from_auth_package_list(void* pAuthData, BOOL* k
PackageInclude = FALSE;
}
if (_stricmp(PackageName, "ntlm") == 0)
if (_stricmp(PackageName, PACKAGE_NAME_NTLM) == 0)
{
*ntlm = PackageInclude;
}
else if (_stricmp(PackageName, "kerberos") == 0)
else if (_stricmp(PackageName, PACKAGE_NAME_KERBEROS) == 0)
{
*kerberos = PackageInclude;
}
else if (_stricmp(PackageName, "u2u") == 0)
else if (_stricmp(PackageName, PACKAGE_NAME_KERBEROS_U2U) == 0)
{
*u2u = PackageInclude;
}
else if (_stricmp(PackageName, PACKAGE_NAME_DISABLE_ALL) == 0)
{
*kerberos = FALSE;
*ntlm = FALSE;
*u2u = FALSE;
if (PackageName != PackageList)
{
WLog_WARN(TAG, "Special keyword '%s' not first in list, aborting", PackageName);
goto fail;
}
}
else
{
WLog_WARN(TAG, "Unknown authentication package name: %s", PackageName);
WLog_WARN(TAG, "Unknown authentication package name: %s, ignoring", PackageName);
}
tok_ptr = strtok_s(NULL, ",", &tok_ctx);
}
rc = TRUE;
fail:
free(PackageList);
return TRUE;
return rc;
}
static BOOL negotiate_get_config(void* pAuthData, BOOL* kerberos, BOOL* ntlm, BOOL* u2u)
@@ -328,11 +347,14 @@ static BOOL negotiate_get_config(void* pAuthData, BOOL* kerberos, BOOL* ntlm, BO
{
DWORD dwValue = 0;
if (negotiate_get_dword(hKey, "kerberos", &dwValue))
if (negotiate_get_dword(hKey, PACKAGE_NAME_KERBEROS, &dwValue))
*kerberos = (dwValue != 0) ? TRUE : FALSE;
if (negotiate_get_dword(hKey, PACKAGE_NAME_KERBEROS_U2U, &dwValue))
*u2u = (dwValue != 0) ? TRUE : FALSE;
#if !defined(WITH_KRB5_NO_NTLM_FALLBACK)
if (negotiate_get_dword(hKey, "ntlm", &dwValue))
if (negotiate_get_dword(hKey, PACKAGE_NAME_NTLM, &dwValue))
*ntlm = (dwValue != 0) ? TRUE : FALSE;
#endif