Bảo mật VBA thông qua DLL VB6 chạy trên office 32bit và office 64bit

tuhocvba

Administrator
Thành viên BQT
Do DLL VB6 chỉ có thể chạy được trên Office 32bit.
Tuy nhiên nếu la Exe VB6 thì có thể chạy được trên Office 64bit cũng như 32bit.
Do đó, ý tưởng của tôi là, cho chương trình Excel gọi Exe VB6, còn bản thân Exe VB6 thì gọi DLL VB6 ra làm việc. Bằng cách này, mọi người có thể bảo mật code thông qua DLL VB6 mà vẫn chạy được trên office 64bit.
Bạn cần đăng nhập để thấy đính kèm

(Còn nữa)
 

tuhocvba

Administrator
Thành viên BQT
1. Tạo file DLL trong VB6.
Mở VB6 chọn ActiveX DLL.
Bạn cần đăng nhập để thấy đính kèm


Trên đó tôi viết code như sau:
Mã:
Public Function tinhtong(ByVal i As Integer, ByVal j As Integer) As Integer
    tinhtong = i + j
End Function
Tiếp theo tôi đổi tên project như sau:
Click chuột phải vào Project và chọn Properties.

Bạn cần đăng nhập để thấy đính kèm


Bạn cần đăng nhập để thấy đính kèm

Tôi nhập tên là MyDLL_1 và ấn OK.
Tiêp theo tôi viết code trên class như sau:
Mã:
Public Function tinhtong(ByVal i As Integer, ByVal j As Integer) As Integer
    tinhtong = i + j
End Function
Giả thiết đây chính là logic ta muốn giấu không cho người khác biết.
Do đó tới đây tôi sẽ build ra DLL.
Bạn cần đăng nhập để thấy đính kèm

Vào File và Make DLL như hình trên.
Giờ thì bạn có thể save project và đóng VB6 đi.
Xin lưu ý là khi build DLL ra sẽ có cảnh báo gì đó, không phải lỗi đâu, kệ nó.

2. Tạo file Exe VB6.
Mở VB6 và làm như hướng dẫn trong .
Bạn cần đăng nhập để thấy đính kèm

Bạn chọn ActiveX EXE và ấn OK.

Tôi sẽ thực hiện add thư viện DLL vừa tạo ở bước trên vào file exe này.
Bạn cần đăng nhập để thấy đính kèm

Vào Project và vô Refenreces.
Chọn tới file DLL mà ta vừa tạo ban nãy.
Bạn cần đăng nhập để thấy đính kèm

Bây giờ tôi viết code như sau :
Mã:
Public Function Newinstance(ProgID As String) As Object
  Set CreateInstance = CreateObject(ProgID)
End Function
Public Function tinhtong2(ByVal a As Integer, ByVal b As Integer) As Integer
    Dim c As New MyDLL_1.Class1
    tinhtong2 = c.tinhtong(a, b)
End Function
Tôi đổi tên class là TestTHVBAX.
Bạn cần đăng nhập để thấy đính kèm

Thực hiện build ra exe. Tôi build ra file là Project1.exe
Tiến hành đăng ký file exe như hướng dẫn ở .
Tiến hành đăng ký file DLL như sau:
Mở CMD chạy với quyền admin.
Gõ lệnh:
Mã:
cd C:\Users\user\Desktop\DLL
trong đó đường dẫn C:\Users\user\Desktop\DLL là nơi tôi đang lưu file DLL ở đó.
Mục đích của lệnh trên là di chuyển con trỏ về đó.
Tiếp theo chạy lệnh sau:
Mã:
regsvr32.exe MyDLL_1.dll
Rồi , bây giờ thì mở exel lên và add file exe vô thư viện.
Bạn cần đăng nhập để thấy đính kèm


Trên Excel tôi viết code như sau:
Mã:
Sub abb()
    Dim a As New Project1.TestTHVBAX
  
    x = a.tinhtong2(3, 5)
    MsgBox x
End Sub
Code chạy và không có lỗi lầm gì.
Bạn cần đăng nhập để thấy đính kèm

Xin lưu ý, cách bảo mật này thì người ta vẫn có thể coi được code của exe. Nhưng code ở exe không hề có logic gì cả, mà logic nằm ở file DLL.
Theo tôi biết thì code DLL được bảo mật, không có khả năng coi được code. Do đó phương án bảo mật này được coi là cách tốt.
Bài viết đã được thực nghiệm trên win 10 64 bit, office 2016 64bit.
Nếu muốn hủy đăng ký DLL thì bạn gõ lệnh sau:
Mã:
regsvr32.exe /u MyDLL_1.dll
Nguồn tham khảo :
Mã:
https://qiita.com/tukiyo3/items/0d53cffb2fa44806eb5d
 

tuhocvba

Administrator
Thành viên BQT
Để quá trình add exe vô thư viện Excel được diễn ra tự động, các bạn có thể gán thủ tục sau vào sự kiện Open Workbook:
Mã:
Sub Addexe2Lib()
    On Error Resume Next
    Call AddExtensibility
    Call AddReference
End Sub
'======================================================'
Sub AddExtensibility()
    On Error Resume Next
    ThisWorkbook.VBProject.References.AddFromGuid "{0002E157-0000-0000-C000-000000000046}", 2, 0 'Dang ki Extensibility 5.0
End Sub
Sub AddReference()
    Dim VBAEditor As VBIDE.VBE
    Dim vbProj As VBIDE.VBProject
    Dim chkRef As VBIDE.Reference

    Set VBAEditor = Application.VBE
    Set vbProj = ActiveWorkbook.VBProject

    For Each chkRef In vbProj.References
        If chkRef.Name = "Project1" Then Exit Sub
    Next
    vbProj.References.AddFromFile ThisWorkbook.Path & "\Project1.exe"
End Sub
 

tuhocvba

Administrator
Thành viên BQT
Ở bài viết trên, tôi đã giải quyết khâu tự tích chọn Library trên Excel cho mọi người rồi.
Bây giờ, ta sẽ giải quyết tiếp vấn đề trên VB6.

Nhắc lại thao tác trước đây:

Với thao tác ở trên VB6 khi tạo file exe chúng ta đã vào Project và vô Refenreces, tích chọn MyDLL_1.
Bạn cần đăng nhập để thấy hình ảnh


Như vậy sau này khi chia sẻ file ra bên ngoài, buộc lòng đường dẫn ở trên máy tính chúng ta như thế nào thì trên máy tính người khác cũng tương tự như vậy.
Chẳng hạn chúng ta lưu DLL ở D:\VBA , thế thì sau này file này cũng phải lưu trên máy tính mọi người đường link tương tự như vậy. Nếu không, khả năng code không chạy là rất cao.

Kịch bản mong muốn:
File VBA Excel và dll và exe để chung trong thư mục Tool. Còn việc mọi người để thư mục Tool ở đâu thì chúng ta không quan tâm.
Bạn cần đăng nhập để thấy đính kèm

Do đó, code cho file exe tôi sẽ sửa lại như sau:
Mã:
Public Function Newinstance(ProgID As String) As Object
  Set CreateInstance = CreateObject(ProgID)
End Function
Public Function tinhtong2(ByVal a As Integer, ByVal b As Integer) As Integer
    Dim c As Object
    Set c = CreateObject("MyDLL_1.Class1")
    tinhtong2 = c.tinhtong(a, b)
End Function
Bằng cách code như trên, thao tác vô Project và Add thư viện MyDLL_1 là không cần thiết.
Như vậy chúng ta đã tự động hoàn toàn khâu add thư viện.

Việc phân phối Tool bây giờ chỉ còn là yêu cầu người dùng đăng ký file exe và DLL để máy tính nhận diện và chấp nhận cho sử dụng mà thôi. Tuy việc này chỉ phải thực hiện một lần duy nhất, nhưng nếu có thể suy nghĩ tự động hoàn toàn bước này, thì topic này coi như đã hoàn thành một cách hoàn mỹ.
 

tuhocvba

Administrator
Thành viên BQT
Từ bài viết trên của tôi, có lẽ các bạn cũng đã thắc mắc, liệu bước add thư viện thực hiện trên excel có phải là không cần thiết hay không?
Đúng vậy, chúng ta viết lại code trên excel như sau, bằng cách này ta cũng không cần phải add thư viện là file exe vô Excel nữa :
Mã:
Sub abb()
    Dim a As Object, x As Integer
    Set a = CreateObject("Project1.TestTHVBAX")
    x = a.tinhtong2(3, 5)
    MsgBox x
End Sub
 

tuhocvba

Administrator
Thành viên BQT
Các bạn download file dưới đây và thực hành theo video nhé.
Bạn cần đăng nhập để thấy đa phương tiện
 

tuhocvba

Administrator
Thành viên BQT
Như vậy mọi người đã thấy DLL đã hoat động ở trên office 64bit.
Tuy nhiên việc đăng ký DLL mà phải vô DOS gõ từng dòng lệnh như thế, thì quá khổ sở.
Do đó, tôi sẽ tạo một file dangkyDLL.bat có nội dung như sau:
dangkyDLL.bat:
cd /d %~dp0
regsvr32  MyDLL_1.dll
File này được để chung thư mục chứa file DLL.
Bây giờ chỉ cần click chuột phải vào file .bat này và chạy với quyền admin là việc đăng ký sẽ diễn ra tự động, người dùng không cần phải vô DOS để gõ lệnh nữa.
Tham khảo:
Mã:
https://maku77.github.io/windows/file/batch-dir.html
 

tuhocvba

Administrator
Thành viên BQT
Tôi tóm tắt lại các bước các bạn cần làm :
1. Các bạn cần tạo ra file dll và exe.
Chú ý, khi mở VB6 nên mở quyền admin. Nếu không sẽ có cảnh báo mỗi lần các bạn tạo ra dll hay exe (dù chẳng ảnh hưởng gì).
2. Các bạn cần đăng ký file exe ( )
3. Các bạn cần đăng ký file dll ( )
Hoàn thành 3 bước trên là file Excel của chúng ta có thể gọi exe => gọi dll ra làm việc.
Trong đó logic chính nằm ở DLL giúp cho việc bảo mật code được coi là tốt nhất tính tới thời điểm hiện tại.
Bạn cần đăng nhập để thấy đính kèm


Như ở topic này đã giới thiệu cách tạo . File DLL này có ưu điểm là không cần đăng ký, chỉ cần nằm chung thư mục với file Exe là Exe có thể gọi tới nó. Nếu như phát hành Tool theo hướng này, thao tác người dùng sẽ bớt đi được 1 thao tác , họ không phải đăng ký DLL nữa. Mà chỉ cần đăng ký file Exe là sau đó có thể dùng file Excel Macro bình thường.
Ở bài viết này tôi sẽ giới thiệu ngắn gọn như sau:
Tôi tao file DLL như . Trong file DLL này có hàm tinhtong. Tôi sẽ sử dụng hàm này như sau:
-Tôi tạo ActiveX Exe :
Mã:
Private Declare Function tinhtong Lib "MyDLLX.dll" (ByVal a As Integer, ByVal b As Integer) As Integer
Public Function Newinstance(ProgID As String) As Object
  Set CreateInstance = CreateObject(ProgID)
End Function
Public Function tinhtong2(ByVal a As Integer, ByVal b As Integer) As Integer
    tinhtong2 = tinhtong(a, b)
End Function
Tên Class là : TestTHVBAXX
Tên Project là: Project1X
Bạn cần đăng nhập để thấy đính kèm

Thực hiện build ra exe cất cùng thư mục với file MyDLLX.dll
-Tiến hành đăng ký file Exe.
-Viết code trên Excel như sau:
Mã:
Sub vidu()
    Dim x
    Dim c As Integer
    Set x = CreateObject("Project1X.TestTHVBAXX")
    c = x.tinhtong2(5, 10)
    MsgBox c
End Sub
Kết quả code chạy bình thường.
Lưu ý cách tạo standard DLL nói trên có ưu điểm là không phải đăng ký DLL, nhưng hiện tại mới test thử chạy tốt cho Function, chưa tốt cho Sub.
 

NhanSu

SMod
Thành viên BQT
Mình đã tạo 1 file exe bằng C++ để tự đăng ký file exe và dll luôn.
Mã:
#include <windows.h>

int main()
{
    HINSTANCE hInstance = LoadLibraryA("MyDll_1.dll");
    FARPROC lpDllEntryPoint = GetProcAddress(hInstance, "DllRegisterServer");
    (*lpDllEntryPoint)();
    int result = system("Project1.exe /regserver");
}
Chương trình dùng đăng ký prject1.exe và mydll_1.dll. Biên dịch với lựa chọn Release - x86. Vào folder Release, copy file exe vào folder chứa prject1.exe và mydll_1.dll. Bấm chuột phải vào file này, chọn Properties - Compatibility - Run as administrator. File sẽ xuất hiện biểu tượng cái khiên, kích đúp chuột để chạy là được.
Có thể tạo file nén tự bung bằng winrar và thiết lập để file dk.exe tự chạy ngay sau khi giải nén để đăng ký luôn.
Bạn cần đăng nhập để thấy đính kèm
 
Sửa lần cuối:
B

bvtvba

Guest
Bấm chuột phải vào file này, chọn Properties - Compatibility - Run as administrator
Khi chia sẻ ra ngoài thì người dùng có cần phải làm thao tác này nữa không bác?
Ngoài ra code ở trên dường như khóa cứng tên file DLL và Exe.
Em nghĩ nếu như xây dựng kịch bản file của bác và file DLL, exe cùng thư mục, thì nếu file của bác tự tìm kiếm trong thư mục của nó xem có file exe khác và dll khác ko, thì tự tiến hành đăng ký, như vậy sẽ tăng độ tùy biến hơn, bác nghĩ sao?
 

NhanSu

SMod
Thành viên BQT
Mình có thể sử dụng tham số dòng lệnh hoặc quét tất cả các file nhưng cách 2 sẽ xảy ra trường hợp đăng ký cả những file khác. Cách dùng tham số dòng lệnh rồi đưa vào file bat tốt hơn.
 
B

bvtvba

Guest
Em nghĩ khi phát hành Tool, trong đó có thư mục LibTHVBA, trong đó chứa file đăng ký của bác và các file DLL và EXE. Mặc định các file trong thư mục cùng với nó sẽ được đăng ký. Cái này quy định cho người phát hành tool. Còn các file DLL khác không cần đăng ký thì để bên ngoài cùng file tool Excel.
 

tuhocvba

Administrator
Thành viên BQT
Ý tưởng của bvtvba cũng hay đó. Câu hỏi này mình cũng quan tâm.
Khi chia sẻ ra ngoài thì người dùng có cần phải làm thao tác này nữa không bác?
 

NhanSu

SMod
Thành viên BQT
Có thể bấm chuột phải vào file exe, chọn Run as administrator. Chắc không có cách nào chỉ cần kích chuột là tự chạy với quyền admin.
 
Sửa lần cuối:

NhanSu

SMod
Thành viên BQT
Đúng rồi, bài 10 mình làm để test nhiều lần, không để ý là chỉ cần bấm chuột phải, chọn run as là xong.
 

shenlong

Yêu THVBA
Sau khi triển khai trên rất nhiều máy thì cái ActiveXExe sẽ được nhận dạng là virus, mặc dù chỉ có 1 dòng lệnh msgbox đơn giản.
 
Top