From: Jonathan Vollebregt Subject: [resend 8/8] reg: Clean up reg_delete Message-Id: <1424082106-29911-8-git-send-email-jnvsor@gmail.com> Date: Mon, 16 Feb 2015 11:21:46 +0100 --- programs/reg/reg.c | 149 +++++++++++++++++++++++------------------------ programs/reg/tests/reg.c | 2 +- 2 files changed, 73 insertions(+), 78 deletions(-) diff --git a/programs/reg/reg.c b/programs/reg/reg.c index 7fb9f00..6460ae4 100755 --- a/programs/reg/reg.c +++ b/programs/reg/reg.c @@ -414,120 +414,115 @@ error: return 1; } -static int reg_delete(WCHAR *key_name, WCHAR *value_name, BOOL value_empty, - BOOL value_all, BOOL force) +static int reg_delete(const WCHAR *key_name, const WCHAR *value_name, const BOOL value_empty, + const BOOL value_all, const BOOL force) { - HKEY subkey; - LONG err; - - static const WCHAR stubW[] = {'D','E','L','E','T','E', - ' ','-',' ','%','s',' ','%','s',' ','%','d',' ','%','d',' ','%','d','\n' - ,0}; - reg_printfW(stubW, key_name, value_name, value_empty, value_all, force); - - err = sane_path(key_name); + HKEY key = NULL; + LONG err = sane_path(key_name); if (err != ERROR_SUCCESS) { reg_print_error(err); return 1; } - err = path_open(key_name, &subkey, FALSE); + err = path_open(key_name, &key, FALSE); if (err != ERROR_SUCCESS) - { - reg_message(STRING_INVALID_KEY); - return 1; - } - - if (value_name && value_empty) - { - reg_message(STRING_INVALID_CMDLINE); - return 1; - } + goto error; - if (value_empty && value_all) + /* Mutually exclusive options */ + if ((!!value_name + !!value_empty + !!value_all) > 1) { - reg_message(STRING_INVALID_CMDLINE); - return 1; + err = ERROR_BAD_COMMAND; + goto error; } if (!force) { - /* FIXME: Prompt for delete */ + WINE_FIXME("Prompt for delete\n"); } - /* Delete subtree only if no /v* option is given */ - if (!value_name && !value_empty && !value_all) + if (value_empty || value_name) { - err = RegDeleteTreeW(subkey, NULL); - if (err != ERROR_SUCCESS) - { - reg_print_error(err); - return 1; - } + if (value_name && value_name[0]) + err = RegDeleteValueW(key, value_name); + else + err = RegDeleteValueW(key, NULL); - err = RegDeleteKeyW(subkey, empty_wstr); if (err != ERROR_SUCCESS) - { - reg_print_error(err); - return 1; - } - reg_message(STRING_SUCCESS); - return 0; + goto error; } - - if (value_all) + else if (value_all) { - LPWSTR szValue; - DWORD maxValue; - DWORD count; - LONG rc; - - rc = RegQueryInfoKeyW(subkey, NULL, NULL, NULL, NULL, NULL, NULL, NULL, - &maxValue, NULL, NULL, NULL); - if (rc != ERROR_SUCCESS) - { - /* FIXME: failure */ - RegCloseKey(subkey); - return 1; - } - maxValue++; - szValue = HeapAlloc(GetProcessHeap(),0,maxValue*sizeof(WCHAR)); + WCHAR *enum_v_name; + DWORD count, max_size, this_size, i = 0, errors = 0; + + err = RegQueryInfoKeyW(key, NULL, NULL, NULL, NULL, NULL, NULL, + &count, &max_size, NULL, NULL, NULL); + if (err != ERROR_SUCCESS) + goto error; - while (1) + enum_v_name = HeapAlloc(GetProcessHeap(), 0, ++max_size * sizeof(WCHAR)); + + while (i < count) { - count = maxValue; - rc = RegEnumValueW(subkey, 0, szValue, &count, NULL, NULL, NULL, NULL); - if (rc == ERROR_SUCCESS) + this_size = max_size; + + err = RegEnumValueW(key, i, enum_v_name, &this_size, NULL, NULL, NULL, NULL); + if (err != ERROR_SUCCESS) { - rc = RegDeleteValueW(subkey, szValue); - if (rc != ERROR_SUCCESS) - break; + i++; + errors++; + reg_print_error(err); + continue; } - else break; + + err = RegDeleteValueW(key, enum_v_name); + if (err != ERROR_SUCCESS) + { + i++; + errors++; + reg_print_error(err); + continue; + } + + count--; } - if (rc != ERROR_SUCCESS) + + HeapFree(GetProcessHeap(), 0, enum_v_name); + + if (errors) { - /* FIXME delete failed */ + RegCloseKey(key); + return 1; } } - else if (value_name) + /* Delete subtree only if no /v* option is given */ + else { - if (RegDeleteValueW(subkey,value_name) != ERROR_SUCCESS) + if (key == path_get_rootkey(key_name)) { - RegCloseKey(subkey); - reg_message(STRING_CANNOT_FIND); + /* "This works well enough on native to make you regret you pressed enter" - stefand */ + WINE_FIXME("Deleting a root key is not implemented.\n"); + RegCloseKey(key); return 1; } - } - else if (value_empty) - { - RegSetValueExW(subkey,NULL,0,REG_SZ,NULL,0); + + err = RegDeleteTreeW(key, NULL); + if (err != ERROR_SUCCESS) + goto error; + err = RegDeleteKeyW(key, empty_wstr); + if (err != ERROR_SUCCESS) + goto error; } - RegCloseKey(subkey); + RegCloseKey(key); reg_message(STRING_SUCCESS); return 0; + +error: + RegCloseKey(key); + reg_print_error(err); + return 1; } static int reg_query(WCHAR *key_name, WCHAR *value_name, BOOL value_empty, diff --git a/programs/reg/tests/reg.c b/programs/reg/tests/reg.c index a3ecdfb..20ef7af 100644 --- a/programs/reg/tests/reg.c +++ b/programs/reg/tests/reg.c @@ -388,7 +388,7 @@ static void test_delete(void) run_reg_exe("reg delete HKCU\\" KEY_BASE " /ve /f", &r); ok(r == REG_EXIT_SUCCESS, "got exit code %d, expected 0\n", r); err = RegQueryValueExA(hkey, "", NULL, NULL, NULL, NULL); - todo_wine ok(err == ERROR_FILE_NOT_FOUND, "got %d\n", err); + ok(err == ERROR_FILE_NOT_FOUND, "got %d\n", err); run_reg_exe("reg delete HKCU\\" KEY_BASE " /va /f", &r); ok(r == REG_EXIT_SUCCESS, "got exit code %d, expected 0\n", r); -- 2.1.4