Bạn sẽ có một xử lý rò rỉ trong trường hợp:
Program -Load> Dll A
-Load> Dll B
-Unload> Dll A
Không có mã đang ngầm thực hiện bởi một mô-đun được bốc dỡ dỡ bỏ các module mà nó nạp.
Vì không có mã nào được thực hiện để giảm số lượng tham chiếu, mô-đun B sẽ không bao giờ được tải xuống.
Dưới đây là các quy tắc cho tải/dlls dỡ:
- Mỗi cuộc gọi đến LoadLibrary và LoadLibraryEx sẽ làm tăng số lần tham khảo cho mô-đun đó. Đây là trong bối cảnh của quá trình gọi điện thoại chỉ, không qua ranh giới quá trình.
- Mỗi cuộc gọi tới FreeLibrary hoặc FreeLibraryAndExitThread sẽ giảm số lượng tham chiếu.
- Khi số tham chiếu đạt đến 0, số này sẽ không được tải.
- Khi Windows thấy rằng chương trình của bạn là đóng, bất kỳ mô-đun chưa tải nào bị rò rỉ sẽ được tải xuống.
- Tùy thuộc vào việc bạn đang làm, DllCanUnloadNow có thể hữu ích cho bạn.
Vẫn trong bộ nhớ vs vẫn nạp:
Không có đảm bảo rằng mô-đun của bạn sẽ được phát hành từ bộ nhớ tại một thời điểm nhất định khi tham chiếu đến 0. Nhưng bạn nên xem xét các mô-đun như thể nó được bốc dỡ khi đếm tham khảo đạt 0.
Dừng các DLL khỏi bị bốc dỡ:
Để buộc các DLL khỏi bị bốc dỡ bạn có thể thử
- Hệ thống gọi DllMain với cờ DLL_PROCESS_DETACH. Bạn có thể cố gắng không quay trở lại từ điều này thông qua một số loại hoạt động chặn.
- Bạn có thể thử gọi LoadLibrary từ bên trong DLL mà bạn không muốn tải xuống. (Tự tải)
Edit:
Bạn nói mục tiêu của bạn là để injet mã vào chương trình đang chạy và bạn muốn rò rỉ tay cầm vào mục đích.
Điều đó là tốt, nhưng nếu bạn chạy thao tác này rất nhiều, nó có thể dẫn đến sự cố trong Chương trình nguồn của bạn vì quá nhiều tay cầm sẽ được sử dụng hoặc cuối cùng quá nhiều bộ nhớ sẽ được sử dụng.
Bạn có thể trả về FALSE từ DllMain để ngăn không cho nó bị tải để bạn không lãng phí bộ nhớ. Bạn làm điều này khi fdwReason là DLL_PROCESS_ATTACH. Bạn có thể read more about it here.
Nếu bạn đang cố gắng mô phỏng một DLL và thêm vào chức năng bổ sung của riêng bạn, bạn sẽ cần phải thực hiện tất cả các chức năng mà DLL nguồn thực hiện và ủy nhiệm mỗi cuộc gọi trở lại nguồn DLL.
Nguồn
2009-03-05 16:56:08
Và chà là bạn không phải gọi FreeLibrary() trong DLLMain trên một quá trình tách, vậy làm thế nào bạn sẽ thực sự đi về làm sạch lên DLL_B? –
Một phương pháp phổ biến là có các lệnh gọi init() và deinit() cho DLL_A tải/dỡ DLL_B (và thực hiện các hàm init/cleanup khác). Nó xâm nhập, nhưng nó đơn giản. –
Trong trường hợp này, tôi muốn * DLL_B bị bỏ lại phía sau cho đến khi ứng dụng chính đóng. Thật vậy, điều này là lý tưởng cho tôi. Ý định của tôi là tiêm DLL và một chuỗi nó sẽ tạo ra trong ứng dụng. – mj2008