Add _krb5_store_string_to_reg_value() for Windows
The new _krb5_store_string_to_reg_value() function permits the caller to create REG_SZ, REG_EXPAND_SZ, REG_DWORD, and REG_MULTI_SZ entries in the registry. Change-Id: Ib5740ad07209618d8ea4c0bf3c75615f27e98b4e
This commit is contained in:
@@ -51,7 +51,8 @@ DLLSDKDEPS= \
|
|||||||
$(PTHREAD_LIB) \
|
$(PTHREAD_LIB) \
|
||||||
secur32.lib \
|
secur32.lib \
|
||||||
shell32.lib \
|
shell32.lib \
|
||||||
dnsapi.lib
|
dnsapi.lib \
|
||||||
|
shlwapi.lib
|
||||||
|
|
||||||
DEF=$(OBJ)\heimdal.def
|
DEF=$(OBJ)\heimdal.def
|
||||||
|
|
||||||
|
@@ -35,9 +35,179 @@
|
|||||||
#error config_reg.c is only for Windows
|
#error config_reg.c is only for Windows
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include <shlwapi.h>
|
||||||
|
|
||||||
|
#ifndef MAX_DWORD
|
||||||
|
#define MAX_DWORD 0xFFFFFFFF
|
||||||
|
#endif
|
||||||
|
|
||||||
#define REGPATH_KERBEROS "SOFTWARE\\Kerberos"
|
#define REGPATH_KERBEROS "SOFTWARE\\Kerberos"
|
||||||
#define REGPATH_HEIMDAL "SOFTWARE\\Heimdal"
|
#define REGPATH_HEIMDAL "SOFTWARE\\Heimdal"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Store a string as a registry value of the specified type
|
||||||
|
*
|
||||||
|
* The following registry types are handled:
|
||||||
|
*
|
||||||
|
* - REG_DWORD: The string is converted to a number.
|
||||||
|
*
|
||||||
|
* - REG_SZ: The string is stored as is.
|
||||||
|
*
|
||||||
|
* - REG_EXPAND_SZ: The string is stored as is.
|
||||||
|
*
|
||||||
|
* - REG_MULTI_SZ:
|
||||||
|
*
|
||||||
|
* . If a separator is specified, the input string is broken
|
||||||
|
* up into multiple strings and stored as a multi-sz.
|
||||||
|
*
|
||||||
|
* . If no separator is provided, the input string is stored
|
||||||
|
* as a multi-sz.
|
||||||
|
*
|
||||||
|
* - REG_NONE:
|
||||||
|
*
|
||||||
|
* . If the string is all numeric, it will be stored as a
|
||||||
|
* REG_DWORD.
|
||||||
|
*
|
||||||
|
* . Otherwise, the string is stored as a REG_SZ.
|
||||||
|
*
|
||||||
|
* Other types are rejected.
|
||||||
|
*
|
||||||
|
* If cb_data is MAX_DWORD, the string pointed to by data must be nul-terminated
|
||||||
|
* otherwise a buffer overrun will occur.
|
||||||
|
*
|
||||||
|
* @param [in]valuename Name of the registry value to be modified or created
|
||||||
|
* @param [in]type Type of the value. REG_NONE if unknown
|
||||||
|
* @param [in]data The input string to be stored in the registry.
|
||||||
|
* @param [in]cb_data Size of the input string in bytes. MAX_DWORD if unknown.
|
||||||
|
* @param [in]separator Separator character for parsing strings.
|
||||||
|
*
|
||||||
|
* @retval 0 if success or non-zero on error.
|
||||||
|
* If non-zero is returned, an error message has been set using
|
||||||
|
* krb5_set_error_message().
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
_krb5_store_string_to_reg_value(krb5_context context,
|
||||||
|
HKEY key, const char * valuename,
|
||||||
|
DWORD type, const char *data, DWORD cb_data,
|
||||||
|
const char * separator)
|
||||||
|
{
|
||||||
|
LONG rcode;
|
||||||
|
DWORD dwData;
|
||||||
|
BYTE static_buffer[16384];
|
||||||
|
BYTE *pbuffer = &static_buffer[0];
|
||||||
|
|
||||||
|
if (data == NULL)
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0,
|
||||||
|
"'data' must not be NULL");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (cb_data == MAX_DWORD)
|
||||||
|
{
|
||||||
|
cb_data = (DWORD)strlen(data) + 1;
|
||||||
|
}
|
||||||
|
else if ((type == REG_MULTI_SZ && cb_data >= sizeof(static_buffer) - 1) ||
|
||||||
|
cb_data >= sizeof(static_buffer))
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0, "cb_data too big");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else if (data[cb_data-1] != '\0')
|
||||||
|
{
|
||||||
|
memcpy(static_buffer, data, cb_data);
|
||||||
|
static_buffer[cb_data++] = '\0';
|
||||||
|
if (type == REG_MULTI_SZ)
|
||||||
|
static_buffer[cb_data++] = '\0';
|
||||||
|
data = static_buffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (type == REG_NONE)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* If input is all numeric, convert to DWORD and save as REG_DWORD.
|
||||||
|
* Otherwise, store as REG_SZ.
|
||||||
|
*/
|
||||||
|
if ( StrToIntExA( data, STIF_SUPPORT_HEX, &dwData) )
|
||||||
|
{
|
||||||
|
type = REG_DWORD;
|
||||||
|
} else {
|
||||||
|
type = REG_SZ;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (type) {
|
||||||
|
case REG_SZ:
|
||||||
|
case REG_EXPAND_SZ:
|
||||||
|
rcode = RegSetValueEx(key, valuename, 0, type, data, cb_data);
|
||||||
|
if (rcode)
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0,
|
||||||
|
"Unexpected error when setting registry value %s gle 0x%x",
|
||||||
|
valuename,
|
||||||
|
GetLastError());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case REG_MULTI_SZ:
|
||||||
|
if (separator && *separator)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
char *cp;
|
||||||
|
|
||||||
|
if (data != static_buffer)
|
||||||
|
static_buffer[cb_data++] = '\0';
|
||||||
|
|
||||||
|
for ( cp = static_buffer; cp < static_buffer+cb_data; cp++)
|
||||||
|
{
|
||||||
|
if (*cp == *separator)
|
||||||
|
*cp = '\0';
|
||||||
|
}
|
||||||
|
|
||||||
|
rcode = RegSetValueEx(key, valuename, 0, type, data, cb_data);
|
||||||
|
if (rcode)
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0,
|
||||||
|
"Unexpected error when setting registry value %s gle 0x%x",
|
||||||
|
valuename,
|
||||||
|
GetLastError());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case REG_DWORD:
|
||||||
|
if ( !StrToIntExA( data, STIF_SUPPORT_HEX, &dwData) )
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0,
|
||||||
|
"Unexpected error when parsing %s as number gle 0x%x",
|
||||||
|
data,
|
||||||
|
GetLastError());
|
||||||
|
}
|
||||||
|
|
||||||
|
rcode = RegSetValueEx(key, valuename, 0, type, dwData, sizeof(DWORD));
|
||||||
|
if (rcode)
|
||||||
|
{
|
||||||
|
if (context)
|
||||||
|
krb5_set_error_message(context, 0,
|
||||||
|
"Unexpected error when setting registry value %s gle 0x%x",
|
||||||
|
valuename,
|
||||||
|
GetLastError());
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parse a registry value as a string
|
* Parse a registry value as a string
|
||||||
*
|
*
|
||||||
|
Reference in New Issue
Block a user