source: trunk/testapp/exceptions/GuardPages/main.cpp@ 21982

Last change on this file since 21982 was 21982, checked in by dmik, 13 years ago

Add test case for #76 and #77.

  • Property svn:eol-style set to native
File size: 6.1 KB
Line 
1#ifdef __WIN32OS2__
2#define INCL_DOSPROCESS
3#define INCL_DOSEXCEPTIONS
4#define INCL_ERRORS
5#define INCL_DOSSEMAPHORES
6#include <os2wrap2.h>
7#endif
8
9#include <windows.h>
10#include <stdio.h>
11#include <stdlib.h>
12#include <tchar.h>
13
14#ifdef __WIN32OS2__
15#include <odinlx.h>
16#include <excpt.h>
17#endif
18
19#ifdef __WIN32OS2__
20
21void os2_PrintMemLayout (os2_PVOID pAddr)
22{
23 os2_APIRET arc;
24 os2_ULONG sz, flags;
25 os2_PVOID pBase, pCur;
26
27 printf ("Layout of memory region containing %x:\n", pAddr);
28
29 // find the base address
30 sz = 0x1000;
31 pBase = (os2_PVOID)(((os2_ULONG) pAddr) & ~0xFFF);
32
33 do
34 {
35 arc = DosQueryMem (pBase, &sz, &flags);
36 if (arc)
37 {
38 printf ("DosQueryMem(%x) failed with %d\n", pBase, arc);
39 return;
40 }
41 if (flags & os2_PAG_BASE)
42 {
43 break;
44 }
45
46 pBase = (os2_PVOID) ((os2_ULONG) pBase - 0x1000);
47 }
48 while (1);
49
50 pCur = pBase;
51 do
52 {
53 sz = ~0;
54 arc = DosQueryMem (pCur, &sz, &flags);
55 if (arc)
56 {
57 printf ("DosQueryMem(%x) failed with %d\n", pCur, arc);
58 return;
59 }
60 if (pCur != pBase && (flags & (os2_PAG_BASE | os2_PAG_FREE)))
61 {
62 break;
63 }
64
65 printf (" %08X-%08X (%08X): Flags %08X\n",
66 pCur, (ULONG) pCur + sz - 1, sz, flags);
67
68 pCur = (os2_PVOID) ((os2_ULONG) pCur + sz);
69 }
70 while (1);
71}
72
73#endif
74
75SYSTEM_INFO sSysInfo;
76
77void PrintMemLayout (LPVOID pAddr)
78{
79 MEMORY_BASIC_INFORMATION sMemInfo;
80 if (VirtualQuery (pAddr, &sMemInfo, sizeof (sMemInfo)))
81 {
82 printf ("Layout of memory region containing %x:\n", pAddr);
83
84 LPVOID pBase = sMemInfo.AllocationBase;
85 DWORD dwSize = 0;
86
87 LPVOID pStart = pBase;
88 do
89 {
90 if (VirtualQuery (pStart, &sMemInfo, sizeof (sMemInfo)))
91 {
92 if (sMemInfo.AllocationBase != pBase)
93 break;
94 printf (" %08X-%08X (%08X): Protect %08X, State %08X, Type %08X\n",
95 sMemInfo.BaseAddress, (DWORD)sMemInfo.BaseAddress + sMemInfo.RegionSize - 1,
96 sMemInfo.RegionSize, sMemInfo.Protect, sMemInfo.State, sMemInfo.Type);
97 pStart = (LPVOID)((DWORD)sMemInfo.BaseAddress + sMemInfo.RegionSize);
98 dwSize += sMemInfo.RegionSize;
99 }
100 else
101 {
102 printf ("VirtualQuery(%x) failed with %d\n", pStart, GetLastError());
103 return;
104 }
105 }
106 while (1);
107 }
108 else
109 {
110 printf ("VirtualQuery(%x) failed with %d\n", pAddr, GetLastError());
111 }
112}
113
114void Alloc4KOnStack(int nTimes)
115{
116 char buf[4096 - 12];
117 printf ("buf %08X\n", &buf);
118 if (--nTimes)
119 Alloc4KOnStack (nTimes);
120}
121
122DWORD ExceptionFilter (DWORD ExceptionCode)
123{
124 printf ("Exception %08X\n", ExceptionCode);
125
126 if (ExceptionCode == EXCEPTION_STACK_OVERFLOW)
127 return EXCEPTION_EXECUTE_HANDLER;
128 if (ExceptionCode == EXCEPTION_GUARD_PAGE)
129 return EXCEPTION_EXECUTE_HANDLER;
130 return EXCEPTION_CONTINUE_SEARCH;
131}
132
133DWORD WINAPI ThreadProc (LPVOID lpParameter)
134{
135 DWORD dwStackSize = (DWORD) lpParameter;
136
137#ifdef _MSC_VER
138 DWORD dwStackTop = __readfsdword (0x04);
139 DWORD dwStackBottom = __readfsdword (0x08);
140#else
141 DWORD dwStackTop;
142 DWORD dwStackBottom;
143 __asm__ ("movl %%fs:0x04, %0" : "=r" (dwStackTop));
144 __asm__ ("movl %%fs:0x08, %0" : "=r" (dwStackBottom));
145#endif
146
147 printf ("Thread: dwStackTop %x, dwStackBottom %x\n", dwStackTop, dwStackBottom);
148
149 ///////////////////////////////////////////////////
150
151 printf ("\nTEST 1 (STACK)\n");
152
153 DWORD dwStackBase = dwStackTop - dwStackSize;
154 DWORD dwYellowZoneSize = sSysInfo.dwPageSize * 3;
155
156#if 1
157 if (VirtualAlloc ((LPVOID) dwStackBase, dwYellowZoneSize,
158 MEM_COMMIT, PAGE_READWRITE))
159 {
160 DWORD dwOldFlags;
161 if (!VirtualProtect ((LPVOID) dwStackBase, dwYellowZoneSize,
162 PAGE_READWRITE | PAGE_GUARD, &dwOldFlags))
163 {
164 printf ("VirtualProtect(%x) failed with %d\n", dwStackBase,
165 GetLastError());
166 }
167 }
168 else
169 {
170 printf ("VirtualAlloc(%x) failed with %d\n", dwStackBase,
171 GetLastError());
172 }
173
174 PrintMemLayout (&dwStackTop);
175
176 {
177 __try
178 {
179 //Alloc4KOnStack (15);
180
181 printf ("Writing to %08X...\n", dwStackBase + sSysInfo.dwPageSize * 3 - 4);
182 *((LPDWORD)(dwStackBase + sSysInfo.dwPageSize * 3 - 4)) = 0;
183 }
184 __except (ExceptionFilter (GetExceptionCode()))
185 {
186 }
187 }
188#endif
189
190 PrintMemLayout (&dwStackTop);
191
192 ///////////////////////////////////////////////////
193
194 printf ("\nTEST 2 (PAGE_GUARD)\n");
195
196 LPVOID pNonStack = VirtualAlloc (NULL, sSysInfo.dwPageSize,
197 MEM_COMMIT, PAGE_READWRITE | PAGE_GUARD);
198 if (!pNonStack)
199 {
200 printf ("VirtualAlloc(0) failed with %d\n", GetLastError());
201 return 0;
202 }
203
204 PrintMemLayout (pNonStack);
205 os2_PrintMemLayout (pNonStack);
206
207 {
208 __try
209 {
210 *((LPDWORD)(pNonStack)) = 0;
211 }
212 __except (ExceptionFilter (GetExceptionCode()))
213 {
214 }
215 }
216
217 PrintMemLayout (pNonStack);
218 os2_PrintMemLayout (pNonStack);
219
220 VirtualFree (pNonStack, 0, MEM_RELEASE);
221
222 return 0;
223}
224
225int main()
226{
227#ifdef __WIN32OS2__
228 EnableSEH();
229#endif
230
231 //setbuf (stdout, NULL);
232
233 GetSystemInfo (&sSysInfo);
234
235 printf ("This computer has page size %d.\n", sSysInfo.dwPageSize);
236
237 DWORD dwStackSize = 64 * 1024;
238
239 HANDLE hThread = CreateThread (NULL, dwStackSize, ThreadProc, (LPVOID) dwStackSize,
240 STACK_SIZE_PARAM_IS_A_RESERVATION,
241 NULL);
242 if (hThread == NULL)
243 {
244 printf ("CreateThread failed with %d\n", GetLastError());
245 //getc (stdin);
246 return 1;
247 }
248
249 printf ("Waiting for thread...\n");
250 DWORD rc = WaitForSingleObject (hThread, INFINITE);
251 printf ("Wait returned %d\n", rc);
252
253 //getc (stdin);
254 return 0;
255}
Note: See TracBrowser for help on using the repository browser.