Есть ли способ взломать пароль в проекте Excel VBA? - PullRequest
444 голосов
/ 22 июня 2009

Меня попросили обновить некоторые макросы Excel 2003, но проекты VBA защищены паролем, и, похоже, не хватает документации ... никто не знает пароли.

Есть ли способ удаления или взлома пароля в проекте VBA?

Ответы [ 22 ]

10 голосов
/ 10 февраля 2018

Пароли проекта VBA в документах Access, Excel, Powerpoint или Word (2007, 2010, 2013 or 2016 версии с расширениями .ACCDB .XLSM .XLTM .DOCM .DOTM .POTM .PPSM) могут быть легко удалены .

Это просто вопрос изменения расширения имени файла на .ZIP, разархивирования файла и использования любого основного шестнадцатеричного редактора (например, XVI32 ), чтобы «сломать» существующий пароль, что «смущает» Office поэтому при следующем открытии файла запрашивается новый пароль.

Краткое изложение шагов:

  • переименуйте файл, чтобы он имел расширение .ZIP.
  • откройте ZIP и перейдите в папку XL.
  • извлеките vbaProject.bin и откройте его с помощью Hex Editor
  • «Найти и заменить», чтобы «заменить все», изменив DPB на DPX.
  • Сохраните изменения, поместите файл .bin обратно в zip, верните его в нормальное расширение и откройте файл как обычно.
  • ALT + F11 для входа в VB Editor и щелкните правой кнопкой мыши в Project Explorer, чтобы выбрать VBA Project Properties.
  • На вкладке Protection Установите новый пароль.
  • Нажмите OK, закройте файл, снова откройте его, нажмите ALT + F11.
  • Введите новый пароль, который вы установили.

На этом этапе вы можете полностью удалить пароль, если захотите.

Полные инструкции с пошаговым видео, которое я сделал «назад, когда» включен YouTube здесь .

Это шокирует, что этот обходной путь существует уже много лет, и Microsoft не устранила проблему.


Мораль этой истории?

Microsoft Office Пароли проекта VBA , на которые нельзя полагаться для обеспечения безопасности любой конфиденциальной информации . Если важна безопасность, используйте стороннее программное обеспечение для шифрования.

9 голосов
/ 30 ноября 2010

Colin Pickard в основном верен, но не путайте защиту «пароль для открытия» всего файла с защитой паролем VBA, которая полностью отличается от предыдущей и одинакова для Office 2003 и 2007 (для Office 2007, переименуйте файл в .zip и найдите vbaProject.bin внутри zip). И что технически правильный способ редактировать файл - это использовать средство просмотра составных документов OLE, такое как CFX, чтобы открыть правильный поток. Конечно, если вы просто заменяете байты, может работать обычный старый бинарный редактор.

Кстати, если вас интересует точный формат этих полей, они уже задокументированы:

http://msdn.microsoft.com/en-us/library/dd926151%28v=office.12%29.aspx

9 голосов
/ 18 ноября 2018

С моей стороны, это основано на превосходном ответе kaybee99, который основан на фантастическом ответе Тхана Нгуйена, чтобы этот метод мог работать как с x86, так и с amd64 версиями Office.

Обзор того, что изменилось, мы избегаем push / ret, который ограничен 32-битными адресами, и заменяем его на mov / jmp reg.

Проверено и работает на

Word / Excel 2016 - 32-битная версия .
Word / Excel 2016 - 64-битная версия .

как это работает

  1. Откройте файл (ы), которые содержат ваши заблокированные проекты VBA.
  2. Создайте новый файл того же типа, что и выше, и сохраните этот код в Module1

    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 11) As Byte
    Dim OriginBytes(0 To 11) 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)), 12
    End Sub
    
    Public Function Hook() As Boolean
        Dim TmpBytes(0 To 11) As Byte
        Dim p As LongPtr, osi As Byte
        Dim OriginProtect As LongPtr
    
        Hook = False
    
        #If Win64 Then
            osi = 1
        #Else
            osi = 0
        #End If
    
        pFunc = GetProcAddress(GetModuleHandleA("user32.dll"), "DialogBoxParamA")
    
        If VirtualProtect(ByVal pFunc, 12, PAGE_EXECUTE_READWRITE, OriginProtect) <> 0 Then
    
            MoveMemory ByVal VarPtr(TmpBytes(0)), ByVal pFunc, osi+1
            If TmpBytes(osi) <> &HB8 Then
    
                MoveMemory ByVal VarPtr(OriginBytes(0)), ByVal pFunc, 12
    
                p = GetPtr(AddressOf MyDialogBoxParam)
    
                If osi Then HookBytes(0) = &H48
                HookBytes(osi) = &HB8
                osi = osi + 1
                MoveMemory ByVal VarPtr(HookBytes(osi)), ByVal VarPtr(p), 4 * osi
                HookBytes(osi + 4 * osi) = &HFF
                HookBytes(osi + 4 * osi + 1) = &HE0
    
                MoveMemory ByVal pFunc, ByVal VarPtr(HookBytes(0)), 12
                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
    
  3. Вставьте этот код в Module2 и запустите его

    Sub unprotected()
        If Hook Then
            MsgBox "VBA Project is unprotected!", vbInformation, "*****"
        End If
    End Sub
    
7 голосов
/ 08 октября 2013

Если файл является действительным zip-файлом (первые несколько байтов 50 4B - используются в таких форматах, как .xlsm), распакуйте файл и найдите подфайл xl/vbaProject.bin. Это файл CFB, как и .xls файлы. Следуйте инструкциям для формата XLS (применяется к подфайлу), а затем просто заархивируйте содержимое.

Для формата XLS вы можете использовать некоторые другие методы в этом посте. Я лично предпочитаю искать блок DPB= и заменять текст

CMG="..."
DPB="..."
GC="..."

с пробелами. Это устраняет проблемы с размером контейнера CFB.

5 голосов
/ 20 ноября 2015

Я попробовал некоторые из приведенных выше решений, и ни одно из них не работает для меня (файл Excel 2007 xlsm). Затем я нашел другое решение, которое даже восстанавливает пароль, а не просто взламывает его.

Вставьте этот код в модуль, запустите его и дайте ему немного времени. Он восстановит ваш пароль грубой силой.

Sub PasswordBreaker()

'Breaks worksheet password protection.

Dim i As Integer, j As Integer, k As Integer
Dim l As Integer, m As Integer, n As Integer
Dim i1 As Integer, i2 As Integer, i3 As Integer
Dim i4 As Integer, i5 As Integer, i6 As Integer
On Error Resume Next
For i = 65 To 66: For j = 65 To 66: For k = 65 To 66
For l = 65 To 66: For m = 65 To 66: For i1 = 65 To 66
For i2 = 65 To 66: For i3 = 65 To 66: For i4 = 65 To 66
For i5 = 65 To 66: For i6 = 65 To 66: For n = 32 To 126
ActiveSheet.Unprotect Chr(i) & Chr(j) & Chr(k) & _
Chr(l) & Chr(m) & Chr(i1) & Chr(i2) & Chr(i3) & _
Chr(i4) & Chr(i5) & Chr(i6) & Chr(n)
If ActiveSheet.ProtectContents = False Then
MsgBox "One usable password is " & Chr(i) & Chr(j) & _
Chr(k) & Chr(l) & Chr(m) & Chr(i1) & Chr(i2) & _
Chr(i3) & Chr(i4) & Chr(i5) & Chr(i6) & Chr(n)
Exit Sub
End If
Next: Next: Next: Next: Next: Next
Next: Next: Next: Next: Next: Next
End Sub
5 голосов
/ 12 апреля 2010

ElcomSoft делает Advanced Office Password Breaker и Advanced Office Password Recovery продуктов, которые могут применяться в этом случае, если документ был создан в Office 2007 или ранее.

4 голосов
/ 12 апреля 2010

Том - я изначально сделал ошибку для школьника, так как не смотрел размер байта, а вместо этого скопировал и вставил из «CMG», настроенного для последующей записи. Это были два разных размера текста между этими двумя файлами, и я потерял проект VBA, как и предупреждал Стеубоб.

Используя HxD, есть счетчик, отслеживающий, сколько файлов вы выбираете. Скопируйте, начиная с CMG, пока счетчик не прочитает 8F (шестнадцатеричное для 143), а также при вставке в заблокированный файл - у меня получилось вдвое больше «...» в конце вставки, что выглядело как-то странно и ощущалось почти неестественно, но это сработало.

Не знаю, критично ли это, но перед тем, как снова открыть файл в Excel, я закрыл оба шестнадцатеричных редактора и вышел из строя. Затем мне пришлось пройти через меню, чтобы открыть VB Editor, в VBProject Properties и ввести «новый» пароль, чтобы разблокировать код.

Надеюсь, это поможет.

3 голосов
/ 03 мая 2011

Мой инструмент, VbaDiff , считывает VBA непосредственно из файла, так что вы можете использовать его для восстановления защищенного кода VBA из большинства офисных документов без использования шестнадцатеричного редактора.

2 голосов
/ 22 июня 2009

Защита представляет собой простое сравнение текста в Excel. Загрузите Excel в ваш любимый отладчик ( Ollydbg - мой инструмент выбора), найдите код, который выполняет сравнение, и исправьте его, чтобы он всегда возвращал true, это должно позволить вам получить доступ к макросам.

1 голос
/ 05 июня 2017

Измените расширение вашего файла Excel на xml. И откройте его в блокноте. текст пароля найти в файле xml.

вы видите, как показано ниже;

Sheets("Sheet1").Unprotect Password:="blabla"

(извините за мой плохой английский)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...