Đồ án Phần mềm keyloger sử dụng Hook Windows

MỤC LỤC

T ỔNG QUAN VỀ ĐỀ TÀI. 5

Chương 1. CƠ SỞ LÝ THUYẾT. 6

I. Giới thiệu. 6

II. Thông Điệp và HÀNG ĐỢI THÔNG ĐIỆP CỦA WINDOWS . 6

II.1. Giới thiệu. 6

II.1.1. Thông đi ệp windo ws . 6

II.1.2. Lo ại Thông điệp . 7

II.1.3. Lộ trình thông đi ệp . 10

II.1.4. Xử lý thông điệp . 12

II.1.5. Lọc thông điệp . 16

II.1.6. Đăng và chuyển thông điệp . 16

II.1.7. Bế tắc thông điệp . 18

II.1.8. Thông đi ệp quảng bá . 19

II.1.9. Truy vấn thông điệp . 20

II.2. Sử dụng thông điệp và hàng đợi thông điệp . 21

II.2.1. T ạo vòng lặp thông điệp . 21

II.2.2. Kiểm tra một hàng đ ợi thông điệp . 24

II.2.3. Đăng thông đi ệp . 25

II.2.4. Gửi một thông đi ệp . 26

III. k ỹ thu ật hook . 28

III.1. Giới thiệu . 28

III.2. Chuỗi Hook . 29

III.2.1. Thủ tục Hook. 29

III.2.2. Các kiểu Hook . 29

III.3. Cách s ử dụng . 31

III.3.1. Cài đ ặt Hook . 31

III.3.2. Giải phóng Hook . 31

IV. win 32 api . 32

IV.1. Giới thiệu . 32

IV.2. Các hàm thườ ng dùng . 32

IV.2.1. SetWindowsHookEx . 32

IV.2.2. UnhookWindowsHookEx . 33

IV.2.3. CallNextHookEx. 33

IV.2.4. LowLevelKeyboardProc . 34

IV.2.5. GetKeyState . 35

IV.2.6. GetKeyboardState . 35

IV.2.7. To Ascii . 35

IV.2.8. LoadLibrary. 36

IV.2.9. GetProcAddress . 36

IV.2.10. OpenProcess . 36

IV.2.11. EnumProcessModules . 37

IV.2.12. GetModuleBaseName. 37

IV.2.13. GetForegroundWindow. 38

IV.2.14. GetWindowThreadProcessId . 38

IV.2.15. GetLocalTime . 39

IV.3. Mã bàn phím ảo . 39

Chương 2. PHÂN TÍCH VÀ XÂY DỰNG CHƯƠNG TRÌNH. 47

I. PHân tích yêu c ầu . 47

I.1. Yêu c ầu v ề chức năng . 47

I.2. Yêu c ầu v ề giao diện người dùng . 47

I.3. Yêu c ầu v ề tương thích . 47

II. phân tích chức năng. 47

III. xây dựng chức năng . 47

III.1. T ập tin thi hành Jaam.exe . 47

III.2. Thư viện Hooker.dll . 49

III.2.1. Phiên bản 1 . 49

III.2.2. Phiên bản 2 . 51

III.2.3. Phiên bản 3 . 53

Chương 3. TRIỂN KHAI VÀ ĐÁNH GIÁ KẾT QUẢ. 57

I. Môi trường triển khai. 57

II. Kết qu ả chức nĂng chương trình . 57

III. Đánh giá và nh ận xét . 58

pdf60 trang | Chia sẻ: maiphuongdc | Lượt xem: 6010 | Lượt tải: 2download
Bạn đang xem trước 20 trang tài liệu Đồ án Phần mềm keyloger sử dụng Hook Windows, để xem tài liệu hoàn chỉnh bạn click vào nút DOWNLOAD ở trên
kiểm soát bằng cách gửi một thông điệp tới nó. Việc kiểm soát có thể thông báo cho cửa sổ cha mẹ thay đổi văn bản được thực hiện bởi người sử dụng bằng cách gửi tin nhắn lại cho phụ huynh. 18 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ Chức năng SendMessageCallback cũng sẽ gửi một thông điệp tới các thủ tục cửa sổ tương ứng với cửa sổ nhất định. Tuy nhiên, chức năng này trả về ngay lập tức. Sau khi các thủ tục cửa sổ xử lý tin nhắn, hệ thống các cuộc gọi chức năng gọi lại quy định. Để biết thêm thông tin về chức năng gọi lại, thấy chức năng SendAsyncProc. Chức năng SendMessageCallback cũng sẽ gửi một thông điệp tới các thủ tục cửa sổ tương ứng với cửa sổ nhất định. Tuy nhiên, chức năng này trả về ngay lập tức. Sau khi các thủ tục cửa sổ xử lý tin nhắn, hệ thống các cuộc gọi chức năng gọi lại quy định. Để biết thêm thông tin về chức năng gọi lại, thấy chức năng SendAsyncProc. Bằng cách sử dụng chức năng InSendMessage hoặc InSendMessageEx, một thủ tục cửa sổ có thể xác định cho dù đó là chế biến một thông báo được gửi bởi thread khác. Khả năng này rất hữu ích khi xử lý thông báo phụ thuộc vào nguồn gốc của tin nhắn. II.1.7. Bế tắc thông điệp Một chủ đề đó gọi hàm SendMessage để gửi tin nhắn đến chủ đề khác không thể tiếp tục thực hiện cho đến khi các thủ tục cửa sổ nhận được tin nhắn trả về. Nếu sản lượng chủ đề được kiểm soát trong khi xử lý tin nhắn, các chủ đề gửi không có thể tiếp tục thực hiện, bởi vì nó là chờ đợi cho SendMessage trở lại. Nếu các chủ đề nhận được được gắn vào hàng đợi tương tự như người gửi, nó có thể gây ra một bế tắc ứng dụng để xảy ra. (Lưu ý rằng tạp chí móc đính kèm các chủ đề cùng một hàng đợi.) Lưu ý rằng các chủ đề nhận được cần không mang lại kiểm soát một cách rõ ràng, gọi điện thoại bất kỳ của các chức năng sau có thể gây ra một thread để năng suất kiểm soát ngầm. - DialogBox - DialogBoxIndirect - DialogBoxIndirectParam - DialogBoxParam KeyLogger-Sử dụng Hook Windows 19 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ - GetMessage - MessageBox - PeekMessage - SendMessage Để tránh bế tắc tiềm năng trong ứng dụng của bạn, hãy xem xét sử dụng SendNotifyMessage hoặc các chức năng SendMessageTimeout. Nếu không, một thủ tục cửa sổ có thể xác định xem một tin nhắn đã nhận được đã được gửi chủ đề khác bằng cách gọi InSendMessage hoặc InSendMessageEx chức năng. Trước khi gọi bất kỳ các chức năng trong danh sách trước khi thực hiện một tin nhắn, các thủ tục cửa sổ đầu tiên nên gọi InSendMessage hoặc InSendMessageEx. Nếu chức năng này trả về TRUE, các thủ tục cửa sổ phải gọi hàm ReplyMessage trước khi bất kỳ chức năng gây ra các chủ đề để sản lượng kiểm soát. II.1.8. Thông điệp quảng bá Mỗi thông điệp bao gồm một định danh thông điệp và hai tham số wParam và lParam. Từ định danh tin nhắn là một giá trị duy nhất quy định cụ thể mục đích thông báo. Các thông số cung cấp thông tin bổ sung đó là thông điệp cụ thể, nhưng các tham số wParam nói chung là một giá trị kiểu cung cấp thông tin về tin nhắn. Chương trình phát sóng tin nhắn chỉ đơn giản là gửi một tin nhắn tới nhiều người trong hệ thống. Để phát sóng một thông điệp từ một ứng dụng, sử dụng chức năng BroadcastSystemMessage, quy định cụ thể người nhận của tin nhắn. Thay vì chỉ định người nhận cá nhân, bạn phải chỉ định một hoặc nhiều loại người nhận. Những loại ứng dụng, trình điều khiển cài đặt, trình điều khiển mạng, và các trình điều khiển thiết bị hệ thống. Hệ thống sẽ gửi tin nhắn quảng bá cho tất cả các thành viên của từng loại quy định. Hệ thống này thường chương trình phát sóng thông điệp phản ứng với những thay đổi diễn ra trong các trình điều khiển thiết bị hệ thống hoặc các thành phần liên quan. Người lái xe hoặc thành phần liên quan đến chương trình phát sóng thông điệp đến các ứng dụng và các thành phần khác để thông báo cho họ về sự thay đổi. 20 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ Ví dụ, thành phần chịu trách nhiệm cho các ổ đĩa chương trình phát sóng một thông báo bất cứ khi nào điều khiển thiết bị cho các ổ đĩa mềm phát hiện một sự thay đổi của các phương tiện truyền thông chẳng hạn như khi người sử dụng chèn một đĩa vào ổ đĩa. Hệ thống chương trình phát sóng tin nhắn đến người nhận theo thứ tự này: hệ thống cấp trình điều khiển thiết bị, trình điều khiển mạng, cài đặt trình điều khiển, và các ứng dụng. Điều này có nghĩa là hệ thống cấp trình điều khiển thiết bị, nếu được lựa chọn như người nhận, luôn luôn có được cơ hội đầu tiên để đối phó với một tin nhắn. Trong thời hạn một loại người nhận nhất định, lái xe không được đảm bảo để nhận được thông báo đưa ra trước khi bất kỳ trình điều khiển khác. Điều này có nghĩa rằng một thông điệp dành cho một trình điều khiển cụ thể phải có một định danh tin nhắn trên toàn cầu duy nhất để không có trình điều khiển khác vô ý quá trình đó. Bạn cũng có thể phát sóng các tin nhắn cho tất cả các cửa sổ cấp cao nhất bằng cách xác định HWND_BROADCAST trong SendMessage, SendMessageCallback, SendMessageTimeout, hoặc SendNotifyMessage chức năng. Các ứng dụng nhận tin nhắn thông qua các thủ tục cửa sổ của cửa sổ cấp cao nhất của họ. Tin nhắn không được gửi đến các cửa sổ con. Dịch vụ có thể nhận tin nhắn thông qua một thủ tục xử lý cửa sổ hoặc dịch vụ kiểm soá Lưu ý hệ thống cấp trình điều khiển thiết bị sử dụng một chức năng, hệ thống cấp liên quan để phát sóng các thông báo hệ thống. II.1.9. Truy vấn thông điệp Bạn có thể tạo ra các tin nhắn tùy chỉnh của bạn và sử dụng chúng để phối hợp hoạt động giữa các ứng dụng của bạn và các thành phần khác trong hệ thống. Điều này đặc biệt hữu ích nếu bạn đã tạo ra trình điều khiển cài đặt riêng của bạn hoặc trình điều khiển thiết bị hệ thống cấp. Tin nhắn tuỳ chỉnh của bạn có thể mang thông tin đến và từ trình điều khiển của bạn và các ứng dụng sử dụng các trình điều khiển. KeyLogger-Sử dụng Hook Windows 21 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ Bạn có thể tạo ra các tin nhắn tùy chỉnh của bạn và sử dụng chúng để phối hợp hoạt động giữa các ứng dụng của bạn và các thành phần khác trong hệ thống. Điều này đặc biệt hữu ích nếu bạn đã tạo ra trình điều khiển cài đặt riêng của bạn hoặc trình điều khiển thiết bị hệ thống cấp. Tin nhắn tuỳ chỉnh của bạn có thể mang thông tin đến và từ trình điều khiển của bạn và các ứng dụng sử dụng các trình điều khiển. II.2. Sử dụng thông điệp và hàng đợi thông điệp II.2.1. Tạo vòng lặp thông điệp Các hệ thống không tự động tạo một hàng đợi tin nhắn cho mỗi thread. Thay vào đó, hệ thống sẽ tạo ra một hàng đợi tin nhắn chỉ dành cho các chủ đề thực hiện các hoạt động mà yêu cầu một hàng đợi thông điệp. Nếu chủ đề tạo ra một hoặc nhiều cửa sổ, một vòng lặp tin nhắn phải được cung cấp, vòng lặp thông điệp này lấy thông điệp từ hàng đợi thông điệp của thread và công văn cho họ các thủ tục cửa sổ thích hợp. Bởi vì hệ thống chỉ đạo thông báo cho các cửa sổ trong một ứng dụng cá nhân, một sợi phải tạo ra ít nhất một cửa sổ trước khi bắt đầu vòng lặp thông điệp của mình. Hầu hết các ứng dụng có chứa một chủ đề duy nhất mà tạo ra cửa sổ. Một ứng dụng điển hình đăng ký lớp cửa sổ cho cửa sổ chính của nó, tạo ra và hiển thị cửa sổ chính, và sau đó bắt đầu vòng lặp thông điệp của nó - tất cả trong hàm WinMain. Bạn tạo ra một vòng lặp tin nhắn bằng cách sử dụng chức năng GetMessage và DispatchMessage. Nếu ứng dụng của bạn phải có đầu vào nhân vật từ người sử dụng, bao gồm các chức năng TranslateMessage trong vòng lặp. TranslateMessage dịch ảo-key tin nhắn vào tin nhắn ký tự. Ví dụ sau đây cho thấy các vòng lặp tin nhắn trong các chức năng winmain của một ứng dụng đơn giản dựa trên Windows. HINSTANCE hinst; HWND hwndMain; int PASCAL WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdLine, int nCmdShow) { 22 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ MSG msg; BOOL bRet; WNDCLASS wc; UNREFERENCED_PARAMETER(lpszCmdLine); // Register the window class for the main window. if (!hPrevInstance) { wc.style = 0; wc.lpfnWndProc = (WNDPROC) WndProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hIcon = LoadIcon((HINSTANCE) NULL, IDI_APPLICATION); wc.hCursor = LoadCursor((HINSTANCE) NULL, IDC_ARROW); wc.hbrBackground = GetStockObject(WHITE_BRUSH); wc.lpszMenuName = "MainMenu"; wc.lpszClassName = "MainWndClass"; if (!RegisterClass(&wc)) return FALSE; } hinst = hInstance; // save instance handle // Create the main window. hwndMain = CreateWindow("MainWndClass", "Sample", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, (HWND) NULL, (HMENU) NULL, hinst, (LPVOID) NULL); // If the main window cannot be created, terminate // the application. if (!hwndMain) return FALSE; KeyLogger-Sử dụng Hook Windows 23 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ // Show the window and paint its contents. ShowWindow(hwndMain, nCmdShow); UpdateWindow(hwndMain); // Start the message loop. while( (bRet = GetMessage( &msg, NULL, 0, 0 )) != 0) { if (bRet == -1) { // handle the error and possibly exit } else { TranslateMessage(&msg); DispatchMessage(&msg); } } // Return the exit code to the system. return msg.wParam; } Ví dụ sau đây cho thấy một vòng lặp tin nhắn cho một chủ đề đó sử dụng máy gia tốc và hiển thị một hộp thoại modeless. Khi TranslateAccelerator hoặc IsDialogMessage trả về TRUE (chỉ ra rằng thông điệp đã được xử lý), TranslateMessage và DispatchMessage không được gọi. Lý do cho việc này là TranslateAccelerator và IsDialogMessage thực hiện tất cả các dịch cần thiết và cử các tin nhắn. HWND hwndMain; HWND hwndDlgModeless = NULL; MSG msg; BOOL bRet; HACCEL haccel; // // Perform initialization and create a main window. // while( (bRet = GetMessage( &msg, NULL, 0, 0 )) != 0) { if (bRet == -1) { 24 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ // handle the error and possibly exit } else { if (hwndDlgModeless == (HWND) NULL || !IsDialogMessage(hwndDlgModeless, &msg) && !TranslateAccelerator(hwndMain, haccel, &msg)) { TranslateMessage(&msg); DispatchMessage(&msg); } } } II.2.2. Kiểm tra một hàng đợi thông điệp Đôi khi, một ứng dụng cần kiểm tra các nội dung của hàng đợi thông điệp của một chủ đề từ bên ngoài vòng lặp thông điệp của chủ đề. Ví dụ, nếu thủ tục cửa sổ của một ứng dụng thực hiện một hoạt động bản vẽ dài, bạn có thể muốn người sử dụng có thể làm gián đoạn hoạt động. Trừ khi ứng dụng của bạn định kỳ kiểm tra hàng đợi thông điệp trong quá trình hoạt động cho chuột và tin nhắn bàn phím, nó sẽ không đáp ứng với người sử dụng đầu vào cho đến khi sau khi hoạt động đã hoàn thành. Lý do cho điều này là rằng các chức năng DispatchMessage trong vòng lặp thông điệp của chủ đề không trả lại cho đến khi các thủ tục cửa sổ kết thúc xử lý tin nhắn. Bạn có thể sử dụng chức năng PeekMessage để kiểm tra một hàng đợi thông điệp trong một hoạt động dài. PeekMessage tương tự như chức năng GetMessage, cả hai kiểm tra một hàng đợi tin nhắn cho một tin nhắn phù hợp với tiêu chuẩn bộ lọc và sau đó sao chép tin nhắn tới một cấu trúc MSG. Sự khác biệt chính giữa hai chức năng là GetMessage không trở lại cho đến khi một tin nhắn phù hợp với tiêu chuẩn lọc được đặt trong hàng đợi, trong khi PeekMessage trả về ngay lập tức bất kể cho dù một thông báo là trong hàng đợi. Ví dụ sau đây cho thấy làm thế nào để sử dụng PeekMessage để kiểm tra một hàng đợi tin nhắn cho số lần nhấp chuột và đầu vào bàn phím trong một hoạt động dài. HWND hwnd; BOOL fDone; MSG msg; // Begin the operation and continue until it is complete KeyLogger-Sử dụng Hook Windows 25 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ // or until the user clicks the mouse or presses a key. fDone = FALSE; while (!fDone) { fDone = DoLengthyOperation(); // application-defined function // Remove any messages that may be in the queue. If the // queue contains any mouse or keyboard // messages, end the operation. while (PeekMessage(&msg, hwnd, 0, 0, PM_REMOVE)) { switch(msg.message) { case WM_LBUTTONDOWN: case WM_RBUTTONDOWN: case WM_KEYDOWN: // // Perform any required cleanup. // fDone = TRUE; } } } Các chức năng khác, bao gồm cả GetQueueStatus và GetInputState, cũng cho phép bạn kiểm tra các nội dung của hàng đợi thông điệp của một chủ đề. GetQueueStatus trả về một mảng của lá cờ cho biết các loại tin nhắn trong hàng đợi, sử dụng nó là cách nhanh nhất để xác định xem liệu hàng đợi có chứa bất kỳ tin nhắn. GetInputState trả về TRUE nếu hàng đợi có chứa tin nhắn chuột hoặc bàn phím. Cả hai của các chức năng này có thể được sử dụng để xác định xem hàng đợi có chứa tin nhắn cần được xử lý. II.2.3. Đăng thông điệp Bạn có thể gửi một thông điệp tới một hàng đợi thông điệp bằng cách sử dụng chức năng PostMessage. PostMessage một tin nhắn vào cuối hàng đợi thông điệp của một chủ đề và trả về ngay lập tức, mà không cần chờ đợi cho thread để xử lý các tin nhắn. Các thông số của chức năng bao gồm một cửa sổ xử lý, nhận dạng một tin nhắn, và hai tham số tin nhắn. Hệ thống bản sao các thông số này một cấu trúc MSG, lấp đầy thời gian và các thành viên pt của cấu trúc, và cấu trúc trong các hàng đợi thông điệp. Hệ thống sử dụng cửa sổ xử lý được thông qua với chức năng PostMessage để xác định mà chủ đề hàng đợi tin nhắn sẽ nhận được thông báo. Nếu xử lý là 26 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ HWND_TOPMOST, các bài viết hệ thống tin nhắn tới hàng đợi tin nhắn của tất cả các cửa sổ cấp cao nhất trong chủ đề. Hệ thống sử dụng cửa sổ xử lý được thông qua với chức năng PostMessage để xác định mà chủ đề hàng đợi tin nhắn sẽ nhận được thông báo. Nếu xử lý là HWND_TOPMOST, các bài viết hệ thống tin nhắn tới hàng đợi tin nhắn của tất cả các cửa sổ cấp cao nhất trong chủ đề. Sử dụng chức năng PostQuitMessage để thoát khỏi vòng lặp thông điệp. PostQuitMessage thông điệp WM_QUIT các chủ đề hiện đang thực hiện. Vòng lặp thông điệp của chủ đề kết thúc và trả về kiểm soát hệ thống khi gặp phải thông điệp WM_QUIT. Một ứng dụng thường gọi PostQuitMessage trong phản ứng với thông điệp WM_DESTROY, như trong ví dụ sau đây. case WM_DESTROY: // Perform cleanup tasks. PostQuitMessage(0); break; II.2.4. Gửi một thông điệp Chức năng SendMessage được sử dụng để gửi tin nhắn trực tiếp đến một thủ tục cửa sổ. SendMessage gọi một thủ tục cửa sổ và chờ đợi cho rằng thủ tục để xử lý tin nhắn và trả lại kết quả. Một thông báo có thể được gửi đến bất kỳ cửa sổ trong hệ thống, tất cả những gì cần thiết là một cửa sổ xử lý. Hệ thống sử dụng xử lý để xác định thủ tục cửa sổ sẽ nhận được tin nhắn. Trước khi chế biến một thông điệp có thể được gửi từ chủ đề khác, một thủ tục cửa sổ đầu tiên nên gọi chức năng InSendMessage. Nếu chức năng này trả về TRUE, các thủ tục cửa sổ nên gọi ReplyMessage trước khi bất kỳ chức năng gây ra các chủ đề năng suất kiểm soát, như trong ví dụ sau đây. case WM_USER + 5: if (InSendMessage()) ReplyMessage(TRUE); DialogBox(hInst, "MyDialogBox", hwndMain, (DLGPROC) MyDlgProc); break; KeyLogger-Sử dụng Hook Windows 27 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ Một số tin nhắn có thể được gửi đến các điều khiển trong một hộp thoại. Những thông điệp điều khiển thiết lập sự xuất hiện, hành vi, và nội dung của các điều khiển hoặc lấy thông tin về điều khiển. Ví dụ, thông điệp CB_ADDSTRING có thể thêm một chuỗi một hộp kết hợp, và tin nhắn BM_SETCHECK có thể thiết lập nhà nước kiểm tra một hộp kiểm tra hoặc nút. Sử dụng chức năng SendDlgItemMessage để gửi một tin nhắn để kiểm soát, xác định định danh của kiểm soát và xử lý của cửa sổ hộp thoại có chứa kiểm soát. Ví dụ sau đây, được lấy từ một thủ tục hộp thoại, bản sao một chuỗi từ kiểm soát chỉnh sửa một hộp kết hợp vào hộp danh sách. Ví dụ sử dụng SendDlgItemMessage để gửi một tin nhắn CB_ADDSTRING vào hộp kết hợp. HWND hwndCombo; int cTxtLen; PSTR pszMem; switch (uMsg) { case WM_COMMAND: switch (LOWORD(wParam)) { case IDD_ADDCBITEM: // Get the handle of the combo box and the // length of the string in the edit control // of the combo box. hwndCombo = GetDlgItem(hwndDlg, IDD_COMBO); cTxtLen = GetWindowTextLength(hwndCombo); // Allocate memory for the string and copy // the string into the memory. pszMem = (PSTR) VirtualAlloc((LPVOID) NULL, (DWORD) (cTxtLen + 1), MEM_COMMIT, PAGE_READWRITE); GetWindowText(hwndCombo, pszMem, cTxtLen + 1); // Add the string to the list box of the // combo box and remove the string from the // edit control of the combo box. if (pszMem != NULL) { SendDlgItemMessage(hwndDlg, IDD_COMBO, CB_ADDSTRING, 0, (DWORD) ((LPSTR) pszMem)); SetWindowText(hwndCombo, (LPSTR) NULL); } // Free the memory and return. 28 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ VirtualFree(pszMem, 0, MEM_RELEASE); return TRUE; // // Process other dialog box commands. // } // // Process other dialog box messages. // } III. KỸ THUẬT HOOK III.1. Giới thiệu Các mô hình Hook : - Local hook: là kỹ thuật Hook dùng để bẫy sự kiện ngay trong tiến trình cài đặt. - Remote hook: là kỹ thuật Hook cho phép bẫy các sự kiện thuộc tiến trình của ứng dụng khác. Trong mô hình này lại tồn tại hai kiểu hook khác : + Thread-specific : kiểu Hook này sẽ bẫy sự kiện của một luồng cụ thể. + System-wide : bẫy sự kiện của tất cả các luồng trong tất cả các tiến trình đang thi hành trong hệ thống. Thành phần của Hook - Chuỗi Hook - Thủ tục Hook - Các kiểu Hook Hook là một kỹ thuật xử lý thông điệp rất mạnh cho phép chúng ta can thiệp sâu vào các tiến trình khác nhau, nhưng nó làm ảnh hưởng tới tốc độ của hệ thống, nhất là hook system-wide, vì tất cả các sự kiện của hệ thống sẽ được định hướng tới một hàm nào đó, rõ ràng điều này làm hệ thống chậm đi đáng kể. Vì thế ta chỉ hên hook những thông điệp thật cần thiết và kết thúc việc hook ngay khi không dùng đến nữa. KeyLogger-Sử dụng Hook Windows 29 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ III.2. Chuỗi Hook Hệ thống có khả năng hỗ trợ nhiều kiểu hook khác nhau, mỗi kiểu lại được quy định một cách thức truy nhập khác nhau trong kỹ thuật điều khiển thông điệp. Do vậy, hệ thống duy trì một chuỗi các hook cho mỗi một kiểu hook khác nhau. Một chuỗi hook là một danh sách các con trỏ đặc biệt, nó được trỏ tới các hàm CallBack gọi là hook procedure (thủ tục hook). Như vậy khi một sự kiện xuất hiện, hệ thống sẽ chuyển sự kiện đó tới các thủ tục hook được tham chiếu bới chuỗi hook theo thứ tự lần lượt. Vì thế phải thực hiện xong thủ tục này mới được gọi thủ tục kế tiếp. III.2.1. Thủ tục Hook Thủ tục hook sẽ là nơi thực hiện các thao tác sau khi bắt được một sự kiện mong muốn. Các thủ tục hook phụ thuộc vào các kiểu hook khác nhau mà có cấu trúc, chức năng khác nhau. Có thủ tục chỉ có thể điều khiển thông điệp, một số khác có thể sửa đổi thông điệp, dừng tiến trình của thông điệp, ngăn cản thực hiện hook tiếp theo hoặc đưa tới cửa sổ cuối cùng … Thủ tục hook có dạng chung như sau: LRESULT CALLBACK HookProc( int nCode, WPARAM wParam, LPARAM lParam ); Trong đó : - HookProc: là tên đại diện của thủ tục hook được cài đặt - nCode : Đây là mã hook, nó quyết định toàn bộ hoạt động của thủ tục hook, mã hook phụ thuộc vào kiểu hook và mỗi kiểu hook được gán cho một ký tự để thiết lập mã hook. - wParam, lParam: Hai tham số này chứa các thông tin về thông điệp được hook và nó phụ thuộc vào mã hook (nCode). III.2.2. Các kiểu Hook Mỗi một kiểu Hook cho phép ứng dụng điều khiển thông điệp theo những cách khác nhau trong kỹ thuật điều khiển thông điệp (message-handling mechanism). Dưới đây là những kiểu hook khác nhau : 30 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ - WH_CALLWNDPROC: Cài đặt một thủ tục hook theo dõi message trước khi hệ thống sẽ gửi chúng đến các thủ tục cửa sổ đích. - WH_CALLWNDPROCRET: Cài đặt một thủ tục hook theo dõi message sau khi đã được xử lý bởi các thủ tục cửa sổ đích. - WH_CBT: Cài đặt một thủ tục hook tiếp nhận thông báo hữu ích để một ứng dụng CBT. - WH_DEBUG: Cài đặt một thủ tục hook hữu ích để gỡ lỗi thủ tục hook khác. - WH_FOREGROUNDIDLE: Cài đặt một thủ tục hook sẽ được gọi khi luồng của ứng dụng là trở thành nhàn rỗi. Hook này rất hữu dụng cho thực hiện nhiệm vụ ưu tiên thấp trong thời gian nhàn rỗi. - WH_GETMESSAGE: Cài đặt một thủ tục hook theo dõi các message được đưa lên một hàng đợi message. - WH_JOURNALPLAYBACK: Cài đặt một thủ tục hook gởi message trước đây được ghi lại bằng một thủ tục hook WH_JOURNALRECORD. - WH_JOURNALRECORD: Cài đặt một thủ tục hook ghi lại các message đầu vào được đưa lên hàng đợi thông điệp hệ thống. Hook này rất hữu ích cho các macro ghi. - WH_KEYBOARD: Cài đặt một thủ tục móc theo dõi tin nhắn tổ hợp phím. - WH_KEYBOARD_LL: Cài đặt một thủ tục móc theo dõi các sự kiện bàn phím đầu vào ở mức độ thấp. - WH_MOUSE: Cài đặt một thủ tục móc theo dõi tin nhắn chuột. - WH_MOUSE_LL: Cài đặt một thủ tục móc theo dõi các sự kiện chuột đầu vào ở mức độ thấp. - WH_MSGFILTER: Cài đặt một thủ tục móc theo dõi tin nhắn được tạo ra như là kết quả của một sự kiện đầu vào trong hộp thoại, hộp thông báo, menu, hoặc di chuyển một thanh. KeyLogger-Sử dụng Hook Windows 31 Nguyễn Quang Nhật – Nguyễn Quốc Mỹ - WH_SHELL: Cài đặt một thủ tục hook tiếp nhận thông báo hữu ích cho các ứng dụng shell. - WH_SYSMSGFILTER: Cài đặt một thủ tục móc theo dõi tin nhắn được tạo ra như là kết quả của một sự kiện đầu vào trong hộp thoại, hộp thông báo, menu, hoặc di chuyển một thanh. III.3. Cách sử dụng III.3.1. Cài đặt Hook Ta có thể cài đặt thủ tục hook vào chuỗi hook bằng việc gọi hàm SetWindowsHookEx và chỉ ra kiểu hook đang gọi thủ tục, việc cài đặt hook có thể thực hiện trên mọi tiến trình trong hệ thống. Nếu sử dụng hook toàn cục thì phải đặt trong thư viện liên kết động (DLL). Ứng dụng muốn sử dụng thư viện liên kết động phải lấy được handle của thư viện đó. Để nhận Handle của thư viện liên kết động ta có thể sử dụng hàm LoadLibrary với tham số là tên của thư viện. Sau khi có được Handle của DLL, ta sẽ lấy địa chỉ của thủ tục hook trong thư viện liên kết động thông qua hàm GetProcAddress. Sau khi đã có thủ tục hook, sử dụng hàm SetWindowsHookEx để cài đặt thủ tục hook vào trong chuỗi hook. Ví dụ về sử dụng thư viện liên kết động : HOOKPROC lpfSetAutoProtect; static HINSTANCE hinstDLL; static HHOOK hhookysMsg; hinstDLL = LoadLibrary(( LPCTSTR ) "c:\\Windows\\ BrowserHook.dll"); lpfSetAutoProtect= (HOOKPROC)GetProcAddress(hinstDLL, "SetAutoProtect"); hhookysMsg= SetWindowsHookEx(WH_SYSMSGFILTER, lpfSetAutoProtect,hinstDLL,0); III.3.2. Giải phóng Hook Như đã nói thì hook nên được bỏ đi nếu như không cần thiết nữa bằng cách sử dụng hàm UnhookWindowsHookEx. Với thread-specific hook, việc sử dụng hàm UnhookWindowsHookEx sẽ giải phóng thủ tục hook. Tuy nhiên với hook toàn tục (system-wide hook) thì hàm này không thể trả tự do cho hàm DLL. Việc gọi hàm LoadLibrary sẽ gọi trong ngữ cảnh của tất cả các tiến trình, tuy nhiên hàm FreeLibrary thì không thể thực hiện với các 32 Bộ môn Mạng và Truyền Thông Nguyễn Quang Nhật – Nguyễn Quốc Mỹ tiến trình khác. Vì vậy, không có cách nào để giải phóng DLL. Hệ thống chỉ có thể giải phóng DLL khi tất cả các tiến trình liên kết tới DLL đó phải kết thúc hoặc gọi FreeLibrary. Giải pháp đặt ra cho vấn đề này là xây dựng hàm cài đặt ngay trong thư viện DLL. Bằng việc liên kết tới DLL, ứng dụng có thể cài đặt hook. Và ngay trong DLL cũng phải có hàm giải phóng hook để giải phóng khi không cần đến nữa. IV. WIN 32 API IV.1. Giới thiệu Windows API, gọi tắ là WINAPI, được gọi là giao diện lập trình ứng dụng (API) có sẵn trong các hệ thống điều hành Microsoft Windows của Microsoft. Nó cũng được gọi là Win32 API, tuy nhiên, tên "Windows API" phản ánh chính xác hơn nguồn gốc của nó trong Windows 16-bit và hỗ trợ trên Windows 64-bit. Hầu như tất cả các chương trình Windows tương tác với các API của Windows trên các dòng Windows NT của hệ điều hành. Công cụ hỗ trợ phát triển có sẵn trong các phiên bản của Microsoft Windows SDK, cung cấp tài liệu và các công cụ cần thiết để xây dựng phần mềm dựa trên các giao diện API Windows và các Windows. Windows API chủ yếu quan tâm đến sự tương tác giữa các hệ thống điều hành và ứng dụng. Đối với truyền thông giữa các ứng dụng Windows khác nhau với nhau, Microsoft

Các file đính kèm theo tài liệu này:

  • pdfkeylog_3468.pdf