Commit d6d99e59 authored by Akihiro Sagawa's avatar Akihiro Sagawa Committed by Alexandre Julliard

ntdll: ObjectName should also be used in NtUnloadKey.

parent 99429480
...@@ -2349,24 +2349,16 @@ LSTATUS WINAPI RegRestoreKeyA( HKEY hkey, LPCSTR lpFile, DWORD dwFlags ) ...@@ -2349,24 +2349,16 @@ LSTATUS WINAPI RegRestoreKeyA( HKEY hkey, LPCSTR lpFile, DWORD dwFlags )
*/ */
LSTATUS WINAPI RegUnLoadKeyW( HKEY hkey, LPCWSTR lpSubKey ) LSTATUS WINAPI RegUnLoadKeyW( HKEY hkey, LPCWSTR lpSubKey )
{ {
DWORD ret;
HKEY shkey;
OBJECT_ATTRIBUTES attr; OBJECT_ATTRIBUTES attr;
UNICODE_STRING subkey; UNICODE_STRING subkey;
TRACE("(%p,%s)\n",hkey, debugstr_w(lpSubKey)); TRACE("(%p,%s)\n",hkey, debugstr_w(lpSubKey));
ret = RegOpenKeyExW( hkey, lpSubKey, 0, MAXIMUM_ALLOWED, &shkey ); if (!(hkey = get_special_root_hkey( hkey, 0 ))) return ERROR_INVALID_HANDLE;
if( ret )
return ERROR_INVALID_PARAMETER;
RtlInitUnicodeString(&subkey, lpSubKey); RtlInitUnicodeString(&subkey, lpSubKey);
InitializeObjectAttributes(&attr, &subkey, OBJ_CASE_INSENSITIVE, shkey, NULL); InitializeObjectAttributes(&attr, &subkey, OBJ_CASE_INSENSITIVE, hkey, NULL);
ret = RtlNtStatusToDosError(NtUnloadKey(&attr)); return RtlNtStatusToDosError( NtUnloadKey(&attr) );
RegCloseKey(shkey);
return ret;
} }
......
...@@ -677,9 +677,15 @@ NTSTATUS WINAPI NtUnloadKey( OBJECT_ATTRIBUTES *attr ) ...@@ -677,9 +677,15 @@ NTSTATUS WINAPI NtUnloadKey( OBJECT_ATTRIBUTES *attr )
TRACE( "(%p)\n", attr ); TRACE( "(%p)\n", attr );
if (!attr || !attr->ObjectName) return STATUS_ACCESS_VIOLATION;
if (attr->Length != sizeof(*attr)) return STATUS_INVALID_PARAMETER;
if (attr->ObjectName->Length & 1) return STATUS_OBJECT_NAME_INVALID;
SERVER_START_REQ( unload_registry ) SERVER_START_REQ( unload_registry )
{ {
req->hkey = wine_server_obj_handle( attr->RootDirectory ); req->parent = wine_server_obj_handle( attr->RootDirectory );
req->attributes = attr->Attributes;
wine_server_add_data( req, attr->ObjectName->Buffer, attr->ObjectName->Length );
ret = wine_server_call(req); ret = wine_server_call(req);
} }
SERVER_END_REQ; SERVER_END_REQ;
......
...@@ -2356,7 +2356,10 @@ struct load_registry_reply ...@@ -2356,7 +2356,10 @@ struct load_registry_reply
struct unload_registry_request struct unload_registry_request
{ {
struct request_header __header; struct request_header __header;
obj_handle_t hkey; obj_handle_t parent;
unsigned int attributes;
/* VARARG(name,unicode_str); */
char __pad_20[4];
}; };
struct unload_registry_reply struct unload_registry_reply
{ {
...@@ -6223,7 +6226,7 @@ union generic_reply ...@@ -6223,7 +6226,7 @@ union generic_reply
/* ### protocol_version begin ### */ /* ### protocol_version begin ### */
#define SERVER_PROTOCOL_VERSION 681 #define SERVER_PROTOCOL_VERSION 682
/* ### protocol_version end ### */ /* ### protocol_version end ### */
......
...@@ -1812,7 +1812,9 @@ struct process_info ...@@ -1812,7 +1812,9 @@ struct process_info
/* UnLoad a registry branch from a file */ /* UnLoad a registry branch from a file */
@REQ(unload_registry) @REQ(unload_registry)
obj_handle_t hkey; /* root key to unload to */ obj_handle_t parent; /* handle to the parent key */
unsigned int attributes; /* object attributes */
VARARG(name,unicode_str); /* key name */
@END @END
......
...@@ -2244,7 +2244,9 @@ DECL_HANDLER(load_registry) ...@@ -2244,7 +2244,9 @@ DECL_HANDLER(load_registry)
DECL_HANDLER(unload_registry) DECL_HANDLER(unload_registry)
{ {
struct key *key; struct key *key, *parent;
struct unicode_str name;
unsigned int access = 0;
if (!thread_single_check_privilege( current, &SeRestorePrivilege )) if (!thread_single_check_privilege( current, &SeRestorePrivilege ))
{ {
...@@ -2252,10 +2254,17 @@ DECL_HANDLER(unload_registry) ...@@ -2252,10 +2254,17 @@ DECL_HANDLER(unload_registry)
return; return;
} }
if ((key = get_hkey_obj( req->hkey, 0 ))) if (!is_wow64_thread( current )) access = (access & ~KEY_WOW64_32KEY) | KEY_WOW64_64KEY;
if ((parent = get_parent_hkey_obj( req->parent )))
{ {
delete_key( key, 1 ); /* FIXME */ get_req_path( &name, !req->parent );
release_object( key ); if ((key = open_key( parent, &name, access, req->attributes )))
{
delete_key( key, 1 ); /* FIXME */
release_object( key );
}
release_object( parent );
} }
} }
......
...@@ -1231,8 +1231,9 @@ C_ASSERT( FIELD_OFFSET(struct delete_key_value_request, hkey) == 12 ); ...@@ -1231,8 +1231,9 @@ C_ASSERT( FIELD_OFFSET(struct delete_key_value_request, hkey) == 12 );
C_ASSERT( sizeof(struct delete_key_value_request) == 16 ); C_ASSERT( sizeof(struct delete_key_value_request) == 16 );
C_ASSERT( FIELD_OFFSET(struct load_registry_request, file) == 12 ); C_ASSERT( FIELD_OFFSET(struct load_registry_request, file) == 12 );
C_ASSERT( sizeof(struct load_registry_request) == 16 ); C_ASSERT( sizeof(struct load_registry_request) == 16 );
C_ASSERT( FIELD_OFFSET(struct unload_registry_request, hkey) == 12 ); C_ASSERT( FIELD_OFFSET(struct unload_registry_request, parent) == 12 );
C_ASSERT( sizeof(struct unload_registry_request) == 16 ); C_ASSERT( FIELD_OFFSET(struct unload_registry_request, attributes) == 16 );
C_ASSERT( sizeof(struct unload_registry_request) == 24 );
C_ASSERT( FIELD_OFFSET(struct save_registry_request, hkey) == 12 ); C_ASSERT( FIELD_OFFSET(struct save_registry_request, hkey) == 12 );
C_ASSERT( FIELD_OFFSET(struct save_registry_request, file) == 16 ); C_ASSERT( FIELD_OFFSET(struct save_registry_request, file) == 16 );
C_ASSERT( sizeof(struct save_registry_request) == 24 ); C_ASSERT( sizeof(struct save_registry_request) == 24 );
......
...@@ -2417,7 +2417,9 @@ static void dump_load_registry_request( const struct load_registry_request *req ...@@ -2417,7 +2417,9 @@ static void dump_load_registry_request( const struct load_registry_request *req
static void dump_unload_registry_request( const struct unload_registry_request *req ) static void dump_unload_registry_request( const struct unload_registry_request *req )
{ {
fprintf( stderr, " hkey=%04x", req->hkey ); fprintf( stderr, " parent=%04x", req->parent );
fprintf( stderr, ", attributes=%08x", req->attributes );
dump_varargs_unicode_str( ", name=", cur_size );
} }
static void dump_save_registry_request( const struct save_registry_request *req ) static void dump_save_registry_request( const struct save_registry_request *req )
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment