115 lines
		
	
	
		
			3.2 KiB
		
	
	
	
		
			C++
		
	
	
	
			
		
		
	
	
			115 lines
		
	
	
		
			3.2 KiB
		
	
	
	
		
			C++
		
	
	
	
| //////////////////////////////////////////////////////////////////////////////
 | |
| //
 | |
| //  Detour functions of a COM interface (commem.cpp of commem.exe)
 | |
| //
 | |
| //  Microsoft Research Detours Package
 | |
| //
 | |
| //  Copyright (c) Microsoft Corporation.  All rights reserved.
 | |
| //
 | |
| //
 | |
| //
 | |
| #include <stdio.h>
 | |
| 
 | |
| //////////////////////////////////////////////////////////////////////////////
 | |
| //
 | |
| //  WARNING:
 | |
| //
 | |
| //  CINTERFACE must be defined so that the lpVtbl pointer is visible
 | |
| //  on COM interfaces.  However, once we've defined it, we must use
 | |
| //  coding conventions when accessing interface members, for example:
 | |
| //      i->lpVtbl->Write
 | |
| //  instead of the C++ syntax:
 | |
| //      i->Write.
 | |
| //  We must also pass the implicit "this" parameter explicitly:
 | |
| //      i->lpVtbl->Write(i, pb, 0, NULL)
 | |
| //  instead of the C++ syntax:
 | |
| //      i->Write(pb, 0, NULL)
 | |
| //
 | |
| #define CINTERFACE
 | |
| #include <ole2.h>
 | |
| #include <windows.h>
 | |
| #include <detours.h>
 | |
| 
 | |
| //////////////////////////////////////////////////////////////////////////////
 | |
| //
 | |
| HRESULT (STDMETHODCALLTYPE *RealIStreamWrite)(IStream * This,
 | |
|                                               const void *pv,
 | |
|                                               ULONG cb,
 | |
|                                               ULONG *pcbWritten) = NULL;
 | |
| 
 | |
| HRESULT STDMETHODCALLTYPE MineIStreamWrite(IStream * This,
 | |
|                                            const void *pv,
 | |
|                                            ULONG cb,
 | |
|                                            ULONG *pcbWritten)
 | |
| {
 | |
|     HRESULT hr;
 | |
|     ULONG cbWritten = 0;
 | |
|     if (pcbWritten == NULL) {
 | |
|         pcbWritten = &cbWritten;
 | |
|     }
 | |
| 
 | |
|     printf("commem:   %p->IStreamWrite(pv=%p, cb=%ld)\n", This, pv, cb);
 | |
|     hr = RealIStreamWrite(This, pv, cb, pcbWritten);
 | |
|     printf("commem:   %p->IStreamWrite -> %08lx (pcbWritten=%ld)\n", This, hr, *pcbWritten);
 | |
| 
 | |
|     return hr;
 | |
| }
 | |
| 
 | |
| //////////////////////////////////////////////////////////////////////////////
 | |
| //
 | |
| int main(int argc, char **argv)
 | |
| {
 | |
|     HRESULT hr;
 | |
| 
 | |
|     (void)argc;
 | |
|     (void)argv;
 | |
| 
 | |
|     LPSTREAM pStream = NULL;
 | |
|     ULARGE_INTEGER ul;
 | |
|     LARGE_INTEGER li;
 | |
| 
 | |
|     CoInitialize(NULL);
 | |
| 
 | |
|     hr = CreateStreamOnHGlobal(NULL, TRUE, &pStream);
 | |
| 
 | |
|     RealIStreamWrite = pStream->lpVtbl->Write;
 | |
| 
 | |
|     ul.QuadPart = 512;
 | |
|     hr = pStream->lpVtbl->SetSize(pStream, ul);
 | |
|     li.QuadPart = 0;
 | |
|     hr = pStream->lpVtbl->Seek(pStream, li, STREAM_SEEK_SET, NULL);
 | |
| 
 | |
|     printf("commem: Calling Write w/o before attach.\n");
 | |
| 
 | |
|     li.QuadPart = 0;
 | |
|     hr = pStream->lpVtbl->Write(pStream, &ul, sizeof(ul), NULL);
 | |
| 
 | |
|     DetourTransactionBegin();
 | |
|     DetourUpdateThread(GetCurrentThread());
 | |
|     DetourAttach(&(PVOID&)RealIStreamWrite, MineIStreamWrite);
 | |
|     DetourTransactionCommit();
 | |
| 
 | |
|     printf("commem: Calling Write w/o after attach.\n");
 | |
| 
 | |
|     li.QuadPart = 1;
 | |
|     hr = pStream->lpVtbl->Write(pStream, &li, sizeof(li), NULL);
 | |
| 
 | |
|     DetourTransactionBegin();
 | |
|     DetourUpdateThread(GetCurrentThread());
 | |
|     DetourDetach(&(PVOID&)RealIStreamWrite, MineIStreamWrite);
 | |
|     DetourTransactionCommit();
 | |
| 
 | |
|     printf("commem: Calling Write w/o after detach.\n");
 | |
| 
 | |
|     li.QuadPart = 2;
 | |
|     hr = pStream->lpVtbl->Write(pStream, &li, sizeof(li), NULL);
 | |
| 
 | |
|     hr = pStream->lpVtbl->Release(pStream);
 | |
|     pStream = NULL;
 | |
| 
 | |
|     CoUninitialize();
 | |
| 
 | |
|     return 0;
 | |
| }
 | |
| 
 |