/*
 * Unit tests to document InternetShortcut's behaviour
 *
 * Copyright 2008 Damjan Jovanovic
 *
 * 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 <stdio.h>

#define COBJMACROS
#define NONAMELESSUNION

#include "windef.h"
#include "winbase.h"
#include "winreg.h"
#include "winerror.h"

#include "shlobj.h"
#include "shobjidl.h"
#include "shlguid.h"
#include "ole2.h"
#include "mshtml.h"
#include "initguid.h"
#include "isguids.h"
#include "intshcut.h"

#include "wine/test.h"

static HRESULT WINAPI Unknown_QueryInterface(IUnknown *pUnknown, REFIID riid, void **ppvObject)
{
    if (IsEqualGUID(&IID_IUnknown, riid))
    {
        *ppvObject = pUnknown;
        return S_OK;
    }
    return E_NOINTERFACE;
}

static ULONG WINAPI Unknown_AddRef(IUnknown *pUnknown)
{
    return 2;
}

static ULONG WINAPI Unknown_Release(IUnknown *pUnknown)
{
    return 1;
}

static IUnknownVtbl unknownVtbl = {
    Unknown_QueryInterface,
    Unknown_AddRef,
    Unknown_Release
};

static IUnknown unknown = {
    &unknownVtbl
};

static const char *printGUID(const GUID *guid)
{
    static char guidSTR[39];

    if (!guid) return NULL;

    sprintf(guidSTR, "{%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x}",
     guid->Data1, guid->Data2, guid->Data3,
     guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3],
     guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7]);
    return guidSTR;
}

static void test_Aggregability(void)
{
    HRESULT hr;
    IUnknown *pUnknown = NULL;

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUnknown, (void**)&pUnknown);
    ok(hr == S_OK, "could not create instance of CLSID_InternetShortcut with IID_IUnknown, hr = 0x%x\n", hr);
    if (pUnknown)
        IUnknown_Release(pUnknown);

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&pUnknown);
    ok(hr == S_OK, "could not create instance of CLSID_InternetShortcut with IID_IUniformResourceLocatorA, hr = 0x%x\n", hr);
    if (pUnknown)
        IUnknown_Release(pUnknown);

    hr = CoCreateInstance(&CLSID_InternetShortcut, &unknown, CLSCTX_ALL, &IID_IUnknown, (void**)&pUnknown);
    ok(hr == CLASS_E_NOAGGREGATION, "aggregation didn't fail like it should, hr = 0x%x\n", hr);
    if (pUnknown)
        IUnknown_Release(pUnknown);
}

static void can_query_interface(IUnknown *pUnknown, REFIID riid)
{
    HRESULT hr;
    IUnknown *newInterface;
    hr = IUnknown_QueryInterface(pUnknown, riid, (void**)&newInterface);
    ok(hr == S_OK, "interface %s could not be queried\n", printGUID(riid));
    if (SUCCEEDED(hr))
        IUnknown_Release(newInterface);
}

static void test_QueryInterface(void)
{
    HRESULT hr;
    IUnknown *pUnknown;

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUnknown, (void**)&pUnknown);
    ok(hr == S_OK, "Could not create InternetShortcut object: %08x\n", hr);

    can_query_interface(pUnknown, &IID_IUniformResourceLocatorA);
    can_query_interface(pUnknown, &IID_IUniformResourceLocatorW);
    can_query_interface(pUnknown, &IID_IPersistFile);
    IUnknown_Release(pUnknown);
}

#define test_shortcut_url(a,b) _test_shortcut_url(__LINE__,a,b)
static void _test_shortcut_url(unsigned line, IUnknown *unk, const char *exurl)
{
    IUniformResourceLocatorA *locator_a;
    char *url_a;
    HRESULT hres;

    hres = IUnknown_QueryInterface(unk, &IID_IUniformResourceLocatorA, (void**)&locator_a);
    ok_(__FILE__,line)(hres == S_OK, "Could not get IUniformResourceLocatorA iface: %08x\n", hres);

    hres = locator_a->lpVtbl->GetURL(locator_a, &url_a);
    ok_(__FILE__,line)(hres == S_OK, "GetURL failed: %08x\n", hres);
    ok_(__FILE__,line)(!strcmp(url_a, exurl), "unexpected URL, got %s, expected %s\n", url_a, exurl);
    CoTaskMemFree(url_a);

    IUnknown_Release(locator_a);
}

#define check_string_transform(a,b,c,d,e) _check_string_transform(__LINE__,a,b,c,d,e)
static void _check_string_transform(unsigned line, IUniformResourceLocatorA *urlA, LPCSTR input, DWORD flags,
        LPCSTR expectedOutput, BOOL is_todo)
{
    CHAR *output;
    HRESULT hr;

    hr = urlA->lpVtbl->SetURL(urlA, input, flags);
    ok_(__FILE__,line)(hr == S_OK, "SetUrl failed, hr=0x%x\n", hr);
    if (FAILED(hr))
        return;

    output = (void*)0xdeadbeef;
    hr = urlA->lpVtbl->GetURL(urlA, &output);
    if(expectedOutput) {
        if(is_todo) {
            todo_wine
            ok_(__FILE__,line)(hr == S_OK, "GetUrl failed, hr=0x%x\n", hr);
        }else {
            ok_(__FILE__,line)(hr == S_OK, "GetUrl failed, hr=0x%x\n", hr);
        }
        todo_wine
        ok_(__FILE__,line)(!lstrcmpA(output, expectedOutput), "unexpected URL change %s -> %s (expected %s)\n",
            input, output, expectedOutput);
        CoTaskMemFree(output);
    }else {
        todo_wine
        ok_(__FILE__,line)(hr == S_FALSE, "GetUrl failed, hr=0x%x\n", hr);
        todo_wine
        ok_(__FILE__,line)(!output, "GetUrl returned %s\n", output);
    }
}

static void test_ReadAndWriteProperties(void)
{
    int iconIndex = 7;
    PROPSPEC ps[2];
    HRESULT hr;
    IUniformResourceLocatorA *urlA;
    IUniformResourceLocatorA *urlAFromFile;
    WCHAR fileNameW[MAX_PATH];

    static const WCHAR shortcutW[] = {'t','e','s','t','s','h','o','r','t','c','u','t','.','u','r','l',0};
    WCHAR iconPath[] = {'f','i','l','e',':','/','/','/','C',':','/','a','r','b','i','t','r','a','r','y','/','i','c','o','n','/','p','a','t','h',0};
    char testurl[] = "http://some/bogus/url.html";

    ps[0].ulKind = PRSPEC_PROPID;
    U(ps[0]).propid = PID_IS_ICONFILE;
    ps[1].ulKind = PRSPEC_PROPID;
    U(ps[1]).propid = PID_IS_ICONINDEX;

    /* Make sure we have a valid temporary directory */
    GetTempPathW(MAX_PATH, fileNameW);
    lstrcatW(fileNameW, shortcutW);

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&urlA);
    ok(hr == S_OK, "Could not create CLSID_InternetShortcut instance: %08x\n", hr);
    if (hr == S_OK)
    {
        IPersistFile *pf;
        IPropertyStorage *pPropStgWrite;
        IPropertySetStorage *pPropSetStg;
        PROPVARIANT pv[2];

        /* We need to set a URL -- IPersistFile refuses to save without one. */
        hr = urlA->lpVtbl->SetURL(urlA, testurl, 0);
        ok(hr == S_OK, "Failed to set a URL.  hr=0x%x\n", hr);

        /* Write this shortcut out to a file so that we can test reading it in again. */
        hr = urlA->lpVtbl->QueryInterface(urlA, &IID_IPersistFile, (void **) &pf);
        ok(hr == S_OK, "Failed to get the IPersistFile for writing.  hr=0x%x\n", hr);

        hr = IPersistFile_Save(pf, fileNameW, TRUE);
        ok(hr == S_OK, "Failed to save via IPersistFile. hr=0x%x\n", hr);

        IPersistFile_Release(pf);

        pv[0].vt = VT_LPWSTR;
        U(pv[0]).pwszVal = (void *) iconPath;
        pv[1].vt = VT_I4;
        U(pv[1]).iVal = iconIndex;
        hr = urlA->lpVtbl->QueryInterface(urlA, &IID_IPropertySetStorage, (void **) &pPropSetStg);
        ok(hr == S_OK, "Unable to get an IPropertySetStorage, hr=0x%x\n", hr);

        hr = IPropertySetStorage_Open(pPropSetStg, &FMTID_Intshcut, STGM_READWRITE | STGM_SHARE_EXCLUSIVE, &pPropStgWrite);
        ok(hr == S_OK, "Unable to get an IPropertyStorage for writing, hr=0x%x\n", hr);

        hr = IPropertyStorage_WriteMultiple(pPropStgWrite, 2, ps, pv, 0);
        ok(hr == S_OK, "Unable to set properties, hr=0x%x\n", hr);

        hr = IPropertyStorage_Commit(pPropStgWrite, STGC_DEFAULT);
        ok(hr == S_OK, "Failed to commit properties, hr=0x%x\n", hr);

        pPropStgWrite->lpVtbl->Release(pPropStgWrite);
        urlA->lpVtbl->Release(urlA);
        IPropertySetStorage_Release(pPropSetStg);
    }

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&urlAFromFile);
    ok(hr == S_OK, "Could not create CLSID_InternetShortcut instance: %08x\n", hr);
    if (hr == S_OK)
    {
        IPropertySetStorage *pPropSetStg;
        IPropertyStorage *pPropStgRead;
        PROPVARIANT pvread[2];
        IPersistFile *pf;
        LPSTR url = NULL;

        /* Now read that .url file back in. */
        hr = urlAFromFile->lpVtbl->QueryInterface(urlAFromFile, &IID_IPersistFile, (void **) &pf);
        ok(hr == S_OK, "Failed to get the IPersistFile for reading.  hr=0x%x\n", hr);

        hr = IPersistFile_Load(pf, fileNameW, 0);
        ok(hr == S_OK, "Failed to load via IPersistFile. hr=0x%x\n", hr);
        IPersistFile_Release(pf);


        hr = urlAFromFile->lpVtbl->GetURL(urlAFromFile, &url);
        ok(hr == S_OK, "Unable to get url from file, hr=0x%x\n", hr);
        ok(lstrcmp(url, testurl) == 0, "Wrong url read from file: %s\n",url);


        hr = urlAFromFile->lpVtbl->QueryInterface(urlAFromFile, &IID_IPropertySetStorage, (void **) &pPropSetStg);
        ok(hr == S_OK, "Unable to get an IPropertySetStorage, hr=0x%x\n", hr);

        hr = IPropertySetStorage_Open(pPropSetStg, &FMTID_Intshcut, STGM_READ | STGM_SHARE_EXCLUSIVE, &pPropStgRead);
        ok(hr == S_OK, "Unable to get an IPropertyStorage for reading, hr=0x%x\n", hr);

        hr = IPropertyStorage_ReadMultiple(pPropStgRead, 2, ps, pvread);
        ok(hr == S_OK, "Unable to read properties, hr=0x%x\n", hr);

        todo_wine /* Wine doesn't yet support setting properties after save */
        {
            ok(U(pvread[1]).iVal == iconIndex, "Read wrong icon index: %d\n", U(pvread[1]).iVal);

            ok(lstrcmpW(U(pvread[0]).pwszVal, iconPath) == 0, "Wrong icon path read: %s\n", wine_dbgstr_w(U(pvread[0]).pwszVal));
        }

        PropVariantClear(&pvread[0]);
        PropVariantClear(&pvread[1]);
        IPropertyStorage_Release(pPropStgRead);
        IPropertySetStorage_Release(pPropSetStg);
        urlAFromFile->lpVtbl->Release(urlAFromFile);
        DeleteFileW(fileNameW);
    }
}

static void test_NullURLs(void)
{
    LPSTR url = NULL;
    HRESULT hr;
    IUniformResourceLocatorA *urlA;

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&urlA);
    ok(hr == S_OK, "Could not create InternetShortcut object: %08x\n", hr);

    hr = urlA->lpVtbl->GetURL(urlA, &url);
    ok(hr == S_FALSE, "getting uninitialized URL unexpectedly failed, hr=0x%x\n", hr);
    ok(url == NULL, "uninitialized URL is not NULL but %s\n", url);

    hr = urlA->lpVtbl->SetURL(urlA, NULL, 0);
    ok(hr == S_OK, "setting NULL URL unexpectedly failed, hr=0x%x\n", hr);

    hr = urlA->lpVtbl->GetURL(urlA, &url);
    ok(hr == S_FALSE, "getting NULL URL unexpectedly failed, hr=0x%x\n", hr);
    ok(url == NULL, "URL unexpectedly not NULL but %s\n", url);

    urlA->lpVtbl->Release(urlA);
}

typedef struct {
    const char *data;
    const char *url;
} load_test_t;

static const load_test_t load_tests[] = {
    {"[InternetShortcut]\n"
     "URL=http://www.winehq.org/\n"
     "HotKey=0\n"
     "IDList=\n"
     "[{000214A0-0000-0000-C000-000000000046}]\n"
     "Prop0=1,2\n",

     "http://www.winehq.org/"
    }
};

static void test_Load(void)
{
    IPersistFile *persist_file;
    const load_test_t *test;
    WCHAR file_path[MAX_PATH];
    DWORD size;
    HANDLE file;
    HRESULT hres;

    static const WCHAR test_urlW[] = {'t','e','s','t','.','u','r','l',0};

    GetTempPathW(MAX_PATH, file_path);
    lstrcatW(file_path, test_urlW);

    for(test = load_tests; test < load_tests + sizeof(load_tests)/sizeof(*load_tests); test++) {
        file = CreateFileW(file_path, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
        ok(file != INVALID_HANDLE_VALUE, "could not create test file\n");
        if(file == INVALID_HANDLE_VALUE)
            continue;

        WriteFile(file, test->data, strlen(test->data), &size, NULL);
        CloseHandle(file);

        hres = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IPersistFile, (void**)&persist_file);
        ok(hres == S_OK, "Could not create InternetShortcut instance: %08x\n", hres);

        hres = IPersistFile_Load(persist_file, file_path, 0);
        ok(hres == S_OK, "Load failed: %08x\n", hres);

        test_shortcut_url((IUnknown*)persist_file, test->url);

        IPersistFile_Release(persist_file);
        DeleteFileW(file_path);
    }
}

static void test_SetURLFlags(void)
{
    HRESULT hr;
    IUniformResourceLocatorA *urlA;

    hr = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&urlA);
    ok(hr == S_OK, "Could not create InternetShortcut object: %08x\n", hr);

    check_string_transform(urlA, "somerandomstring", 0, NULL, TRUE);
    check_string_transform(urlA, "www.winehq.org", 0, NULL, TRUE);

    check_string_transform(urlA, "www.winehq.org", IURL_SETURL_FL_GUESS_PROTOCOL, "http://www.winehq.org/", FALSE);
    check_string_transform(urlA, "ftp.winehq.org", IURL_SETURL_FL_GUESS_PROTOCOL, "ftp://ftp.winehq.org/", FALSE);

    urlA->lpVtbl->Release(urlA);
}

static void test_InternetShortcut(void)
{
    IUniformResourceLocatorA *url;
    HRESULT hres;

    hres = CoCreateInstance(&CLSID_InternetShortcut, NULL, CLSCTX_ALL, &IID_IUniformResourceLocatorA, (void**)&url);
    ok(hres == S_OK, "Could not create CLSID_InternetShortcut instance: %08x\n", hres);
    if(FAILED(hres))
        return;

    test_Aggregability();
    test_QueryInterface();
    test_NullURLs();
    test_SetURLFlags();
    test_ReadAndWriteProperties();
    test_Load();
}

START_TEST(intshcut)
{
    OleInitialize(NULL);

    test_InternetShortcut();

    OleUninitialize();
}
