/*
 * Advpack registry functions
 *
 * Copyright 2004 Huw D M Davies
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include <stdarg.h>
#include "windef.h"
#include "winbase.h"
#include "winreg.h"
#include "winerror.h"
#include "winuser.h"
#include "winternl.h"
#include "advpub.h"
#include "wine/unicode.h"
#include "wine/debug.h"

WINE_DEFAULT_DEBUG_CHANNEL(advpack);

static const WCHAR REGINST[] = {'R','E','G','I','N','S','T',0};
static const WCHAR Strings[] = {'S','t','r','i','n','g','s',0};
static const WCHAR MOD_PATH[] = {'_','M','O','D','_','P','A','T','H',0};
static const WCHAR SYS_MOD_PATH[] = {'_','S','Y','S','_','M','O','D','_','P','A','T','H',0};
static const WCHAR SystemRoot[] = {'S','y','s','t','e','m','R','o','o','t',0};
static const WCHAR escaped_SystemRoot[] = {'%','S','y','s','t','e','m','R','o','o','t','%',0};
static const WCHAR quote[] = {'\"',0};

static BOOL get_temp_ini_path(LPWSTR name)
{
    WCHAR tmp_dir[MAX_PATH];
    WCHAR prefix[] = {'a','v','p',0};

    if(!GetTempPathW(sizeof(tmp_dir)/sizeof(WCHAR), tmp_dir))
       return FALSE;

    if(!GetTempFileNameW(tmp_dir, prefix, 0, name))
        return FALSE;
    return TRUE;
}

static BOOL create_tmp_ini_file(HMODULE hm, WCHAR *ini_file)
{
    HRSRC hrsrc;
    HGLOBAL hmem = NULL;
    DWORD rsrc_size, bytes_written;
    VOID *rsrc_data;
    HANDLE hf = INVALID_HANDLE_VALUE;

    if(!get_temp_ini_path(ini_file)) {
        ERR("Can't get temp ini file path\n");
        goto error;
    }

    if(!(hrsrc = FindResourceW(hm, REGINST, REGINST))) {
        ERR("Can't find REGINST resource\n");
        goto error;
    }

    rsrc_size = SizeofResource(hm, hrsrc);
    hmem = LoadResource(hm, hrsrc);
    rsrc_data = LockResource(hmem);

    if(!rsrc_data || !rsrc_size) {
        ERR("Can't load REGINST resource\n");
        goto error;
    }       

    if((hf = CreateFileW(ini_file, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS,
                         FILE_ATTRIBUTE_NORMAL, NULL)) == INVALID_HANDLE_VALUE) {
        ERR("Unable to create temp ini file\n");
        goto error;
    }
    if(!WriteFile(hf, rsrc_data, rsrc_size, &bytes_written, NULL) || rsrc_size != bytes_written) {
        ERR("Write failed\n");
        goto error;
    }
    FreeResource(hmem);
    CloseHandle(hf);
    return TRUE;
error:
    if(hmem) FreeResource(hmem);
    if(hf != INVALID_HANDLE_VALUE) CloseHandle(hf);
    return FALSE;
}

static void strentry_atow(const STRENTRYA *aentry, STRENTRYW *wentry)
{
    DWORD name_len, val_len;

    name_len = MultiByteToWideChar(CP_ACP, 0, aentry->pszName, -1, NULL, 0);
    val_len = MultiByteToWideChar(CP_ACP, 0, aentry->pszValue, -1, NULL, 0);

    wentry->pszName = HeapAlloc(GetProcessHeap(), 0, name_len * sizeof(WCHAR));
    wentry->pszValue = HeapAlloc(GetProcessHeap(), 0, val_len * sizeof(WCHAR));

    MultiByteToWideChar(CP_ACP, 0, aentry->pszName, -1, wentry->pszName, name_len);
    MultiByteToWideChar(CP_ACP, 0, aentry->pszValue, -1, wentry->pszValue, val_len);
}

static STRTABLEW *strtable_atow(const STRTABLEA *atable)
{
    STRTABLEW *wtable;
    DWORD j;

    wtable = HeapAlloc(GetProcessHeap(), 0, sizeof(STRTABLEW));
    wtable->pse = HeapAlloc(GetProcessHeap(), 0, atable->cEntries * sizeof(STRENTRYW));
    wtable->cEntries = atable->cEntries;

    for (j = 0; j < wtable->cEntries; j++)
        strentry_atow(&atable->pse[j], &wtable->pse[j]);

    return wtable;
}

static void free_strtable(STRTABLEW *wtable)
{
    DWORD j;

    for (j = 0; j < wtable->cEntries; j++)
    {
        HeapFree(GetProcessHeap(), 0, wtable->pse[j].pszName);
        HeapFree(GetProcessHeap(), 0, wtable->pse[j].pszValue);
    }

    HeapFree(GetProcessHeap(), 0, wtable->pse);
    HeapFree(GetProcessHeap(), 0, wtable);
}

/***********************************************************************
 *          RegInstallA (advpack.@)
 *
 * See RegInstallW.
 */
HRESULT WINAPI RegInstallA(HMODULE hm, LPCSTR pszSection, const STRTABLEA* pstTable)
{
    UNICODE_STRING section;
    STRTABLEW *wtable;
    HRESULT hr;

    TRACE("(%p, %s, %p)\n", hm, debugstr_a(pszSection), pstTable);

    if (pstTable)
        wtable = strtable_atow(pstTable);
    else
        wtable = NULL;

    RtlCreateUnicodeStringFromAsciiz(&section, pszSection);

    hr = RegInstallW(hm, section.Buffer, wtable);

    if (pstTable)
        free_strtable(wtable);

    RtlFreeUnicodeString(&section);

    return hr;
}

static HRESULT write_predefined_strings(HMODULE hm, LPCWSTR ini_path)
{
    WCHAR mod_path[MAX_PATH + 2];
    WCHAR sys_mod_path[MAX_PATH + 2];
    WCHAR sys_root[MAX_PATH];

    *mod_path = '\"';
    if (!GetModuleFileNameW(hm, mod_path + 1, sizeof(mod_path) / sizeof(WCHAR) - 2))
        return E_FAIL;

    lstrcatW(mod_path, quote);
    WritePrivateProfileStringW(Strings, MOD_PATH, mod_path, ini_path);

    *sys_root = '\0';
    GetEnvironmentVariableW(SystemRoot, sys_root, sizeof(sys_root) / sizeof(WCHAR));

    if(!strncmpiW(sys_root, mod_path + 1, strlenW(sys_root)))
    {
        *sys_mod_path = '\"';
        strcpyW(sys_mod_path + 1, escaped_SystemRoot);
        strcatW(sys_mod_path, mod_path + 1 + strlenW(sys_root));
    }
    else
    {
        FIXME("SYS_MOD_PATH needs more work\n");
        strcpyW(sys_mod_path, mod_path);
    }

    WritePrivateProfileStringW(Strings, SYS_MOD_PATH, sys_mod_path, ini_path);

    return S_OK;
}

/***********************************************************************
 *          RegInstallW (advpack.@)
 *
 * Loads an INF from a string resource, adds entries to the string
 * substitution table, and executes the INF.
 *
 * PARAMS
 *   hm         [I] Module that contains the REGINST resource.
 *   pszSection [I] The INF section to execute.
 *   pstTable   [I] Table of string substitutions.
 * 
 * RETURNS
 *   Success: S_OK.
 *   Failure: E_FAIL.
 */
HRESULT WINAPI RegInstallW(HMODULE hm, LPCWSTR pszSection, const STRTABLEW* pstTable)
{
    unsigned int i;
    CABINFOW cabinfo;
    WCHAR tmp_ini_path[MAX_PATH];
    HRESULT hr = E_FAIL;

    TRACE("(%p, %s, %p)\n", hm, debugstr_w(pszSection), pstTable);

    if(!create_tmp_ini_file(hm, tmp_ini_path))
        return E_FAIL;

    if (write_predefined_strings(hm, tmp_ini_path) != S_OK)
        goto done;

    /* Write the additional string table */
    if (pstTable)
    {
        for(i = 0; i < pstTable->cEntries; i++)
        {
            WCHAR tmp_value[MAX_PATH + 2];
    
            tmp_value[0] = '\"';
            lstrcpyW(tmp_value + 1, pstTable->pse[i].pszValue);
            lstrcatW(tmp_value, quote);
    
            WritePrivateProfileStringW(Strings, pstTable->pse[i].pszName, tmp_value, tmp_ini_path);
        }
    }

    /* flush cache */
    WritePrivateProfileStringW(NULL, NULL, NULL, tmp_ini_path);

    /* FIXME: read AdvOptions val for dwFlags */
    ZeroMemory(&cabinfo, sizeof(CABINFOW));
    cabinfo.pszInf = tmp_ini_path;
    cabinfo.pszSection = (LPWSTR)pszSection;
    cabinfo.dwFlags = 0;

    hr = ExecuteCabW(NULL, &cabinfo, NULL);

done:

    DeleteFileW(tmp_ini_path);

    return hr;
}

/***********************************************************************
 *          RegRestoreAllA (advpack.@)
 *
 * See RegRestoreAllW.
 */
HRESULT WINAPI RegRestoreAllA(HWND hWnd, LPSTR pszTitleString, HKEY hkBackupKey)
{
    UNICODE_STRING title;
    HRESULT hr;

    TRACE("(%p, %s, %p)\n", hWnd, debugstr_a(pszTitleString), hkBackupKey);

    RtlCreateUnicodeStringFromAsciiz(&title, pszTitleString);

    hr = RegRestoreAllW(hWnd, title.Buffer, hkBackupKey);

    RtlFreeUnicodeString(&title);

    return hr;
}

/***********************************************************************
 *          RegRestoreAllW (advpack.@)
 *
 * Restores all saved registry entries.
 *
 * PARAMS
 *   hWnd           [I] Handle to the window used for the display.
 *   pszTitleString [I] Title of the window.
 *   hkBackupKey    [I] Handle to the backup key.
 *
 * RETURNS
 *   Success: S_OK.
 *   Failure: E_FAIL.
 *
 * BUGS
 *   Unimplemented.
 */
HRESULT WINAPI RegRestoreAllW(HWND hWnd, LPWSTR pszTitleString, HKEY hkBackupKey)
{
    FIXME("(%p, %s, %p) stub\n", hWnd, debugstr_w(pszTitleString), hkBackupKey);
    
    return E_FAIL;   
}

/***********************************************************************
 *          RegSaveRestoreA (advpack.@)
 *
 * See RegSaveRestoreW.
 */
HRESULT WINAPI RegSaveRestoreA(HWND hWnd, LPCSTR pszTitleString, HKEY hkBackupKey,
                               LPCSTR pcszRootKey, LPCSTR pcszSubKey,
                               LPCSTR pcszValueName, DWORD dwFlags)
{
    UNICODE_STRING title, root, subkey, value;
    HRESULT hr;

    TRACE("(%p, %s, %p, %s, %s, %s, %d)\n", hWnd, debugstr_a(pszTitleString),
          hkBackupKey, debugstr_a(pcszRootKey), debugstr_a(pcszSubKey),
          debugstr_a(pcszValueName), dwFlags);

    RtlCreateUnicodeStringFromAsciiz(&title, pszTitleString);
    RtlCreateUnicodeStringFromAsciiz(&root, pcszRootKey);
    RtlCreateUnicodeStringFromAsciiz(&subkey, pcszSubKey);
    RtlCreateUnicodeStringFromAsciiz(&value, pcszValueName);

    hr = RegSaveRestoreW(hWnd, title.Buffer, hkBackupKey, root.Buffer,
                         subkey.Buffer, value.Buffer, dwFlags);

    RtlFreeUnicodeString(&title);
    RtlFreeUnicodeString(&root);
    RtlFreeUnicodeString(&subkey);
    RtlFreeUnicodeString(&value);

    return hr;
}

/***********************************************************************
 *          RegSaveRestoreW (advpack.@)
 *
 * Saves or restores the specified registry value.
 *
 * PARAMS
 *   hWnd           [I] Handle to the window used for the display.
 *   pszTitleString [I] Title of the window.
 *   hkBackupKey    [I] Key used to store the backup data.
 *   pcszRootKey    [I] Root key of the registry value
 *   pcszSubKey     [I] Sub key of the registry value.
 *   pcszValueName  [I] Value to save or restore. 
 *   dwFlags        [I] See advpub.h.
 * 
 * RETURNS
 *   Success: S_OK.
 *   Failure: E_FAIL.
 *
 * BUGS
 *   Unimplemented.
 */
HRESULT WINAPI RegSaveRestoreW(HWND hWnd, LPCWSTR pszTitleString, HKEY hkBackupKey,
                               LPCWSTR pcszRootKey, LPCWSTR pcszSubKey,
                               LPCWSTR pcszValueName, DWORD dwFlags)
{
    FIXME("(%p, %s, %p, %s, %s, %s, %d): stub\n", hWnd, debugstr_w(pszTitleString),
          hkBackupKey, debugstr_w(pcszRootKey), debugstr_w(pcszSubKey),
          debugstr_w(pcszValueName), dwFlags);

    return E_FAIL;   
}

/***********************************************************************
 *          RegSaveRestoreOnINFA (advpack.@)
 *
 * See RegSaveRestoreOnINFW.
 */
HRESULT WINAPI RegSaveRestoreOnINFA(HWND hWnd, LPCSTR pszTitle, LPCSTR pszINF,
                                    LPCSTR pszSection, HKEY hHKLMBackKey,
                                    HKEY hHKCUBackKey, DWORD dwFlags)
{
    UNICODE_STRING title, inf, section;
    HRESULT hr;

    TRACE("(%p, %s, %s, %s, %p, %p, %d)\n", hWnd, debugstr_a(pszTitle),
          debugstr_a(pszINF), debugstr_a(pszSection),
          hHKLMBackKey, hHKCUBackKey, dwFlags);

    RtlCreateUnicodeStringFromAsciiz(&title, pszTitle);
    RtlCreateUnicodeStringFromAsciiz(&inf, pszINF);
    RtlCreateUnicodeStringFromAsciiz(&section, pszSection);

    hr = RegSaveRestoreOnINFW(hWnd, title.Buffer, inf.Buffer, section.Buffer,
                              hHKLMBackKey, hHKCUBackKey, dwFlags);

    RtlFreeUnicodeString(&title);
    RtlFreeUnicodeString(&inf);
    RtlFreeUnicodeString(&section);

    return hr;
}

/***********************************************************************
 *          RegSaveRestoreOnINFW (advpack.@)
 *
 * Saves or restores the specified INF Reg section.
 *
 * PARAMS
 *   hWnd         [I] Handle to the window used for the display.
 *   pszTitle     [I] Title of the window.
 *   pszINF       [I] Filename of the INF.
 *   pszSection   [I] Section to save or restore.
 *   hHKLMBackKey [I] Opened key in HKLM to store data.
 *   hHKCUBackKey [I] Opened key in HKCU to store data.
 *   dwFlags      [I] See advpub.h
 *
 * RETURNS
 *   Success: S_OK.
 *   Failure: E_FAIL.
 *
 * BUGS
 *   Unimplemented.
 */
HRESULT WINAPI RegSaveRestoreOnINFW(HWND hWnd, LPCWSTR pszTitle, LPCWSTR pszINF,
                                    LPCWSTR pszSection, HKEY hHKLMBackKey,
                                    HKEY hHKCUBackKey, DWORD dwFlags)
{
    FIXME("(%p, %s, %s, %s, %p, %p, %d): stub\n", hWnd, debugstr_w(pszTitle),
          debugstr_w(pszINF), debugstr_w(pszSection),
          hHKLMBackKey, hHKCUBackKey, dwFlags);

    return E_FAIL;   
}
