Click here to Skip to main content
12,296,833 members (63,282 online)
Click here to Skip to main content

Stats

138.6K views
9.7K downloads
169 bookmarked
Posted

Password SPY++

, 26 Sep 2005
Peeking ***** off both the password edit boxes and the input field on a homepage residing inside an Internet Explorer window.
SuperPwdHook.dll
SuperPwdSpy.exe
Doc
SPwdSpyArchitecture.gif
SPwdSpyIE-class.gif
SPwdSpyInterface1.jpg
SPwdSpyInterface2.jpg
SPwdSpyInterface3.jpg
SPwdSpyInterface4.jpg
SPwdSpyPortrait.jpg
Release
SuperPwdHook.dll
SuperPwdSpy.exe
res
blank.ico
blank_ic.ico
BMPBACK.BMP
ico00001.ico
look.cur
look.ico
look_cur.cur
look_ico.ico
main.ico
notstaytop.ico
portrait.jpg
staytop.ico
SuperPwdSpy.ico
SuperPwdHook.dsp
SuperPwdHook.dsw
SuperPwdSpy.clw
SuperPwdSpy.dsp
SuperPwdSpy.dsw
// SuperPwdHook.cpp : Defines the entry point for the DLL application.
//

/************************************
  REVISION LOG ENTRY
  Revision By: Zhang, Zhefu
  Contact: codetiger@hotmail.com
  Revised on 12/7/2002 10:44:33 AM
  Comment: Following Source is Written To Contribute to WWW.CodeGuru.Com
  Also check http://codeguru.earthweb.com/ieprogram/SPwdSpy.html
       for latest patch
 ************************************/


#include "DLLstdafx.h"
#include "SuperPwdHook.h"
#include <TCHAR.h>

#define _WIN32_WINNT  0x0500
#ifdef _WIN32_IE 
  #undef _WIN32_IE
  #define _WIN32_IE 0x0500
#endif

// Forward references
//LRESULT WINAPI GetMsgProc(int nCode, WPARAM wParam, LPARAM lParam);
LRESULT CALLBACK CallWndProcHook(int nCode, WPARAM wParam, LPARAM lParam) ;
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);

// Instruct the compiler to put the g_hXXXhook data variable in 
// its own data section called Shared. We then instruct the 
// linker that we want to share the data in this section 
// with all instances of this application.
#pragma data_seg("Shared")
//Post Hook Handle 
HHOOK g_hHook = NULL;
HWND  g_hCaller = NULL;
HWND  g_hTarget = NULL;
UINT  g_msg = 0;
DWORD  g_bPasswordPage = 0;
//IHTMLDocument2 pointer
MSHTML::IHTMLDocument2Ptr g_lpHTMLDocument2 = NULL;
BOOL g_bReenter = FALSE;
#pragma data_seg()

// Instruct the linker to make the Shared section
// readable, writable, and shared.
#pragma comment(linker, "/section:Shared,rws")

// Nonshared variables
HINSTANCE g_hinstDll = NULL;

BOOL APIENTRY DllMain( HANDLE hModule, 
                       DWORD  ul_reason_for_call, 
                       LPVOID lpReserved
					 )
{
    switch (ul_reason_for_call)
	{
		case DLL_PROCESS_ATTACH:
			g_hinstDll = (HINSTANCE)hModule;
			break;
		case DLL_THREAD_ATTACH:
		case DLL_THREAD_DETACH:
		case DLL_PROCESS_DETACH:
			break;
    }
    return TRUE;
}

BOOL WINAPI SetHook(HWND hWndCaller, HWND hWndTarget, UINT uMsg)
{
	if(g_bReenter)
		PopMsg(_T("Re Enter Hook"));
	if(g_hHook)
		::UnsetHook(g_hCaller, g_hTarget);
//	g_hHook = SetWindowsHookEx(WH_GETMESSAGE, GetMsgProc,
//					       g_hinstDll, 
//						   GetWindowThreadProcessId(hWndTarget, NULL));
	g_hHook = SetWindowsHookEx(WH_CALLWNDPROC, (HOOKPROC) CallWndProcHook,
					       g_hinstDll, 
						   GetWindowThreadProcessId(hWndTarget, NULL));
	if(g_hHook == NULL)
	{
		return FALSE;
	}
	g_hCaller = hWndCaller;
    g_hTarget = hWndTarget;
    g_msg = uMsg;
	g_bPasswordPage = 0;

	g_bReenter = TRUE;
	return TRUE;
}

BOOL WINAPI UnsetHook(HWND hWndCaller, HWND hWndTarget)
{
//	if(g_lpHTMLDocument2)
//	{
//		g_lpHTMLDocument2->Release();
//		g_lpHTMLDocument2 = NULL;
//	}
	g_bReenter = FALSE;
	if(g_hHook)
		return UnhookWindowsHookEx(g_hHook);
	return FALSE;
}

/*
LRESULT WINAPI GetMsgProc(int nCode, WPARAM wParam, LPARAM lParam) 
{
	MSG* msg = (MSG*)lParam;
	
	// Uncomment the line below to invoke the debugger 
    // on the process that just got the injected DLL.
    // ForceDebugBreak();
   
	HWND hWnd = msg->hwnd;
	if(g_hTarget == hWnd && msg->message == g_msg)
	{
		TCHAR szBuffer[MAX_PATH] = {_T('\0')};
        //Password Fetch Here

		// Use a WM_COPYDATA message to send the password back to PasswordSpy
		COPYDATASTRUCT cds = {0};
		cds.dwData = (DWORD)hWnd;
		cds.cbData = (lstrlen(szBuffer) + 1) * sizeof(TCHAR);
		cds.lpData = szBuffer;

		SendMessage(g_hCaller, WM_COPYDATA, (WPARAM)hWnd, (LPARAM)&cds);
	}
	return(CallNextHookEx(g_hEditPostHook[dwIndex], nCode, wParam, lParam));
}
*/

//SendMessage Hook Proc
LRESULT CALLBACK CallWndProcHook(
  int nCode,      // hook code
  WPARAM wParam,  // If sent by the current thread, it is nonzero; otherwise, it is zero. 
  LPARAM lParam   // message data
)
{
	CWPSTRUCT* pCwp = (CWPSTRUCT*)lParam;
    
	if(pCwp->message == g_msg && pCwp->hwnd == g_hTarget)
	{
		if(pCwp->wParam == 0)
		{
			TCHAR szBuffer[MAX_PATH] = {_T('\0')};

//			HWND hParent = ::GetParent(g_hTarget);
//			HWND hwndEdit = CreateWindow( 
//                _T("EDIT"),     // predefined class 
//                NULL,       // no window title 
//                WS_CHILD | WS_VISIBLE | WS_VSCROLL | 
//                    ES_LEFT | ES_MULTILINE | ES_AUTOVSCROLL, 
//                0, 0, 0, 0, // set size in WM_SIZE message 
//                hParent,       // parent window 
//                (HMENU)555, // edit control ID 
//                (HINSTANCE) GetWindowLong(g_hTarget, GWL_HINSTANCE), 
//                NULL);                // pointer not needed 
//
//          LONG_PTR lpNewEdit = GetWindowLongPtr(hwndEdit, GWLP_WNDPROC); 
//			LONG_PTR lp = ::SetWindowLongPtr(g_hTarget, GWLP_WNDPROC, (LONG_PTR)lpNewEdit); 
  
            //Password Fetch Here
            SendMessage(g_hTarget, WM_GETTEXT, sizeof(szBuffer) / sizeof(TCHAR), (LPARAM)szBuffer);

            //::SetWindowLongPtr(g_hTarget, GWLP_WNDPROC, (LONG_PTR)lp); 

		    // Use a WM_COPYDATA message to send the password back to PasswordSpy
		    COPYDATASTRUCT cds = {0};
		    cds.dwData = (DWORD)g_hTarget;
		    cds.cbData = (lstrlen(szBuffer) + 1) * sizeof(TCHAR);
		    cds.lpData = szBuffer;

		    SendMessage(g_hCaller, WM_COPYDATA, (WPARAM)g_hTarget, (LPARAM)&cds);		
		}
		else if(pCwp->wParam == 1) //If Password Page
		{
			CoInitialize(NULL);
			if(HWnd2HtmlDocument())
				g_bPasswordPage = CheckHtmlDocument();

			//Quit IHTMLDocument2
			if(g_lpHTMLDocument2)
			{
				g_lpHTMLDocument2->Release();
			    g_lpHTMLDocument2 = NULL;
			}
			CoUninitialize();

//			if(HWnd2HtmlDocument())
//				g_bPasswordPage = CheckHtmlDocument();
//			else
//				PopMsg(_T("HWnd2HtmlDocument Failed"));
						

		}
		else if(pCwp->wParam == 2) //Query Page Password
		{
			CoInitialize(NULL);
			if(HWnd2HtmlDocument())
				CrackHtmlDocument();

			//Quit IHTMLDocument2
			if(g_lpHTMLDocument2)
			{
				g_lpHTMLDocument2->Release();
			    g_lpHTMLDocument2 = NULL;
			}
			CoUninitialize();
//			if(HWnd2HtmlDocument())
//			{
//				CrackHtmlDocument();
//			}
			
		}
	}
	if (nCode < 0) 
    {
		// just pass it on 
	    return CallNextHookEx (g_hHook, nCode, wParam, lParam) ;
    }  
	return CallNextHookEx (g_hHook, nCode, wParam, lParam) ;
}

BOOL WINAPI QueryPasswordEdit()
{
	if(g_hHook == NULL || g_hCaller == NULL || g_hTarget == NULL || g_msg == 0)
		return FALSE;
    ::SendMessage(g_hTarget, g_msg, 0, 0);
	return TRUE;
}

DWORD WINAPI IsPasswordPage()
{
	if(g_hHook == NULL || g_hCaller == NULL || g_hTarget == NULL || g_msg == 0)
	{
		::PopMsg(_T("IsPasswordPage Lack Para"));
		return FALSE;
	}
    ::SendMessage(g_hTarget, g_msg, 1, 0);
	return g_bPasswordPage;
}

BOOL WINAPI QueryPasswordPage()
{
	//return TRUE;

	if(g_hHook == NULL || g_hCaller == NULL || g_hTarget == NULL || g_msg == 0)
		return FALSE;
    ::SendMessage(g_hTarget, g_msg, 2, 0);
	return TRUE;
}

BOOL HWnd2HtmlDocument()
{
//	if(g_lpHTMLDocument2 != NULL)
//	{
//        ::PopMsg(_T("HWnd2HtmlDocument g_lpHTMLDocument2 != NULL"));
//		return TRUE;
//	}
	CoInitialize(NULL);
	HINSTANCE hInst = ::LoadLibrary( _T("OLEACC.DLL") );
	if ( hInst == NULL ) 
	{
		::ReportErr(_T("LoadLibrary Err"));
		return FALSE;
	}
	LRESULT lRes = 0;
		
	UINT nMsg = ::RegisterWindowMessage( _T("WM_HTML_GETOBJECT") );
	//PopMsg(_T("%u - %x"), nMsg, g_hTarget);
	LRESULT lRet = ::SendMessageTimeout( g_hTarget, nMsg,
		0L, 0L, SMTO_ABORTIFHUNG, 1000, (DWORD*)&lRes );
	
	//PopMsg(_T("%d"), lRes);
	//-2147221008

	if(lRet == 0)
	{
		::ReportErr(_T("SendMessageTimeout Err"));
		return FALSE;
	}

	LPFNOBJECTFROMLRESULT pfObjectFromLresult = (LPFNOBJECTFROMLRESULT)::GetProcAddress( hInst, "ObjectFromLresult");
	if ( pfObjectFromLresult == NULL )
	{
		::ReportErr(_T("GetProcAddress Err"));
		::FreeLibrary( hInst );
		CoUninitialize();
		return FALSE;
	}
	WCHAR strDoc[] =  L"{626fc520-a41e-11cf-a731-00a0c9082637}";
    CLSID uuidDoc;
    HRESULT hrDoc = CLSIDFromString((LPOLESTR)strDoc, 
		             &uuidDoc
					//IID_IHTMLDocument2
					);
    if(!SUCCEEDED(hrDoc))
	{
		::ReportErr(_T("CLSIDFromString Err"));
		::FreeLibrary( hInst );
		CoUninitialize();
		return FALSE; 
	}
//	if(g_lpHTMLDocument2 != NULL)
//		PopMsg(_T("IHTMLDocument2 = %lp"), g_lpHTMLDocument2);
	HRESULT hr;
	
	hr = (*pfObjectFromLresult)( lRes, 
		__uuidof(MSHTML::IHTMLDocument2),
		 //uuidDoc,
		//IID_IHTMLDocument,
		0, (void**)&g_lpHTMLDocument2);
	if ( SUCCEEDED(hr) )
	{
		//PopMsg(_T("SUCCEEDED(hr) %lp"), g_lpHTMLDocument2);
	}
	else
	{
		switch(hr)
		{
		case E_INVALIDARG:
			PopMsg(_T("E_INVALIDARG %lp"), g_lpHTMLDocument2);
			break;
		case E_NOINTERFACE:
			PopMsg(_T("E_NOINTERFACE"));
			break;
		case E_UNEXPECTED:
			PopMsg(_T("E_UNEXPECTED"));
			break;
		default:
			::ReportErr(_T("pfObjectFromLresult Err"));
			break;
		}
		::FreeLibrary( hInst );
		CoUninitialize();
		return FALSE;
	}	
	::FreeLibrary( hInst );
	CoUninitialize();
	return TRUE;
}


//Oops, g_lpHTMLDocument2 = NULL here??
DWORD CheckHtmlDocument()
{
	if(g_lpHTMLDocument2 == NULL)
	{
		::PopMsg(_T("CheckHtmlDocument g_lpHTMLDocument2 = NULL"));
		return 0;
	}
	MSHTML::IHTMLElementCollection *pForm;	
    HRESULT hr = g_lpHTMLDocument2->get_all(&pForm);
	if(FAILED(hr)) return 0;
	long len;
    pForm->get_length(&len);
	DWORD dwRet = 0;
	for(int i = 0; i < len; i++)
	{
		LPDISPATCH lpItem = pForm->item(CComVariant(i), CComVariant(i));

		MSHTML::IHTMLInputElementPtr lpInput;
        HRESULT hr = lpItem->QueryInterface(&lpInput);
		if(FAILED(hr)) continue;

		_bstr_t type(_T("password"));
		if(lpInput->Gettype() == type)
		{
			//_bstr_t x = lpInput->Getvalue();
            dwRet++;
//			lpItem->Release();
//		    lpItem = NULL;
//			pForm->Release();
//	        pForm = NULL;
//			return TRUE;
		}
		lpItem->Release();
		lpItem = NULL;
	}
	pForm->Release();
	pForm = NULL;
	return dwRet;
}


	
BOOL CrackHtmlDocument()
{
	//bytes: 4       + 16              + string len + 1           + 
	//  field number + No1. field Rect + field value(NULL ending) + No2. 

	BYTE buf[1024]; //should be enough
	LPBYTE lp = buf;
	lp += 4;
	MSHTML::IHTMLElementCollection *pForm;	
    HRESULT hr = g_lpHTMLDocument2->get_all(&pForm);
	if(FAILED(hr)) return FALSE;
	long len;
    pForm->get_length(&len);
	DWORD dwRet = 0;
	for(int i = 0; i < len; i++)
	{
		LPDISPATCH lpItem = pForm->item(CComVariant(i), CComVariant(i));

		MSHTML::IHTMLInputElementPtr lpInput;
        HRESULT hr = lpItem->QueryInterface(&lpInput);
		if(FAILED(hr)) continue;

		_bstr_t type(_T("password"));
		if(lpInput->Gettype() == type)
		{
			dwRet++;
			LPBYTE bHead = lp;
			RECT rect;
             
			MSHTML::IHTMLElementPtr lpElement;
            hr = lpInput->QueryInterface(&lpElement);

			MSHTML::IHTMLElement2Ptr lpElement2;
            hr = lpInput->QueryInterface(&lpElement2);

			long left, top, width, height;
			left = lpElement->GetoffsetLeft() - lpElement2->GetclientLeft();
			top = lpElement->GetoffsetTop() - lpElement2->GetclientTop();
			width = lpElement->GetoffsetWidth();
			height = lpElement->GetoffsetHeight();

//			left = lpElement->GetclientLeft();
//			top = lpElement->GetclientTop();
//			width = lpElement->GetclientWidth();
//			height = lpElement->GetclientHeight();
			rect.left = left; rect.top = top;
			rect.right = left + width; rect.bottom = top + height;
			CopyMemory(lp, &rect, 16);			
			lp += 16; //coordinate
            _bstr_t x = lpInput->Getvalue();
			LPTSTR pStr = (LPTSTR)lp;
			if(::lstrlen((LPCTSTR)x) == 0)
			{
				::lstrcpy(pStr, (LPCTSTR)_T("<None>"));
			    lp += (::lstrlen(_T("<Empty Field>")) + 1)*sizeof(TCHAR);
			}
			else
			{
				::lstrcpy(pStr, (LPCTSTR)x);
			    lp += (::lstrlen(pStr) + 1)*sizeof(TCHAR);
			}
			lpElement->Release();
			lpElement = NULL;

			lpElement2->Release();
			lpElement2 = NULL;
		}
		lpItem->Release();
		lpItem = NULL;
	}
	pForm->Release();
	pForm = NULL;
    CopyMemory(buf, &dwRet, 4);

	COPYDATASTRUCT cds = {0};
	cds.dwData = (DWORD)g_hTarget;
	cds.cbData = 1024;
	cds.lpData = buf;

	SendMessage(g_hCaller, WM_COPYDATA, (WPARAM)g_hTarget, (LPARAM)&cds);		
	return TRUE;
}

//LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
//{
//	switch (message) 
//	{
//		case WM_DESTROY:
//			PostQuitMessage(0);
//			break;
//		default:
//			return DefWindowProc(hWnd, message, wParam, lParam);
//   }
//   return 0;
//}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

Share

About the Author

Zhefu Zhang
Other
United States United States
fdefewtr534554yutki8op09;[pio';l.n,kbnmcvbxcvzxaqW876876UIYIUJUGHJGFHYFGHRDTR4564QWEDASASFDXCBVCBNGHNMJHMJN,NJKL;O[P-0=-]'[P';L/L,M.NM,BNMCGNGFXDGDFGTYU76TRYW34TR5AWERFASDVGfdsxbvfbvnvnm,jkl.k

You may also be interested in...

| Advertise | Privacy | Terms of Use | Mobile
Web01 | 2.8.160525.2 | Last Updated 26 Sep 2005
Article Copyright 2005 by Zhefu Zhang
Everything else Copyright © CodeProject, 1999-2016
Layout: fixed | fluid