/*
 * Unit tests for window stations and desktops
 *
 * Copyright 2002 Alexandre Julliard
 *
 * 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 "wine/test.h"
#include "winbase.h"
#include "wingdi.h"
#include "winuser.h"
#include "winnls.h"

#define DESKTOP_ALL_ACCESS 0x01ff

static void print_object( HANDLE obj )
{
    char buffer[100];
    DWORD size;

    strcpy( buffer, "foobar" );
    if (!GetUserObjectInformationA( obj, UOI_NAME, buffer, sizeof(buffer), &size ))
        trace( "could not get info for %p\n", obj );
    else
        trace( "obj %p name '%s'\n", obj, buffer );
    strcpy( buffer, "foobar" );
    if (!GetUserObjectInformationA( obj, UOI_TYPE, buffer, sizeof(buffer), &size ))
        trace( "could not get type for %p\n", obj );
    else
        trace( "obj %p type '%s'\n", obj, buffer );
}

static void register_class(void)
{
    WNDCLASSA cls;

    cls.style = CS_DBLCLKS;
    cls.lpfnWndProc = DefWindowProcA;
    cls.cbClsExtra = 0;
    cls.cbWndExtra = 0;
    cls.hInstance = GetModuleHandleA(0);
    cls.hIcon = 0;
    cls.hCursor = LoadCursorA(0, IDC_ARROW);
    cls.hbrBackground = GetStockObject(WHITE_BRUSH);
    cls.lpszMenuName = NULL;
    cls.lpszClassName = "WinStationClass";
    RegisterClassA(&cls);
}

static HDESK initial_desktop;

static DWORD CALLBACK thread( LPVOID arg )
{
    HDESK d1, d2;
    HWND hwnd = CreateWindowExA(0,"WinStationClass","test",WS_POPUP,0,0,100,100,GetDesktopWindow(),0,0,0);
    ok( hwnd != 0, "CreateWindow failed\n" );
    d1 = GetThreadDesktop(GetCurrentThreadId());
    trace( "thread %p desktop: %p\n", arg, d1 );
    ok( d1 == initial_desktop, "thread %p doesn't use initial desktop\n", arg );

    SetLastError( 0xdeadbeef );
    ok( !CloseHandle( d1 ), "CloseHandle succeeded\n" );
    ok( GetLastError() == ERROR_INVALID_HANDLE, "bad last error %d\n", GetLastError() );
    SetLastError( 0xdeadbeef );
    ok( !CloseDesktop( d1 ), "CloseDesktop succeeded\n" );
    ok( GetLastError() == ERROR_BUSY || broken(GetLastError() == 0xdeadbeef), /* wow64 */
        "bad last error %d\n", GetLastError() );
    print_object( d1 );
    d2 = CreateDesktop( "foobar2", NULL, NULL, 0, DESKTOP_ALL_ACCESS, NULL );
    trace( "created desktop %p\n", d2 );
    ok( d2 != 0, "CreateDesktop failed\n" );

    SetLastError( 0xdeadbeef );
    ok( !SetThreadDesktop( d2 ), "set thread desktop succeeded with existing window\n" );
    ok( GetLastError() == ERROR_BUSY || broken(GetLastError() == 0xdeadbeef), /* wow64 */
        "bad last error %d\n", GetLastError() );

    DestroyWindow( hwnd );
    ok( SetThreadDesktop( d2 ), "set thread desktop failed\n" );
    d1 = GetThreadDesktop(GetCurrentThreadId());
    ok( d1 == d2, "GetThreadDesktop did not return set desktop %p/%p\n", d1, d2 );
    print_object( d2 );
    if (arg < (LPVOID)5)
    {
        HANDLE hthread = CreateThread( NULL, 0, thread, (char *)arg + 1, 0, NULL );
        Sleep(1000);
        WaitForSingleObject( hthread, INFINITE );
        CloseHandle( hthread );
    }
    return 0;
}

static void test_handles(void)
{
    HWINSTA w1, w2, w3;
    HDESK d1, d2, d3;
    HANDLE hthread;
    DWORD id, flags;
    ATOM atom;
    char buffer[20];

    /* win stations */

    w1 = GetProcessWindowStation();
    ok( GetProcessWindowStation() == w1, "GetProcessWindowStation returned different handles\n" );
    ok( !CloseWindowStation(w1), "closing process win station succeeded\n" );
    SetLastError( 0xdeadbeef );
    ok( !CloseHandle(w1), "closing process win station handle succeeded\n" );
    ok( GetLastError() == ERROR_INVALID_HANDLE, "bad last error %d\n", GetLastError() );
    print_object( w1 );

    flags = 0;
    ok( GetHandleInformation( w1, &flags ), "GetHandleInformation failed\n" );
    ok( !(flags & HANDLE_FLAG_PROTECT_FROM_CLOSE) ||
        broken(flags & HANDLE_FLAG_PROTECT_FROM_CLOSE), /* set on nt4 */
        "handle %p PROTECT_FROM_CLOSE set\n", w1 );

    ok( DuplicateHandle( GetCurrentProcess(), w1, GetCurrentProcess(), (PHANDLE)&w2, 0,
                         TRUE, DUPLICATE_SAME_ACCESS ), "DuplicateHandle failed\n" );
    ok( CloseWindowStation(w2), "closing dup win station failed\n" );

    ok( DuplicateHandle( GetCurrentProcess(), w1, GetCurrentProcess(), (PHANDLE)&w2, 0,
                         TRUE, DUPLICATE_SAME_ACCESS ), "DuplicateHandle failed\n" );
    ok( CloseHandle(w2), "closing dup win station handle failed\n" );

    w2 = CreateWindowStation("WinSta0", 0, WINSTA_ALL_ACCESS, NULL );
    ok( w2 != 0, "CreateWindowStation failed\n" );
    ok( w2 != w1, "CreateWindowStation returned default handle\n" );
    SetLastError( 0xdeadbeef );
    ok( !CloseDesktop( (HDESK)w2 ), "CloseDesktop succeeded on win station\n" );
    ok( GetLastError() == ERROR_INVALID_HANDLE || broken(GetLastError() == 0xdeadbeef), /* wow64 */
        "bad last error %d\n", GetLastError() );
    ok( CloseWindowStation( w2 ), "CloseWindowStation failed\n" );

    w2 = CreateWindowStation("WinSta0", 0, WINSTA_ALL_ACCESS, NULL );
    ok( CloseHandle( w2 ), "CloseHandle failed\n" );

    w2 = OpenWindowStation("winsta0", TRUE, WINSTA_ALL_ACCESS );
    ok( w2 != 0, "OpenWindowStation failed\n" );
    ok( w2 != w1, "OpenWindowStation returned default handle\n" );
    ok( CloseWindowStation( w2 ), "CloseWindowStation failed\n" );

    w2 = OpenWindowStation("dummy name", TRUE, WINSTA_ALL_ACCESS );
    ok( !w2, "open dummy win station succeeded\n" );

    CreateMutexA( NULL, 0, "foobar" );
    w2 = CreateWindowStation("foobar", 0, WINSTA_ALL_ACCESS, NULL );
    ok( w2 != 0, "create foobar station failed\n" );

    w3 = OpenWindowStation("foobar", TRUE, WINSTA_ALL_ACCESS );
    ok( w3 != 0, "open foobar station failed\n" );
    ok( w3 != w2, "open foobar station returned same handle\n" );
    ok( CloseWindowStation( w2 ), "CloseWindowStation failed\n" );
    ok( CloseWindowStation( w3 ), "CloseWindowStation failed\n" );

    w3 = OpenWindowStation("foobar", TRUE, WINSTA_ALL_ACCESS );
    ok( !w3, "open foobar station succeeded\n" );

    w2 = CreateWindowStation("foobar1", 0, WINSTA_ALL_ACCESS, NULL );
    ok( w2 != 0, "create foobar station failed\n" );
    w3 = CreateWindowStation("foobar2", 0, WINSTA_ALL_ACCESS, NULL );
    ok( w3 != 0, "create foobar station failed\n" );
    ok( GetHandleInformation( w2, &flags ), "GetHandleInformation failed\n" );
    ok( GetHandleInformation( w3, &flags ), "GetHandleInformation failed\n" );

    SetProcessWindowStation( w2 );
    register_class();
    atom = GlobalAddAtomA("foo");
    ok( GlobalGetAtomNameA( atom, buffer, sizeof(buffer) ) == 3, "GlobalGetAtomName failed\n" );
    ok( !lstrcmpiA( buffer, "foo" ), "bad atom value %s\n", buffer );

    ok( !CloseWindowStation( w2 ), "CloseWindowStation succeeded\n" );
    ok( GetHandleInformation( w2, &flags ), "GetHandleInformation failed\n" );

    SetProcessWindowStation( w3 );
    ok( GetHandleInformation( w2, &flags ), "GetHandleInformation failed\n" );
    ok( CloseWindowStation( w2 ), "CloseWindowStation failed\n" );
    ok( GlobalGetAtomNameA( atom, buffer, sizeof(buffer) ) == 3, "GlobalGetAtomName failed\n" );
    ok( !lstrcmpiA( buffer, "foo" ), "bad atom value %s\n", buffer );

    /* desktops */
    d1 = GetThreadDesktop(GetCurrentThreadId());
    initial_desktop = d1;
    ok( GetThreadDesktop(GetCurrentThreadId()) == d1,
        "GetThreadDesktop returned different handles\n" );

    flags = 0;
    ok( GetHandleInformation( d1, &flags ), "GetHandleInformation failed\n" );
    ok( !(flags & HANDLE_FLAG_PROTECT_FROM_CLOSE), "handle %p PROTECT_FROM_CLOSE set\n", d1 );

    SetLastError( 0xdeadbeef );
    ok( !CloseDesktop(d1), "closing thread desktop succeeded\n" );
    ok( GetLastError() == ERROR_BUSY || broken(GetLastError() == 0xdeadbeef), /* wow64 */
        "bad last error %d\n", GetLastError() );

    SetLastError( 0xdeadbeef );
    if (CloseHandle( d1 ))  /* succeeds on nt4 */
    {
        win_skip( "NT4 desktop handle management is completely different\n" );
        return;
    }
    ok( GetLastError() == ERROR_INVALID_HANDLE, "bad last error %d\n", GetLastError() );

    ok( DuplicateHandle( GetCurrentProcess(), d1, GetCurrentProcess(), (PHANDLE)&d2, 0,
                         TRUE, DUPLICATE_SAME_ACCESS ), "DuplicateHandle failed\n" );
    ok( CloseDesktop(d2), "closing dup desktop failed\n" );

    ok( DuplicateHandle( GetCurrentProcess(), d1, GetCurrentProcess(), (PHANDLE)&d2, 0,
                         TRUE, DUPLICATE_SAME_ACCESS ), "DuplicateHandle failed\n" );
    ok( CloseHandle(d2), "closing dup desktop handle failed\n" );

    d2 = OpenDesktop( "dummy name", 0, TRUE, DESKTOP_ALL_ACCESS );
    ok( !d2, "open dummy desktop succeeded\n" );

    d2 = CreateDesktop( "foobar", NULL, NULL, 0, DESKTOP_ALL_ACCESS, NULL );
    ok( d2 != 0, "create foobar desktop failed\n" );
    SetLastError( 0xdeadbeef );
    ok( !CloseWindowStation( (HWINSTA)d2 ), "CloseWindowStation succeeded on desktop\n" );
    ok( GetLastError() == ERROR_INVALID_HANDLE || broken(GetLastError() == 0xdeadbeef), /* wow64 */
        "bad last error %d\n", GetLastError() );

    SetLastError( 0xdeadbeef );
    d3 = CreateDesktop( "foobar", NULL, NULL, 0, DESKTOP_ALL_ACCESS, NULL );
    ok( d3 != 0, "create foobar desktop again failed\n" );
    ok( GetLastError() == 0xdeadbeef, "bad last error %d\n", GetLastError() );
    ok( CloseDesktop( d3 ), "CloseDesktop failed\n" );

    d3 = OpenDesktop( "foobar", 0, TRUE, DESKTOP_ALL_ACCESS );
    ok( d3 != 0, "open foobar desktop failed\n" );
    ok( d3 != d2, "open foobar desktop returned same handle\n" );
    ok( CloseDesktop( d2 ), "CloseDesktop failed\n" );
    ok( CloseDesktop( d3 ), "CloseDesktop failed\n" );

    d3 = OpenDesktop( "foobar", 0, TRUE, DESKTOP_ALL_ACCESS );
    ok( !d3, "open foobar desktop succeeded\n" );

    ok( !CloseHandle(d1), "closing thread desktop handle succeeded\n" );
    d2 = GetThreadDesktop(GetCurrentThreadId());
    ok( d1 == d2, "got different handles after close\n" );

    trace( "thread 1 desktop: %p\n", d1 );
    print_object( d1 );
    hthread = CreateThread( NULL, 0, thread, (LPVOID)2, 0, &id );
    Sleep(1000);
    trace( "get other thread desktop: %p\n", GetThreadDesktop(id) );
    WaitForSingleObject( hthread, INFINITE );
    CloseHandle( hthread );
}

/* Enumeration tests */

static BOOL CALLBACK window_station_callbackA(LPSTR winsta, LPARAM lp)
{
    trace("window_station_callbackA called with argument %s\n", winsta);
    return lp;
}

static BOOL CALLBACK open_window_station_callbackA(LPSTR winsta, LPARAM lp)
{
    HWINSTA hwinsta;

    trace("open_window_station_callbackA called with argument %s\n", winsta);
    hwinsta = OpenWindowStationA(winsta, FALSE, WINSTA_ENUMERATE);
    ok(hwinsta != NULL, "Could not open desktop %s!\n", winsta);
    if (hwinsta)
        CloseWindowStation(hwinsta);
    return lp;
}

static void test_enumstations(void)
{
    BOOL ret;

    if (0) /* Crashes instead */
    {
        SetLastError(0xbabefeed);
        ret = EnumWindowStationsA(NULL, 0);
        ok(!ret, "EnumWindowStationsA returned successfully!\n");
        ok(GetLastError() == ERROR_INVALID_PARAMETER, "LastError is set to %08x\n", GetLastError());
    }

    SetLastError(0xdeadbeef);
    ret = EnumWindowStationsA(open_window_station_callbackA, 0x12345);
    ok(ret == 0x12345, "EnumWindowStationsA returned %x\n", ret);
    ok(GetLastError() == 0xdeadbeef, "LastError is set to %08x\n", GetLastError());

    SetLastError(0xdeadbeef);
    ret = EnumWindowStationsA(window_station_callbackA, 0);
    ok(!ret, "EnumWindowStationsA returned %x\n", ret);
    ok(GetLastError() == 0xdeadbeef, "LastError is set to %08x\n", GetLastError());
}

static BOOL CALLBACK desktop_callbackA(LPSTR desktop, LPARAM lp)
{
    trace("desktop_callbackA called with argument %s\n", desktop);
    return lp;
}

static BOOL CALLBACK open_desktop_callbackA(LPSTR desktop, LPARAM lp)
{
    HDESK hdesk;
    static int once;

    trace("open_desktop_callbackA called with argument %s\n", desktop);
    /* Only try to open one desktop */
    if (once++)
        return lp;

    hdesk = OpenDesktopA(desktop, 0, FALSE, DESKTOP_ENUMERATE);
    ok(hdesk != NULL, "Could not open desktop %s!\n", desktop);
    if (hdesk)
        CloseDesktop(hdesk);
    return lp;
}

static void test_enumdesktops(void)
{
    BOOL ret;

    if (0)  /* Crashes instead */
    {
        SetLastError(0xbabefeed);
        ret = EnumDesktopsA(GetProcessWindowStation(), NULL, 0);
        ok(!ret, "EnumDesktopsA returned successfully!\n");
        ok(GetLastError() == ERROR_INVALID_PARAMETER, "LastError is set to %08x\n", GetLastError());
    }

    SetLastError(0xdeadbeef);
    ret = EnumDesktopsA(NULL, desktop_callbackA, 0x12345);
    ok(ret == 0x12345, "EnumDesktopsA returned %x\n", ret);
    ok(GetLastError() == 0xdeadbeef, "LastError is set to %08x\n", GetLastError());

    SetLastError(0xdeadbeef);
    ret = EnumDesktopsA(GetProcessWindowStation(), open_desktop_callbackA, 0x12345);
    ok(ret == 0x12345, "EnumDesktopsA returned %x\n", ret);
    ok(GetLastError() == 0xdeadbeef, "LastError is set to %08x\n", GetLastError());

    SetLastError(0xdeadbeef);
    ret = EnumDesktopsA(INVALID_HANDLE_VALUE, desktop_callbackA, 0x12345);
    ok(!ret, "EnumDesktopsA returned %x\n", ret);
    ok(GetLastError() == ERROR_INVALID_HANDLE, "LastError is set to %08x\n", GetLastError());

    SetLastError(0xdeadbeef);
    ret = EnumDesktopsA(GetProcessWindowStation(), desktop_callbackA, 0);
    ok(!ret, "EnumDesktopsA returned %x\n", ret);
    ok(GetLastError() == 0xdeadbeef, "LastError is set to %08x\n", GetLastError());
}

START_TEST(winstation)
{
    /* Check whether this platform supports WindowStation calls */

    SetLastError( 0xdeadbeef );
    GetProcessWindowStation();
    if (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
    {
        skip("WindowStation calls not supported on this platform\n");
        return;
    }

    test_enumstations();
    test_enumdesktops();
    test_handles();
}
