advapi32: Implement RegCopyTreeA/W.
Signed-off-by: Michael Müller <michael@fds-team.de> Signed-off-by: Sebastian Lackner <sebastian@fds-team.de> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
8358fd1c26
commit
6b7c576bc5
|
@ -575,8 +575,8 @@
|
||||||
@ stdcall RegConnectRegistryW(wstr long ptr)
|
@ stdcall RegConnectRegistryW(wstr long ptr)
|
||||||
# @ stub RegConnectRegistryExA
|
# @ stub RegConnectRegistryExA
|
||||||
# @ stub RegConnectRegistryExW
|
# @ stub RegConnectRegistryExW
|
||||||
# @ stub RegCopyTreeA
|
@ stdcall RegCopyTreeA(long str long)
|
||||||
# @ stub RegCopyTreeW
|
@ stdcall RegCopyTreeW(long wstr long)
|
||||||
@ stdcall RegCreateKeyA(long str ptr)
|
@ stdcall RegCreateKeyA(long str ptr)
|
||||||
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr)
|
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr)
|
||||||
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr)
|
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr)
|
||||||
|
|
|
@ -3104,6 +3104,101 @@ LSTATUS WINAPI RegDeleteTreeA(HKEY hKey, LPCSTR lpszSubKey)
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/******************************************************************************
|
||||||
|
* RegCopyTreeW [ADVAPI32.@]
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
LONG WINAPI RegCopyTreeW( HKEY hsrc, const WCHAR *subkey, HKEY hdst )
|
||||||
|
{
|
||||||
|
DWORD name_size, max_name;
|
||||||
|
DWORD value_size, max_value;
|
||||||
|
DWORD max_subkey, i, type;
|
||||||
|
WCHAR *name_buf = NULL;
|
||||||
|
BYTE *value_buf = NULL;
|
||||||
|
HKEY hkey;
|
||||||
|
LONG ret;
|
||||||
|
|
||||||
|
TRACE( "(%p, %s, %p)\n", hsrc, debugstr_w(subkey), hdst );
|
||||||
|
|
||||||
|
if (subkey)
|
||||||
|
{
|
||||||
|
ret = RegOpenKeyExW( hsrc, subkey, 0, KEY_READ, &hsrc );
|
||||||
|
if (ret) return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = RegQueryInfoKeyW( hsrc, NULL, NULL, NULL, NULL, &max_subkey,
|
||||||
|
NULL, NULL, &max_name, &max_value, NULL, NULL );
|
||||||
|
if (ret)
|
||||||
|
goto cleanup;
|
||||||
|
|
||||||
|
max_name = max( max_subkey, max_name ) + 1;
|
||||||
|
if (!(name_buf = heap_alloc( max_name * sizeof(WCHAR) )))
|
||||||
|
{
|
||||||
|
ret = ERROR_NOT_ENOUGH_MEMORY;
|
||||||
|
goto cleanup;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(value_buf = heap_alloc( max_value )))
|
||||||
|
{
|
||||||
|
ret = ERROR_NOT_ENOUGH_MEMORY;
|
||||||
|
goto cleanup;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Copy values */
|
||||||
|
for (i = 0;; i++)
|
||||||
|
{
|
||||||
|
name_size = max_name;
|
||||||
|
value_size = max_value;
|
||||||
|
ret = RegEnumValueW( hsrc, i, name_buf, &name_size, NULL, &type, value_buf, &value_size );
|
||||||
|
if (ret == ERROR_NO_MORE_ITEMS) break;
|
||||||
|
if (ret) goto cleanup;
|
||||||
|
ret = RegSetValueExW( hdst, name_buf, 0, type, value_buf, value_size );
|
||||||
|
if (ret) goto cleanup;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Recursively copy subkeys */
|
||||||
|
for (i = 0;; i++)
|
||||||
|
{
|
||||||
|
name_size = max_name;
|
||||||
|
ret = RegEnumKeyExW( hsrc, i, name_buf, &name_size, NULL, NULL, NULL, NULL );
|
||||||
|
if (ret == ERROR_NO_MORE_ITEMS) break;
|
||||||
|
if (ret) goto cleanup;
|
||||||
|
ret = RegCreateKeyExW( hdst, name_buf, 0, NULL, 0, KEY_WRITE, NULL, &hkey, NULL );
|
||||||
|
if (ret) goto cleanup;
|
||||||
|
ret = RegCopyTreeW( hsrc, name_buf, hkey );
|
||||||
|
RegCloseKey( hkey );
|
||||||
|
if (ret) goto cleanup;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = ERROR_SUCCESS;
|
||||||
|
|
||||||
|
cleanup:
|
||||||
|
heap_free( name_buf );
|
||||||
|
heap_free( value_buf );
|
||||||
|
if (subkey)
|
||||||
|
RegCloseKey( hsrc );
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/******************************************************************************
|
||||||
|
* RegCopyTreeA [ADVAPI32.@]
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
LONG WINAPI RegCopyTreeA( HKEY hsrc, const char *subkey, HKEY hdst )
|
||||||
|
{
|
||||||
|
UNICODE_STRING subkeyW;
|
||||||
|
LONG ret;
|
||||||
|
|
||||||
|
if (subkey) RtlCreateUnicodeStringFromAsciiz( &subkeyW, subkey );
|
||||||
|
else subkeyW.Buffer = NULL;
|
||||||
|
ret = RegCopyTreeW( hsrc, subkeyW.Buffer, hdst );
|
||||||
|
RtlFreeUnicodeString( &subkeyW );
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/******************************************************************************
|
/******************************************************************************
|
||||||
* RegDisableReflectionKey [ADVAPI32.@]
|
* RegDisableReflectionKey [ADVAPI32.@]
|
||||||
*
|
*
|
||||||
|
|
|
@ -2090,7 +2090,7 @@ static void test_reg_copy_tree(void)
|
||||||
|
|
||||||
if (!pRegCopyTreeA)
|
if (!pRegCopyTreeA)
|
||||||
{
|
{
|
||||||
skip("Skipping RegCopyTreeA tests, function not present\n");
|
win_skip("Skipping RegCopyTreeA tests, function not present\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
@ stdcall RegCloseKey(long) advapi32.RegCloseKey
|
@ stdcall RegCloseKey(long) advapi32.RegCloseKey
|
||||||
@ stub RegCopyTreeW
|
@ stdcall RegCopyTreeW(long wstr long) advapi32.RegCopyTreeW
|
||||||
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExA
|
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExA
|
||||||
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExW
|
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExW
|
||||||
@ stdcall RegDeleteKeyExA(long str long long) advapi32.RegDeleteKeyExA
|
@ stdcall RegDeleteKeyExA(long str long long) advapi32.RegDeleteKeyExA
|
||||||
|
|
|
@ -84,7 +84,7 @@
|
||||||
@ stdcall PrivilegedServiceAuditAlarmW(wstr wstr long ptr long) advapi32.PrivilegedServiceAuditAlarmW
|
@ stdcall PrivilegedServiceAuditAlarmW(wstr wstr long ptr long) advapi32.PrivilegedServiceAuditAlarmW
|
||||||
@ stub QuerySecurityAccessMask
|
@ stub QuerySecurityAccessMask
|
||||||
@ stdcall RegCloseKey(long) advapi32.RegCloseKey
|
@ stdcall RegCloseKey(long) advapi32.RegCloseKey
|
||||||
@ stub RegCopyTreeW
|
@ stdcall RegCopyTreeW(long wstr long) advapi32.RegCopyTreeW
|
||||||
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExA
|
@ stdcall RegCreateKeyExA(long str long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExA
|
||||||
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExW
|
@ stdcall RegCreateKeyExW(long wstr long ptr long long ptr ptr ptr) advapi32.RegCreateKeyExW
|
||||||
@ stdcall RegDeleteKeyExA(long str long long) advapi32.RegDeleteKeyExA
|
@ stdcall RegDeleteKeyExA(long str long long) advapi32.RegDeleteKeyExA
|
||||||
|
|
Loading…
Reference in New Issue