xref: /reactos/modules/rostests/apitests/crt/atexit.c (revision 34593d93)
1 /*
2 * PROJECT:         ReactOS API tests
3 * LICENSE:         LGPLv2.1+ - See COPYING.LIB in the top level directory
4 * PURPOSE:         Test for atexit
5 * PROGRAMMER:      Timo Kreuzer <timo.kreuzer@reactos.org>
6 */
7 
8 #include <apitest.h>
9 
10 #include <stdlib.h>
11 #include <stdio.h>
12 #include <ntndk.h>
13 
14 int g_sequence = 0;
15 HANDLE g_hSemaphore;
16 
17 void exitfunc1(void)
18 {
19     ok_int(g_sequence, 1);
20     g_sequence++;
21     ReleaseSemaphore(g_hSemaphore, 1, NULL);
22 }
23 
24 void exitfunc2(void)
25 {
26     ok_int(g_sequence, 2);
27     g_sequence++;
28     ReleaseSemaphore(g_hSemaphore, 1, NULL);
29 }
30 
31 void exitfunc3(void)
32 {
33     ok_int(g_sequence, 0);
34     g_sequence++;
35     ReleaseSemaphore(g_hSemaphore, 1, NULL);
36     printf("exitfunc3\n");
37 }
38 
39 typedef int (__cdecl *PFN_atexit)(void (__cdecl*)(void));
40 
41 void Test_atexit()
42 {
43     HMODULE hmod;
44     PFN_atexit patexit;
45 
46     /* Open the named sempahore to count atexit callbacks */
47     g_hSemaphore = OpenSemaphoreA(SEMAPHORE_ALL_ACCESS, FALSE, "atext_apitest_sempahore");
48     ok(g_hSemaphore != NULL, "couldn't open semaphore.\n");
49 
50     /* Load atexit from msvcrt.dll */
51     hmod = GetModuleHandleA("msvcrt.dll");
52     patexit = (PFN_atexit)GetProcAddress(hmod, "atexit");
53     ok(patexit != NULL, "failed to get atexit from msvcrt.dll\n");
54 
55     /* Register 3 exit functions, the second one in msvcrt. */
56     ok_int(atexit(exitfunc1), 0);
57     if (patexit != NULL)
58     {
59         ok_int(patexit(exitfunc2), 0);
60     }
61     ok_int(atexit(exitfunc3), 0);
62 }
63 
64 START_TEST(atexit)
65 {
66     CHAR Buffer[MAX_PATH];
67     PSTR CommandLine;
68     int result;
69     HANDLE hSemaphore;
70     SEMAPHORE_BASIC_INFORMATION SemInfo;
71     NTSTATUS Status;
72 
73     /* Check recursive call */
74     CommandLine = GetCommandLineA();
75     if (strstr(CommandLine, "-run") != NULL)
76     {
77         Test_atexit();
78         return;
79     }
80 
81     /* Create a named semaphore to count atexit callbacks in remote process */
82     hSemaphore = CreateSemaphoreA(NULL, 1, 20, "atext_apitest_sempahore");
83 
84     /* Run the actual test in a new process */
85     sprintf(Buffer, "%s -run", CommandLine);
86     result = system(Buffer);
87     ok_int(result, 0);
88 
89     /* Check the new semaphore state */
90     Status = NtQuerySemaphore(hSemaphore, SemaphoreBasicInformation, &SemInfo, sizeof(SemInfo), NULL);
91     ok(NT_SUCCESS(Status), "NtQuerySemaphore failed: 0x%lx\n", Status);
92     ok_int(SemInfo.CurrentCount, 4);
93 }
94