From: Rémi Bernon rbernon@codeweavers.com
--- dlls/user32/tests/class.c | 369 ++++++++++++++++++++++++-------------- 1 file changed, 234 insertions(+), 135 deletions(-)
diff --git a/dlls/user32/tests/class.c b/dlls/user32/tests/class.c index 58a34e9bf59..537651f31a9 100644 --- a/dlls/user32/tests/class.c +++ b/dlls/user32/tests/class.c @@ -1452,156 +1452,255 @@ static void test_actctx_classes(void) "<windowClass>MyTestClass</windowClass>" "</file>" "</assembly>"; - static const char *testclass = "MyTestClass"; - WNDCLASSA wc; + const HINSTANCE hinst = GetModuleHandleW( 0 ); + WNDCLASSA tmp_wc, wc = + { + .lpfnWndProc = ClassTest_WndProc, + .hIcon = LoadIconW( 0, (LPCWSTR)IDI_APPLICATION ), + }; + char buf[64], path[MAX_PATH]; + ATOM class, tmp_class; + HWND hwnd, tmp_hwnd; ULONG_PTR cookie; HANDLE context; - BOOL ret; - ATOM class; - HINSTANCE hinst; - char buff[64]; - HWND hwnd, hwnd2; - char path[MAX_PATH]; - - GetTempPathA(ARRAY_SIZE(path), path); - strcat(path, "actctx_classes.manifest"); - - create_manifest_file(path, main_manifest); - context = create_test_actctx(path); - ret = DeleteFileA(path); - ok(ret, "Failed to delete manifest file, error %ld.\n", GetLastError()); - - ret = ActivateActCtx(context, &cookie); - ok(ret, "Failed to activate context.\n"); - - memset(&wc, 0, sizeof(wc)); - wc.lpfnWndProc = ClassTest_WndProc; - wc.hIcon = LoadIconW(0, (LPCWSTR)IDI_APPLICATION); - wc.lpszClassName = testclass; - - hinst = GetModuleHandleW(0); - - ret = GetClassInfoA(hinst, testclass, &wc); - ok(!ret, "Expected failure.\n"); - - class = RegisterClassA(&wc); - ok(class != 0, "Failed to register class.\n"); - - /* Class info is available by versioned and regular names. */ - ret = GetClassInfoA(hinst, testclass, &wc); - ok(ret, "Failed to get class info.\n"); - - hwnd = CreateWindowExA(0, testclass, "test", 0, 0, 0, 0, 0, 0, 0, hinst, 0); - ok(hwnd != NULL, "Failed to create a window.\n"); - - hwnd2 = FindWindowExA(NULL, NULL, "MyTestClass", NULL); - ok(hwnd2 == hwnd, "Failed to find test window.\n"); - - hwnd2 = FindWindowExA(NULL, NULL, "4.3.2.1!MyTestClass", NULL); - ok(hwnd2 == NULL, "Unexpected find result %p.\n", hwnd2); - - ret = GetClassNameA(hwnd, buff, sizeof(buff)); - ok(ret, "Failed to get class name.\n"); - ok(!strcmp(buff, testclass), "Unexpected class name.\n"); - - ret = GetClassInfoA(hinst, "4.3.2.1!MyTestClass", &wc); - ok(ret, "Failed to get class info.\n"); - - ret = UnregisterClassA(testclass, hinst); - ok(!ret, "Failed to unregister class.\n"); - - ret = DeactivateActCtx(0, cookie); - ok(ret, "Failed to deactivate context.\n"); - - ret = GetClassInfoA(hinst, testclass, &wc); - ok(!ret, "Unexpected ret val %d.\n", ret); - - ret = GetClassInfoA(hinst, "4.3.2.1!MyTestClass", &wc); - ok(ret, "Failed to get class info.\n"); - - ret = GetClassNameA(hwnd, buff, sizeof(buff)); - ok(ret, "Failed to get class name.\n"); - ok(!strcmp(buff, testclass), "Unexpected class name.\n"); - - DestroyWindow(hwnd); + UINT ret;
- hwnd = CreateWindowExA(0, "4.3.2.1!MyTestClass", "test", 0, 0, 0, 0, 0, 0, 0, hinst, 0); - ok(hwnd != NULL, "Failed to create a window.\n"); + GetTempPathA( ARRAY_SIZE(path), path ); + strcat( path, "actctx_classes.manifest" );
- hwnd2 = FindWindowExA(NULL, NULL, "MyTestClass", NULL); - ok(hwnd2 == hwnd, "Failed to find test window.\n"); + create_manifest_file( path, main_manifest ); + context = create_test_actctx( path ); + ret = DeleteFileA( path ); + ok( ret, "DeleteFileA failed, error %ld.\n", GetLastError() );
- hwnd2 = FindWindowExA(NULL, NULL, "4.3.2.1!MyTestClass", NULL); - ok(hwnd2 == NULL, "Unexpected find result %p.\n", hwnd2); - - DestroyWindow(hwnd); - - ret = UnregisterClassA("MyTestClass", hinst); - ok(!ret, "Unexpected ret value %d.\n", ret); - - ret = UnregisterClassA("4.3.2.1!MyTestClass", hinst); - ok(ret, "Failed to unregister class.\n"); - - /* Register versioned class without active context. */ - wc.lpszClassName = "4.3.2.1!MyTestClass"; - class = RegisterClassA(&wc); - ok(class != 0, "Failed to register class.\n"); - - ret = ActivateActCtx(context, &cookie); - ok(ret, "Failed to activate context.\n");
+ ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); wc.lpszClassName = "MyTestClass"; - class = RegisterClassA(&wc); - ok(class == 0, "Expected failure.\n"); - - ret = DeactivateActCtx(0, cookie); - ok(ret, "Failed to deactivate context.\n"); - - ret = UnregisterClassA("4.3.2.1!MyTestClass", hinst); - ok(ret, "Failed to unregister class.\n"); - - /* Only versioned name is registered. */ - ret = ActivateActCtx(context, &cookie); - ok(ret, "Failed to activate context.\n"); - + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + + + /* UnregisterClassA is possible by atom, versioned, base names when context is active */ + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + ret = UnregisterClassA( MAKEINTRESOURCEA( class ), hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = UnregisterClassA( "MyTestClass", hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = UnregisterClassA( "4.3.2.1!MyTestClass", hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + + /* UnregisterClassA is possible by versioned name only when context isn't active */ + ret = UnregisterClassA( MAKEINTRESOURCEA( class ), hinst ); + todo_wine ok( !ret, "UnregisterClassA succeeded\n" ); + ret = UnregisterClassA( "MyTestClass", hinst ); + ok( !ret, "UnregisterClassA succeeded\n" ); + ret = UnregisterClassA( "4.3.2.1!MyTestClass", hinst ); + todo_wine ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + + + /* registering versioned class while context isn't active */ + wc.lpszClassName = "4.3.2.1!MyTestClass"; + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + + /* GetClassInfoA now works with base name */ + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + /* prevents the class to be registered when context is active */ + tmp_class = RegisterClassA( &wc ); + ok( !tmp_class, "RegisterClassA succeeded, error %lu\n", GetLastError() ); wc.lpszClassName = "MyTestClass"; - class = RegisterClassA(&wc); - ok(class != 0, "Failed to register class\n"); - - ret = DeactivateActCtx(0, cookie); - ok(ret, "Failed to deactivate context.\n"); - - ret = GetClassInfoA(hinst, "MyTestClass", &wc); - ok(!ret, "Expected failure.\n"); - - ret = GetClassInfoA(hinst, "4.3.2.1!MyTestClass", &wc); - ok(ret, "Failed to get class info.\n"); - - ret = UnregisterClassA("4.3.2.1!MyTestClass", hinst); - ok(ret, "Failed to unregister class.\n"); + tmp_class = RegisterClassA( &wc ); + ok( !tmp_class, "RegisterClassA succeeded, error %lu\n", GetLastError() ); + + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + /* versioned class can be unregistered with its base name */ + ret = UnregisterClassA( "MyTestClass", hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + + + /* registering unversioned class before context is activated */ + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); + + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + + /* unversioned class is innaccessible now */ + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + todo_wine ok( !ret, "GetClassInfoA succeeded\n" ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); + + /* versioned class can be registered when context is active, returns same atom as unversioned */ + tmp_class = RegisterClassA( &wc ); + todo_wine ok( tmp_class == class, "RegisterClassA failed, error %lu\n", GetLastError() ); + + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &tmp_wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + /* versioned class can be unregistered with its base name */ + ret = UnregisterClassA( "MyTestClass", hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + /* unversioned class cannot be unregistered */ + ret = UnregisterClassA( "MyTestClass", hinst ); + ok( !ret, "UnregisterClassA succeeded\n" ); + ret = UnregisterClassA( MAKEINTRESOURCEA( class ), hinst ); + todo_wine ok( !ret, "UnregisterClassA succeeded\n" ); + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + /* unversioned class can be unregistered now */ + ret = UnregisterClassA( MAKEINTRESOURCEA( class ), hinst ); + todo_wine ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() ); + + + /* class info is available by atom, versioned, base names when context is active */ + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + class = RegisterClassA( &wc ); + ok( class != 0, "RegisterClassA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "MyTestClass", &wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + /* class info is available by versioned name only, if context isn't active. */ + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + ret = GetClassInfoA( hinst, MAKEINTRESOURCEA( class ), &wc ); + todo_wine ok( !ret, "GetClassInfoA succeeded\n" ); + ret = GetClassInfoA( hinst, "MyTestClass", &wc ); + ok( !ret, "GetClassInfoA succeeded\n" ); + ret = GetClassInfoA( hinst, "4.3.2.1!MyTestClass", &wc ); + ok( ret, "GetClassInfoA failed, error %lu\n", GetLastError() ); + + + /* CreateWindow is allowed by atom, versioned, base names when context is active */ + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + hwnd = CreateWindowExA( 0, MAKEINTRESOURCEA( class ), NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + ret = GetClassNameA( hwnd, buf, sizeof(buf) ); + ok( ret == 11, "GetClassNameA returned %d, error %lu\n", ret, GetLastError() ); + ok( !strcmp( buf, "MyTestClass" ), "GetClassNameA returned %s\n", debugstr_a(buf) ); + DestroyWindow( hwnd ); + hwnd = CreateWindowExA( 0, "MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + ret = GetClassNameA( hwnd, buf, sizeof(buf) ); + ok( ret == 11, "GetClassNameA returned %d, error %lu\n", ret, GetLastError() ); + ok( !strcmp( buf, "MyTestClass" ), "GetClassNameA returned %s\n", debugstr_a(buf) ); + DestroyWindow( hwnd ); + hwnd = CreateWindowExA( 0, "4.3.2.1!MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + ret = GetClassNameA( hwnd, buf, sizeof(buf) ); + ok( ret == 11, "GetClassNameA returned %d, error %lu\n", ret, GetLastError() ); + ok( !strcmp( buf, "MyTestClass" ), "GetClassNameA returned %s\n", debugstr_a(buf) ); + DestroyWindow( hwnd );
- /* Register regular name first, it's not considered when versioned name is registered. */ - wc.lpszClassName = "MyTestClass"; - class = RegisterClassA(&wc); - ok(class != 0, "Failed to register class.\n"); + /* CreateWindow is allowed by versioned name only when context isn't active */ + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + hwnd = CreateWindowExA( 0, MAKEINTRESOURCEA( class ), NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + todo_wine ok( !hwnd, "CreateWindowExA succeeded\n" ); + if (hwnd) DestroyWindow( hwnd ); + hwnd = CreateWindowExA( 0, "MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( !hwnd, "CreateWindowExA succeeded\n" ); + hwnd = CreateWindowExA( 0, "4.3.2.1!MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + ret = GetClassNameA( hwnd, buf, sizeof(buf) ); + ok( ret == 11, "GetClassNameA returned %d, error %lu\n", ret, GetLastError() ); + ok( !strcmp( buf, "MyTestClass" ), "GetClassNameA returned %s\n", debugstr_a(buf) ); + DestroyWindow( hwnd );
- ret = ActivateActCtx(context, &cookie); - ok(ret, "Failed to activate context.\n");
- wc.lpszClassName = "MyTestClass"; - class = RegisterClassA(&wc); - ok(class != 0, "Failed to register class.\n"); + /* FindWindow is allowed only by atom and base names */ + ret = ActivateActCtx( context, &cookie ); + ok( ret, "ActivateActCtx failed, error %lu\n", GetLastError() ); + hwnd = CreateWindowExA( 0, "4.3.2.1!MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, MAKEINTRESOURCEA( class ), NULL ); + todo_wine ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, "MyTestClass", NULL ); + ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA(NULL, NULL, "4.3.2.1!MyTestClass", NULL); + ok( tmp_hwnd == NULL, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + + ret = DeactivateActCtx( 0, cookie ); + ok( ret, "DeactivateActCtx failed, error %lu\n", GetLastError() ); + + tmp_hwnd = FindWindowExA( NULL, NULL, MAKEINTRESOURCEA( class ), NULL ); + todo_wine ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, "MyTestClass", NULL ); + ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA(NULL, NULL, "4.3.2.1!MyTestClass", NULL); + ok( tmp_hwnd == NULL, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + DestroyWindow( hwnd );
- ret = DeactivateActCtx(0, cookie); - ok(ret, "Failed to deactivate context.\n"); + hwnd = CreateWindowExA( 0, "4.3.2.1!MyTestClass", NULL, 0, 0, 0, 0, 0, 0, 0, hinst, 0 ); + ok( hwnd != NULL, "CreateWindowExA failed, error %lu\n", GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, MAKEINTRESOURCEA( class ), NULL ); + todo_wine ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, "MyTestClass", NULL ); + ok( tmp_hwnd == hwnd, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + tmp_hwnd = FindWindowExA( NULL, NULL, "4.3.2.1!MyTestClass", NULL ); + ok( tmp_hwnd == NULL, "FindWindowExA returned %p, error %lu\n", tmp_hwnd, GetLastError() ); + DestroyWindow( hwnd );
- ret = UnregisterClassA("4.3.2.1!MyTestClass", hinst); - ok(ret, "Failed to unregister class.\n"); + ret = UnregisterClassA( "4.3.2.1!MyTestClass", hinst ); + ok( ret, "UnregisterClassA failed, error %lu\n", GetLastError() );
- ret = UnregisterClassA("MyTestClass", hinst); - ok(ret, "Failed to unregister class.\n");
- ReleaseActCtx(context); + ReleaseActCtx( context ); }
static void test_uxtheme(void)