Index: ddraw/ddraw.cpp |
— | — | @@ -273,7 +273,7 @@ |
274 | 274 | HRESULT WINAPI DirectDrawEnumerateA(LPDDENUMCALLBACKA lpCallback, LPVOID lpContext)
|
275 | 275 | {
|
276 | 276 | TRACE_ENTER(2,14,lpCallback,14,lpContext);
|
277 | | - if(!IsReadablePointer(lpCallback))
|
| 277 | + if (!IsReadablePointer(lpCallback, 1))
|
278 | 278 | {
|
279 | 279 | TRACE_EXIT(23,DDERR_INVALIDPARAMS);
|
280 | 280 | return DDERR_INVALIDPARAMS;
|
— | — | @@ -311,7 +311,7 @@ |
312 | 312 | HRESULT WINAPI DirectDrawEnumerateW(LPDDENUMCALLBACKW lpCallback, LPVOID lpContext)
|
313 | 313 | {
|
314 | 314 | TRACE_ENTER(2,14,lpCallback,14,lpContext);
|
315 | | - if(!IsReadablePointer(lpCallback))
|
| 315 | + if (!IsReadablePointer(lpCallback, 1))
|
316 | 316 | {
|
317 | 317 | TRACE_EXIT(23,DDERR_INVALIDPARAMS);
|
318 | 318 | return DDERR_INVALIDPARAMS;
|
— | — | @@ -357,7 +357,7 @@ |
358 | 358 | HRESULT WINAPI DirectDrawEnumerateExA(LPDDENUMCALLBACKEXA lpCallback, LPVOID lpContext, DWORD dwFlags)
|
359 | 359 | {
|
360 | 360 | TRACE_ENTER(3,14,lpCallback,14,lpContext,9,dwFlags);
|
361 | | - if(!IsReadablePointer(lpCallback))
|
| 361 | + if (!IsReadablePointer(lpCallback, 1))
|
362 | 362 | {
|
363 | 363 | TRACE_EXIT(23,DDERR_INVALIDPARAMS);
|
364 | 364 | return DDERR_INVALIDPARAMS;
|
— | — | @@ -418,7 +418,7 @@ |
419 | 419 | HRESULT WINAPI DirectDrawEnumerateExW(LPDDENUMCALLBACKEXW lpCallback, LPVOID lpContext, DWORD dwFlags)
|
420 | 420 | {
|
421 | 421 | TRACE_ENTER(3,14,lpCallback,14,lpContext,9,dwFlags);
|
422 | | - if(!IsReadablePointer(lpCallback))
|
| 422 | + if (!IsReadablePointer(lpCallback, 1))
|
423 | 423 | {
|
424 | 424 | TRACE_EXIT(23,DDERR_GENERIC);
|
425 | 425 | return DDERR_INVALIDPARAMS;
|
Index: ddraw/glDirectDraw.cpp |
— | — | @@ -603,7 +603,7 @@ |
604 | 604 | glD3D3 = new glDirect3D3(glD3D7);
|
605 | 605 | glD3D2 = new glDirect3D2(glD3D7);
|
606 | 606 | glD3D1 = new glDirect3D1(glD3D7);
|
607 | | - if (((ULONG_PTR)lpGUID > 2) && !IsReadablePointer(lpGUID))
|
| 607 | + if (((ULONG_PTR)lpGUID > 2) && !IsReadablePointer(lpGUID, sizeof(GUID)))
|
608 | 608 | {
|
609 | 609 | error = DDERR_INVALIDPARAMS ;
|
610 | 610 | TRACE_EXIT(-1,0);
|
— | — | @@ -863,7 +863,7 @@ |
864 | 864 | HRESULT WINAPI glDirectDraw7::CreatePalette(DWORD dwFlags, LPPALETTEENTRY lpDDColorArray, LPDIRECTDRAWPALETTE FAR *lplpDDPalette, IUnknown FAR *pUnkOuter)
|
865 | 865 | {
|
866 | 866 | TRACE_ENTER(5, 14, this, 9, dwFlags, 14, lpDDColorArray, 14, lplpDDPalette, 14, pUnkOuter);
|
867 | | - if (!this) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
| 867 | + if (!IsReadablePointer(this,sizeof(glDirectDraw7))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
868 | 868 | if (pUnkOuter) TRACE_RET(HRESULT, 23, CLASS_E_NOAGGREGATION);
|
869 | 869 | HRESULT ret = CreatePalette2(dwFlags, lpDDColorArray, lplpDDPalette, pUnkOuter);
|
870 | 870 | if (ret == DD_OK)
|
— | — | @@ -878,7 +878,7 @@ |
879 | 879 | HRESULT glDirectDraw7::CreatePalette2(DWORD dwFlags, LPPALETTEENTRY lpDDColorArray, LPDIRECTDRAWPALETTE FAR *lplpDDPalette, IUnknown FAR *pUnkOuter)
|
880 | 880 | {
|
881 | 881 | TRACE_ENTER(5,14,this,9,dwFlags,14,lpDDColorArray,14,lplpDDPalette,14,pUnkOuter);
|
882 | | - if(!this) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 882 | + if (!IsReadablePointer(this, sizeof(glDirectDraw7))) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
883 | 883 | if(!lplpDDPalette) TRACE_RET(HRESULT,23,DDERR_INVALIDPARAMS);
|
884 | 884 | if(pUnkOuter) TRACE_RET(HRESULT,23,CLASS_E_NOAGGREGATION);
|
885 | 885 | if (!cooplevel) TRACE_RET(HRESULT, 23, DDERR_NOCOOPERATIVELEVELSET);
|
— | — | @@ -2132,7 +2132,7 @@ |
2133 | 2133 | HRESULT WINAPI glDirectDraw1::CreatePalette(DWORD dwFlags, LPPALETTEENTRY lpDDColorArray, LPDIRECTDRAWPALETTE FAR *lplpDDPalette, IUnknown FAR *pUnkOuter)
|
2134 | 2134 | {
|
2135 | 2135 | TRACE_ENTER(5, 14, this, 9, dwFlags, 14, lpDDColorArray, 14, lplpDDPalette, 14, pUnkOuter);
|
2136 | | - if (!this) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
| 2136 | + if (!IsReadablePointer(this, sizeof(glDirectDraw1))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
2137 | 2137 | HRESULT ret = glDD7->CreatePalette2(dwFlags, lpDDColorArray, lplpDDPalette, pUnkOuter);
|
2138 | 2138 | TRACE_EXIT(23, ret);
|
2139 | 2139 | return ret;
|
— | — | @@ -2332,7 +2332,7 @@ |
2333 | 2333 | HRESULT WINAPI glDirectDraw2::CreatePalette(DWORD dwFlags, LPPALETTEENTRY lpDDColorArray, LPDIRECTDRAWPALETTE FAR *lplpDDPalette, IUnknown FAR *pUnkOuter)
|
2334 | 2334 | {
|
2335 | 2335 | TRACE_ENTER(5, 14, this, 9, dwFlags, 14, lpDDColorArray, 14, lplpDDPalette, 14, pUnkOuter);
|
2336 | | - if (!this) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
| 2336 | + if (!IsReadablePointer(this, sizeof(glDirectDraw2))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
2337 | 2337 | HRESULT ret = glDD7->CreatePalette2(dwFlags, lpDDColorArray, lplpDDPalette, pUnkOuter);
|
2338 | 2338 | TRACE_EXIT(23, ret);
|
2339 | 2339 | return ret;
|
— | — | @@ -2556,7 +2556,7 @@ |
2557 | 2557 | HRESULT WINAPI glDirectDraw4::CreatePalette(DWORD dwFlags, LPPALETTEENTRY lpDDColorArray, LPDIRECTDRAWPALETTE FAR *lplpDDPalette, IUnknown FAR *pUnkOuter)
|
2558 | 2558 | {
|
2559 | 2559 | TRACE_ENTER(5, 14, this, 9, dwFlags, 14, lpDDColorArray, 14, lplpDDPalette, 14, pUnkOuter);
|
2560 | | - if (!this) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
| 2560 | + if (!IsReadablePointer(this, sizeof(glDirectDraw4))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
2561 | 2561 | HRESULT ret = glDD7->CreatePalette2(dwFlags, lpDDColorArray, lplpDDPalette, pUnkOuter);
|
2562 | 2562 | if (ret == DD_OK)
|
2563 | 2563 | {
|
Index: ddraw/glDirectDrawPalette.c |
— | — | @@ -1,5 +1,5 @@ |
2 | 2 | // DXGL
|
3 | | -// Copyright (C) 2011-2014 William Feely
|
| 3 | +// Copyright (C) 2011-2016 William Feely
|
4 | 4 |
|
5 | 5 | // This library is free software; you can redistribute it and/or
|
6 | 6 | // modify it under the terms of the GNU Lesser General Public
|
— | — | @@ -17,6 +17,7 @@ |
18 | 18 |
|
19 | 19 | #include "common.h"
|
20 | 20 | #include "glDirectDrawPalette.h"
|
| 21 | +#include "util.h"
|
21 | 22 |
|
22 | 23 |
|
23 | 24 | const unsigned char DefaultPalette[1024] = {
|
— | — | @@ -90,7 +91,7 @@ |
91 | 92 | HRESULT WINAPI glDirectDrawPalette_QueryInterface(glDirectDrawPalette *This, REFIID riid, void** ppvObj)
|
92 | 93 | {
|
93 | 94 | TRACE_ENTER(3,14,This,24,&riid,14,ppvObj);
|
94 | | - if(!This) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 95 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
95 | 96 | if(!ppvObj) TRACE_RET(HRESULT,23,DDERR_INVALIDPARAMS);
|
96 | 97 | if(!memcmp(riid,&IID_IUnknown,sizeof(GUID)))
|
97 | 98 | {
|
— | — | @@ -107,7 +108,7 @@ |
108 | 109 | ULONG WINAPI glDirectDrawPalette_AddRef(glDirectDrawPalette *This)
|
109 | 110 | {
|
110 | 111 | TRACE_ENTER(1,14,This);
|
111 | | - if(!This) return 0;
|
| 112 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(ULONG, 8, 0);
|
112 | 113 | This->refcount++;
|
113 | 114 | TRACE_EXIT(8,This->refcount);
|
114 | 115 | return This->refcount;
|
— | — | @@ -117,7 +118,7 @@ |
118 | 119 | {
|
119 | 120 | ULONG ret;
|
120 | 121 | TRACE_ENTER(1, 14, This);
|
121 | | - if(!This) return 0;
|
| 122 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(ULONG, 8, 0);
|
122 | 123 | This->refcount--;
|
123 | 124 | ret = This->refcount;
|
124 | 125 | if (This->refcount == 0)
|
— | — | @@ -132,7 +133,8 @@ |
133 | 134 | HRESULT WINAPI glDirectDrawPalette_GetCaps(glDirectDrawPalette *This, LPDWORD lpdwCaps)
|
134 | 135 | {
|
135 | 136 | TRACE_ENTER(2,14,This,14,lpdwCaps);
|
136 | | - if(!This) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 137 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
| 138 | + if (!IsReadablePointer(lpdwCaps, sizeof(LPDWORD))) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
137 | 139 | *lpdwCaps = This->flags;
|
138 | 140 | TRACE_VAR("*lpdwCaps",9,*lpdwCaps);
|
139 | 141 | TRACE_EXIT(23,DD_OK);
|
— | — | @@ -144,7 +146,7 @@ |
145 | 147 | DWORD allentries = 256;
|
146 | 148 | DWORD entrysize;
|
147 | 149 | TRACE_ENTER(5, 14, This, 9, dwFlags, 8, dwBase, 8, dwNumEntries, 14, lpEntries);
|
148 | | - if(!This) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 150 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
149 | 151 | if(This->flags & DDPCAPS_1BIT) allentries=2;
|
150 | 152 | if(This->flags & DDPCAPS_2BIT) allentries=4;
|
151 | 153 | if(This->flags & DDPCAPS_4BIT) allentries=16;
|
— | — | @@ -159,7 +161,7 @@ |
160 | 162 | HRESULT WINAPI glDirectDrawPalette_Initialize(glDirectDrawPalette *This, LPDIRECTDRAW lpDD, DWORD dwFlags, LPPALETTEENTRY lpDDColorTable)
|
161 | 163 | {
|
162 | 164 | TRACE_ENTER(4,14,This,14,lpDD,9,dwFlags,14,lpDDColorTable);
|
163 | | - if(!This) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 165 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(HRESULT, 23, DDERR_INVALIDOBJECT);
|
164 | 166 | TRACE_EXIT(23,DDERR_ALREADYINITIALIZED);
|
165 | 167 | return DDERR_ALREADYINITIALIZED;
|
166 | 168 | }
|
— | — | @@ -168,7 +170,7 @@ |
169 | 171 | DWORD allentries = 256;
|
170 | 172 | DWORD entrysize;
|
171 | 173 | TRACE_ENTER(5, 14, This, 9, dwFlags, 8, dwStartingEntry, 8, dwCount, 14, lpEntries);
|
172 | | - if(!This) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
| 174 | + if (!IsReadablePointer(This, sizeof(glDirectDrawPalette))) TRACE_RET(HRESULT,23,DDERR_INVALIDOBJECT);
|
173 | 175 | if(This->flags & DDPCAPS_1BIT) allentries=2;
|
174 | 176 | if(This->flags & DDPCAPS_2BIT) allentries=4;
|
175 | 177 | if(This->flags & DDPCAPS_4BIT) allentries=16;
|
— | — | @@ -213,7 +215,8 @@ |
214 | 216 | {
|
215 | 217 | glDirectDrawPalette *newpal;
|
216 | 218 | TRACE_ENTER(3,9,dwFlags,14,lpDDColorArray,14,lplpDDPalette);
|
217 | | - if (!lplpDDPalette) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
| 219 | + if (!IsWritablePointer(lplpDDPalette, sizeof(LPDIRECTDRAWPALETTE), FALSE)) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
| 220 | + if (lpDDColorArray && !IsReadablePointer(lpDDColorArray,256*sizeof(PALETTEENTRY))) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
218 | 221 | if (dwFlags & 0xFFFFF000) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
219 | 222 | if ((dwFlags & DDPCAPS_8BIT) && (dwFlags & DDPCAPS_8BITENTRIES)) TRACE_RET(HRESULT, 23, DDERR_INVALIDPARAMS);
|
220 | 223 | if (((dwFlags & DDPCAPS_1BIT) || (dwFlags & DDPCAPS_2BIT) || (dwFlags & DDPCAPS_4BIT)) && (dwFlags & DDPCAPS_ALLOW256))
|
Index: ddraw/util.c |
— | — | @@ -1,5 +1,5 @@ |
2 | 2 | // DXGL
|
3 | | -// Copyright (C) 2013-2014 William Feely
|
| 3 | +// Copyright (C) 2013-2016 William Feely
|
4 | 4 |
|
5 | 5 | // This library is free software; you can redistribute it and/or
|
6 | 6 | // modify it under the terms of the GNU Lesser General Public
|
— | — | @@ -18,24 +18,31 @@ |
19 | 19 | #include "common.h"
|
20 | 20 | #include "util.h"
|
21 | 21 |
|
| 22 | +#ifdef _MSC_VER
|
| 23 | +#pragma optimize("g", off)
|
| 24 | +#endif
|
22 | 25 | /**
|
23 | | - * Tests if a pointer is valid for reading from. Compile in Visual C++ with /EHa
|
24 | | - * enabled Structed Exception Handling in C++ code, to prevent crashes on invalid
|
25 | | - * pointers.
|
| 26 | + * Tests if a pointer is valid for reading from. Uses SEH on Visual C++,
|
| 27 | + * non-recommended Windows API on other systems.
|
26 | 28 | * @param ptr
|
27 | 29 | * Pointer to test for validity.
|
| 30 | + * @param size
|
| 31 | + * Size of block to check
|
28 | 32 | * @return
|
29 | | - * Returns false if the pointer is valid, or true if an error occurs.
|
| 33 | + * Returns non-zero if the pointer is valid, or zero if an error occurs.
|
30 | 34 | */
|
31 | | -char IsReadablePointer(void *ptr)
|
| 35 | +char IsReadablePointer(void *ptr, LONG_PTR size)
|
32 | 36 | {
|
33 | 37 | char a;
|
| 38 | + char *ptr2 = ptr;
|
34 | 39 | if(!ptr) return 0;
|
35 | 40 | #ifdef _MSC_VER
|
36 | 41 | __try
|
37 | 42 | {
|
38 | | - a = *(char*)ptr;
|
| 43 | + a = ptr2[0];
|
39 | 44 | if (!a) a++;
|
| 45 | + if (size > 1) a = ptr2[size-1];
|
| 46 | + if (!a) a++;
|
40 | 47 | return a;
|
41 | 48 | }
|
42 | 49 | __except (GetExceptionCode() == STATUS_ACCESS_VIOLATION)
|
— | — | @@ -43,7 +50,49 @@ |
44 | 51 | return 0;
|
45 | 52 | }
|
46 | 53 | #else
|
47 | | - if(IsBadReadPtr(ptr,1) return 0;
|
48 | | - else return 1;)
|
| 54 | + if(IsBadReadPtr(ptr,size)) return 0;
|
| 55 | + else return 1;
|
49 | 56 | #endif
|
50 | 57 | }
|
| 58 | +
|
| 59 | +/**
|
| 60 | +* Tests if a pointer is valid for writing to. Uses SEH on Visual C++,
|
| 61 | +* non-recommended Windows API on other systems.
|
| 62 | +* @param ptr
|
| 63 | +* Pointer to test for validity.
|
| 64 | +* @param size
|
| 65 | +* Size of block to check
|
| 66 | +* @param preserve
|
| 67 | +* TRUE to preserve the contents of the pointer.
|
| 68 | +* @return
|
| 69 | +* Returns false if the pointer is valid, or true if an error occurs.
|
| 70 | +*/
|
| 71 | +char IsWritablePointer(void *ptr, LONG_PTR size, BOOL preserve)
|
| 72 | +{
|
| 73 | + char a;
|
| 74 | + char *ptr2 = ptr;
|
| 75 | + if (!ptr) return 0;
|
| 76 | +#ifdef _MSC_VER
|
| 77 | + __try
|
| 78 | + {
|
| 79 | + if (preserve) a = ptr2[0];
|
| 80 | + else a = 1;
|
| 81 | + ptr2[0] = a + 1;
|
| 82 | + if (preserve) ptr2[0] = a;
|
| 83 | + if (size > 1)
|
| 84 | + {
|
| 85 | + if (preserve) a = ptr2[size-1];
|
| 86 | + ptr2[size-1] = a + 1;
|
| 87 | + if (preserve) ptr2[size-1] = a;
|
| 88 | + }
|
| 89 | + return 1;
|
| 90 | + }
|
| 91 | + __except (GetExceptionCode() == STATUS_ACCESS_VIOLATION)
|
| 92 | + {
|
| 93 | + return 0;
|
| 94 | + }
|
| 95 | +#else
|
| 96 | + if (IsBadWritePtr(ptr, 1)) return 0;
|
| 97 | + else return 1;
|
| 98 | +#endif
|
| 99 | +} |
\ No newline at end of file |
Index: ddraw/util.h |
— | — | @@ -1,5 +1,5 @@ |
2 | 2 | // DXGL
|
3 | | -// Copyright (C) 2013-2014 William Feely
|
| 3 | +// Copyright (C) 2013-2016 William Feely
|
4 | 4 |
|
5 | 5 | // This library is free software; you can redistribute it and/or
|
6 | 6 | // modify it under the terms of the GNU Lesser General Public
|
— | — | @@ -23,7 +23,8 @@ |
24 | 24 | extern "C" {
|
25 | 25 | #endif
|
26 | 26 |
|
27 | | -char IsReadablePointer(void *ptr);
|
| 27 | +char IsReadablePointer(void *ptr, LONG_PTR size);
|
| 28 | +char IsWritablePointer(void *ptr, LONG_PTR size, BOOL preserve);
|
28 | 29 |
|
29 | 30 | #ifdef __cplusplus
|
30 | 31 | }
|