In a recent assignment at my office last week, I came across a situation where I had to make some changes in the VBA code of an excel document. The excel document was something getting used from long time and there was no one having details related to password through which VBA code in that document was protected. Also there was no related supporting document available. I was in a situation where I required getting the access of VBA code without password.
After a lot of search on web and spending quite some time, I was able to access the VBA code without knowing the password. Although there are a lot of information already available on web related to the topic, however most of the information are either in bits and pieces or not very simple to understand for a non techie person.
Hence I decided to write this blog to present the information in simplest manner possible. Give it a try if you are in similar situation and I am sure this is going to work for you as well. Please follow all steps precisely as mentioned.
Before we jump into steps to access the password protected VBA, it make sense to understand how it works. When we try to access password protected VBA document, the VBE (Visual Basic Editor) will call in build system function to create the password dialogue box. This dialogue box is where the user will enter password to access the document and will click on OK. If the user enters correct password and press OK, the system function will return 1. If the user enters incorrect password or click cancel, the system function will return 0. After the dialogue box is closed, the Visual Basic Editor (VBE) will check the value entered. If the value is 1, VBE will think that the password is right and will open the document. On the other hand, if the value is 0, VBE will think that password is incorrect and will not allow access to the document. The trick that we are going to use is basically to swap the value of 0 to 1 by using a code that can be written easily or can be taken from this post and included in your excel document. Hope this basic helps in making the concept a little easier. Lets jump into the steps now.
For the ease of understanding, I have created a sample VBA document called “Password_Test”. As you can see below, when I try to open this VBAProject, it prompts for a password to be entered.
Okay, so now we will go to the steps directly.
Step 1: First step first. make sure you take a backup of your original file and keep it at a different location in your PC or Laptop so that if accidentally we corrupt the file then we have a backup readily available.
Step 2: Create a new file with .xlsm extension.
An XLSM file is a macro-enabled spreadsheet created by Microsoft Excel, a widely used spreadsheet program that comes with every edition of the Microsoft Office suite.
For ease of understanding, I have named this file as “macro.xlsm”. To create this file, open MS Excel application and then go to File->SaveAs->location and then name your file as macro.xlsm. You can also choose file type from drop down.
Step 3: Open you locked VBA project file. In our case, its “Password_Test”.
Step 4: Open the new blank file that we just created. In our case its “macro.xlsm”
Step 5: We need to insert certain code in our new created “macro.xlsm” file. Once the file is open, click “ctrl+F11” to open the Visual Basic Editor. Once your VBE is open, you will see a screen like this.
Step 6: Select VBAProject (macro.xlsm) then go to Insert and click on Module. A blank page will open on right panel of the VB Editor.
Step 7: On the blank page that open on right of VBE, copy and paste below mentioned code:
Option Explicit Private Const PAGE_EXECUTE_READWRITE = &H40 Private Declare PtrSafe Sub MoveMemory Lib "kernel32" Alias "RtlMoveMemory" _ (Destination As LongPtr, Source As LongPtr, ByVal Length As LongPtr) Private Declare PtrSafe Function VirtualProtect Lib "kernel32" (lpAddress As LongPtr, _ ByVal dwSize As LongPtr, ByVal flNewProtect As LongPtr, lpflOldProtect As LongPtr) As LongPtr Private Declare PtrSafe Function GetModuleHandleA Lib "kernel32" (ByVal lpModuleName As String) As LongPtr Private Declare PtrSafe Function GetProcAddress Lib "kernel32" (ByVal hModule As LongPtr, _ ByVal lpProcName As String) As LongPtr Private Declare PtrSafe Function DialogBoxParam Lib "user32" Alias "DialogBoxParamA" (ByVal hInstance As LongPtr, _ ByVal pTemplateName As LongPtr, ByVal hWndParent As LongPtr, _ ByVal lpDialogFunc As LongPtr, ByVal dwInitParam As LongPtr) As Integer Dim HookBytes(0 To 5) As Byte Dim OriginBytes(0 To 5) As Byte Dim pFunc As LongPtr Dim Flag As Boolean Private Function GetPtr(ByVal Value As LongPtr) As LongPtr GetPtr = Value End Function Public Sub RecoverBytes() If Flag Then MoveMemory ByVal pFunc, ByVal VarPtr(OriginBytes(0)), 6 End Sub Public Function Hook() As Boolean Dim TmpBytes(0 To 5) As Byte Dim p As LongPtr Dim OriginProtect As LongPtr Hook = False pFunc = GetProcAddress(GetModuleHandleA("user32.dll"), "DialogBoxParamA") If VirtualProtect(ByVal pFunc, 6, PAGE_EXECUTE_READWRITE, OriginProtect) <> 0 Then MoveMemory ByVal VarPtr(TmpBytes(0)), ByVal pFunc, 6 If TmpBytes(0) <> &H68 Then MoveMemory ByVal VarPtr(OriginBytes(0)), ByVal pFunc, 6 p = GetPtr(AddressOf MyDialogBoxParam) HookBytes(0) = &H68 MoveMemory ByVal VarPtr(HookBytes(1)), ByVal VarPtr(p), 4 HookBytes(5) = &HC3 MoveMemory ByVal pFunc, ByVal VarPtr(HookBytes(0)), 6 Flag = True Hook = True End If End If End Function Private Function MyDialogBoxParam(ByVal hInstance As LongPtr, _ ByVal pTemplateName As LongPtr, ByVal hWndParent As LongPtr, _ ByVal lpDialogFunc As LongPtr, ByVal dwInitParam As LongPtr) As Integer If pTemplateName = 4070 Then MyDialogBoxParam = 1 Else RecoverBytes MyDialogBoxParam = DialogBoxParam(hInstance, pTemplateName, _ hWndParent, lpDialogFunc, dwInitParam) Hook End If End Function
Step 8: Repeat Step 6 and 7 and paste following code in “Module 2”
Sub unprotected() If Hook Then MsgBox "VBA Project is unprotected!", vbInformation, "*****" End If End Sub
Step 9: We are almost done. Next you need to run your code. To run the code, click on small Play button on the menu bar on top
You will see a message like this. Click on “OK” and your locked VBA project will be accessible now. Please note: This trick will work on 64 bit MS Excel only.