Giáo trình Lập trình hệ thống - Chương 2: Ngắt và sự kiện

1. Khái niệm

Ngắt (interrupt) là quá trình dừng chương trình chính đang chạy để ưu tiên thực hiện

một chương trình khác, chương trình này được gọi là chương trình phục vụ ngắt (ISR –

Interrupt Service Routine). ISR hoàn toàn giống với một chương trình bình thường trên máy

tính, nghĩa là nó có khả năng truy xuất đến tất cả các lệnh ngôn ngữ máy của µP. Tuy nhiên

cuối ISR sẽ kết thúc bằng lệnh IRET (Interrupt Return) để µP tiếp tục thực hiện lệnh đã kết

thúc trước đây.

Các nguyên nhân dẫn đến ngắt là:

- Bản thân chương trình đang thực hiện bị lỗi, ví dụ như: chia cho 0,

- Do tác động của thiết bị ngoại vi, ví dụ như: thực hiện lệnh in nhưng máy in lỗi,

ghi dữ liệu vào đĩa nhưng không có đĩa,

- Do lập trình viên chủ động gọi các ngắt có sẵn.

Một cách đơn giản, chúng ta có thể xem ngắt như là quá trình gọi chương trình con

nhưng các chương trình con này được tạo ra sẵn trong máy tính và quá trình gọi này có thể

xảy ra tại thời điểm không xác định trước.

Sự kiện (Event) là một tác động lên một đối tượng trong môi trường Windows. Khi

có một sự kiện xảy ra, Windows sẽ gởi thông điệp (message) đến đối tượng. Các sự kiện

thường xảy ra là:

- Sự kiện chuột: Click, Double Click,

- Sự kiện bàn phím: nhấn phím, nhả phím,

- Sự kiện cửa sổ: Activate, Load, Unload,

pdf15 trang | Chuyên mục: Lập Trình Hệ Thống Và Mạng | Chia sẻ: yen2110 | Lượt xem: 400 | Lượt tải: 0download
Tóm tắt nội dung Giáo trình Lập trình hệ thống - Chương 2: Ngắt và sự kiện, để xem tài liệu hoàn chỉnh bạn click vào nút "TẢI VỀ" ở trên
 Windows 
Các ứng dụng trên nền Windows sử dụng các hàm SetWindowsHookEx, 
UnhookWindowsHookEx và CallNextHookEx để quản lý chuỗi hàm lọc trong một quá 
trình câu móc. Trước phiên bản 3.1, Windows thực hiện quản lý bằng các hàm 
SetWindowsHook, UnhookWindowsHook và DefHookProc. Mặc dù các hàm này cũng 
có khả năng thực hiện được trên nền Win32 nhưng sẽ có một số đặc trưng không sử dụng 
được như các phiên bản mới (Ex). 
4.1.1. Hàm SetWindowsHookEx 
Dùng để thêm một hàm lọc vào một quá trình câu móc. 
Khai báo: 
Public Declare Function SetWindowsHook Lib "user32" 
Alias "SetWindowsHookA" (ByVal nFilterType As Long, ByVal 
pfnFilterProc As Long) As Long 
Public Declare Function SetWindowsHookEx Lib "user32" 
Alias "SetWindowsHookExA" (ByVal idHook As Long, ByVal lpfn 
As Long, ByVal hmod As Long, ByVal dwThreadId As Long) As 
Long 
Hàm SetWindowsHookEx gồm có 4 tham số: 
- idHook: xác định loại hàm câu móc sẽ cài đặt. Thông số này gồm các giá trị sau: 
WH_KEYBOARD: cài đặt hàm câu móc quản lý thông điệp gởi đi khi nhấn phím 
(ngoại trừ tổ hợp Ctrl – Alt – Del). 
WH_MOUSE: cài đặt hàm câu móc quản lý thông điệp khi điều khiển chuột. 
WH_CALLWNDPROC: cài đặt hàm câu móc quản lý thông điệp trước khi hệ thống 
gởi đến cửa sổ, chỉ cho phép xử lý thông điệp mà không được thay đổi thông điệp. 
Tài liệu Lập trình hệ thống Chương 2 
Phạm Hùng Kim Khánh Trang 44 
WH_CALLWNDPROCRET: cài đặt hàm câu móc quản lý thông điệp sau khi cửa sổ 
đã xử lý. Loại này cho phép thay đổi giá trị trả về của thông điệp. 
WH_MSGFILTER: cài đặt hàm câu móc quản lý các thông điệp được tạo ra giống 
như có một sự kiện của dialog box, message box, menu hay scroll bar. 
WH_GETMESSAGE: cài đặt hàm câu móc quản lý các thông điệp được gởi tới hàng 
đợi. 
WH_CBT: cài đặt hàm câu móc để nhận thông báo từ ứng dụng CBT. 
WH_DEBUG: cài đặt hàm câu móc để gỡ rối một hàm câu móc khác. 
WH_FOREGROUNDIDLE: cài đặt hàm câu móc trong đó hàm này được gọi khi 
luồng (thread) foreground của ứng dụng rảnh (idle). Quá trình này thường sử dụng để thực 
thi các tác vụ có độ ưu tiên thấp khi luồng ưu tiên rảnh. 
WH_JOURNALPLAYBACK: cài đặt hàm câu móc để gởi các thông điệp đã được 
lưu bằng hàm câu móc WH_JOURNALRECORD. 
WH_JOURNALRECORD: cài đặt hàm câu móc lưu lại các thông điệp đã gởi đến 
hàng đợi. 
WH_KEYBOARD_LL: cài đặt hàm câu móc quản lý sự kiện bàn phím ở mức thấp 
(dùng cho Windows NT/2000/XP). 
WH_MOUSE_LL: cài đặt hàm câu móc quản lý sự kiện chuột ở mức thấp (dùng cho 
Windows NT/2000/XP). 
WH_SHELL: cài đặt hàm câu móc cho một ứng dụng shell. 
WH_SYSMSGFILTER: cài đặt hàm câu móc quản lý các thông điệp được tạo ra 
giống như có một sự kiện của dialog box, message box, menu hay scroll bar. Hàm này quản 
lý cho tất cả ứng dụng trong cùng một desktop. 
- lpfn: 
Con trỏ chỉ đến địa chỉ của hàm lọc. Nếu tham số dwThreadId = 0 hay chỉ đến một 
luồng được tạo bởi một tiến trình (process) khác, tham số lpfn phải chỉ đến một hàm câu 
móc trong một thư viện liên kết động (DLL). Ngược lại, lpfn chỉ đến hàm câu móc chứa 
trong bản thân tiến trình hiện hành. 
- hMod: 
handle chỉ đến DLL chứa hàm xử lý xác định bằng tham số lpfn. Tham số hMod phải 
đặt là NULL nếu hàm câu móc nằm trong tiến trình hiện hành 
- dwThreadId: 
Xác định ID của luồng thực hiện quá trình câu móc. Nếu dwThreadId = 0, hàm câu 
móc sẽ tác động đến tất cả các luồng. Ứng dụng có thể dùng hàm GetCurrentThreadId để 
xác định ID của luồng hiện hành. 
Tài liệu Lập trình hệ thống Chương 2 
Phạm Hùng Kim Khánh Trang 45 
Phạm vi thực hiện của hàm câu móc mô tả như sau: 
Hook Phạm vi 
WH_CALLWNDPROC Luồng hay hệ thống 
WH_CBT Luồng hay hệ thống 
WH_DEBUG Luồng hay hệ thống 
WH_GETMESSAGE Luồng hay hệ thống 
WH_JOURNALRECORD Hệ thống 
WH_JOURNALPLAYBACK Hệ thống 
WH_FOREGROUNDIDLE Luồng hay hệ thống 
WH_SHELL Luồng hay hệ thống 
WH_KEYBOARD Luồng hay hệ thống 
WH_MOUSE Luồng hay hệ thống 
WH_MSGFILTER Luồng hay hệ thống 
WH_SYSMSGFILTER Hệ thống 
Hàm SetWindowsHookEx trả về handle của quá trình câu móc đã cài đặt và trả về 
NULL nếu quá trình cài đặt không thành công. Handle này được dùng để xóa quá trình câu 
móc khi sử dụng hàm UnhookWindowsHookEx. Các thông báo lỗi khi quá trình câu móc 
không thành công là: 
- ERROR_INVALID_HOOK_FILTER: mã câu móc sai 
- ERROR_INVALID_FILTER_PROC: hàm lọc sai 
- ERROR_HOOK_NEEDS_HMOD: một quá trình câu móc toàn cục sử dụng tham 
số hMod = NULL hay chỉ đến một luồng không tồn tại. 
- ERROR_GLOBAL_ONLY_HOOK: một quá trình câu móc chỉ dùng được cho 
hệ thống nhưng được cài đặt cho một luồng xác định. 
- ERROR_INVALID_PARAMETER: ID của luồng sai. 
- ERROR_JOURNAL_HOOK_SET: Cài đặt thêm một quá trình câu móc dạng 
nhật ký (WH_JOURNALRECORD và WH_JOURNALPLAYBACK) trong khi 
một quá trình dạng này đang tồn tại (tại một thời điểm chỉ cho phép một quá trình 
dạng nhật ký). 
- ERROR_MOD_NOT_FOUND: Tham số hMod chỉ đến một hàm không xác định 
được. 
- Khác: không cho phép do bảo mật của hệ thống hay bộ nhớ tràn. 
Tài liệu Lập trình hệ thống Chương 2 
Phạm Hùng Kim Khánh Trang 46 
4.1.2. Hàm UnhookWindowsHookEx: 
Dùng để xoá một hàm lọc ra khỏi chuỗi xử lý một quá trình câu móc. Hàm này lấy 
handle của quá trình câu móc trả về từ lệnh gọi hàm SetWindowsHookEx và luôn trả về giá 
trị TRUE. 
Khai báo: 
Public Declare Function UnhookWindowsHook Lib "user32" 
Alias "UnhookWindowsHook" (ByVal nCode As Long, ByVal 
pfnFilterProc As Long) As Long 
Public Declare Function UnhookWindowsHookEx Lib 
"user32" Alias "UnhookWindowsHookEx" (ByVal hHook As Long) 
As Long 
4.1.3. Hàm CallNextHookEx: 
Dùng để chuyển thông tin câu móc đến hàm câu móc kế tiếp trong chuỗi xử lý. 
Declare Function CallNextHookEx Lib "user32" (ByVal hHook 
As Long, ByVal ncode As Long, ByVal wParam As Long, lParam As 
Any) As Long 
- hHook: handle của quá trình câu móc, là giá trị trả về từ lệnh gọi hàm 
SetWindowsHookEx. Thông thường Windows bỏ qua giá trị này. 
- nCode: mã của quá trình câu móc, hàm câu móc dùng mã này để xác định 
phương pháp xử lý thông tin. 
- wParam: xác định tham số được xử lý bởi hàm câu móc. 
- lParam: giống như wParam. 
Khi một quá trình câu móc khởi động, Windows gọi hàm đầu tiên trong chuỗi hàm 
lọc và kết thúc quản lý quá trình, các hàm lọc phía sau sẽ không xử lý. Để thực hiện các 
hàm ở phía sau trong chuỗi hàm, Windows cung cấp hàm CallNextHookEx cho phép gọi 
một hàm kế tiếp trong chuỗi hàm lọc. Như vậy, nếu một hàm lọc nào đó không thực hiện 
hàm CallNextHookEx thì các hàm lọc ở phía sau sẽ không thực hiện. 
Một ví dụ sử dụng các hàm xử lý câu móc như sau: 
'Ch•a trong m•t file module 
Public Const WH_KEYBOARD = 2 
Public Const VK_SHIFT = &H10 
Public Const VK_CONTROL = &H11 
Public Const VK_MENU = &H12 
Declare Function CallNextHookEx Lib "user32" (ByVal hHook 
As Long, ByVal ncode As Long, ByVal wParam As Long, lParam As 
Any) As Long 
Declare Function GetKeyState Lib "user32" (ByVal nVirtKey 
As Long) As Integer ‘Xác ••nh tr•ng thái c•a m•t phím (Bit15) 
Tài liệu Lập trình hệ thống Chương 2 
Phạm Hùng Kim Khánh Trang 47 
Declare Function SetWindowsHookEx Lib "user32" Alias 
"SetWindowsHookExA" (ByVal idHook As Long, ByVal lpfn As 
Long, ByVal hmod As Long, ByVal dwThreadId As Long) As Long 
Declare Function UnhookWindowsHookEx Lib "user32" (ByVal 
hHook As Long) As Long 
Public hHook As Long 
Public Function KeyboardProc(ByVal idHook As Long, ByVal 
wParam As Long, ByVal lParam As Long) As Long 
If idHook < 0 Then 
'G•i hàm x• lý k• ti•p 
KeyboardProc = CallNextHookEx(hHook, idHook, wParam, 
ByVal lParam) 
Else 
'N•u nh•n Shift-C 
If (GetKeyState(VK_SHIFT) And &H8000) And wParam = 
Asc("C") Then 
'thì hi•n th• k•t qu• 
Form1.Print "Shift-C pressed ..." 
End If 
If (GetKeyState(VK_CONTROL) And &H8000) And wParam = 
Asc("C") Then 
Form1.Print "Ctrl-C pressed ..." 
End If 
If (GetKeyState(VK_MENU) And &H8000) And wParam = 
Asc("C") Then 
Form1.Print "Alt-C pressed ..." 
End If 
'G•i hàm x• lý k• ti•p 
KeyboardProc = CallNextHookEx(hHook, idHook, wParam, 
ByVal lParam) 
End If 
End Function 
----------------------------------------------- 
'Ch•a trong form 
Private Sub Form_Load() 
'••t quá trình câu móc 
hHook = SetWindowsHookEx(WH_KEYBOARD, AddressOf 
KeyboardProc, App.hInstance, App.ThreadID) 
End Sub 
Private Sub Form_Unload(Cancel As Integer) 
Tài liệu Lập trình hệ thống Chương 2 
Phạm Hùng Kim Khánh Trang 48 
'Xoá quá trình câu móc 
UnhookWindowsHookEx hHook 
End Sub 
4.2. Hàm lọc 
Hàm lọc thường có dạng như sau: 
Function FilterFunc (ByVal nCode As Integer, ByVal wParam 
As Long, ByVal lParam As Long) 
Hàm lọc nhận 3 tham số: 
- nCode: mã của quá trình câu móc, là một số nguyên xác định hàm lọc, ví dụ như 
loại sự kiện làm khởi động quá trình câu móc. Mã này được xác định khi hàm lọc 
xử lý sự kiện hay gọi hàm DefHookProc. Nếu mã câu móc < 0 thì hàm lọc sẽ 
không xử lý sự kiện mà sẽ gọi hàm DefHookProc để truyền 3 tham số còn lại cho 
hàm lọc kế tiếp trong chuỗi hàm lọc bằng hàm CallNextHookEx. 
- Tham số thứ hai wParam và thứ ba lParam chứa các thông tin cần thiết cho hàm 
lọc. Mỗi quá trình câu móc dùng các giá trị wParam và lParam khác nhau. Ví dụ 
như, quá trình câu móc bàn phím WH_KEYBOARD chứa mã phím nhấn trong 
wParam và trạng thái bàn phím trong lParam. Hay quá trình câu móc 
WH_MSGFILTER chứa giá trị NULL trong wParam và một con trỏ chỉ đến 
thông điệp chứa trong lParam. 
Hàm lọc dùng trong DLL: 
Đối với các quá trình câu móc cục bộ, hàm lọc có thể đặt ngay trong mã lệnh của ứng 
dụng nhưng đối với các quá trình câu móc hệ thống, hàm lọc phải được đặt trong một DLL. 
Chỉ có quá trình câu móc dạng nhật ký (WH_JOURNALRECORD và 
WH_JOURNALPLAYBACK) là ngoại lệ. Hàm lọc của quá trình câu móc hệ thống phải 
chia sẻ dữ liệu cho tiến trình thực hiện quá trình câu móc. Các biến toàn cục sử dụng trong 
DLL phải được xác định rõ hay phải đặt trong vùng dữ liệu chia sẻ. 

File đính kèm:

  • pdfgiao_trinh_lap_trinh_he_thong_chuong_2_ngat_va_su_kien.pdf
Tài liệu liên quan