Извлечение паролей сайтов в плагине LastPass

Извлечение паролей сайтов в плагине LastPass

Метод заключается в извлечение любых данных, которые могут быть в памяти, во время криминалистического исследования.

Автор: Кевин

Перед началом повествования я хотел бы сказать, что это не эксплоит и не уязвимость в LastPass. Метод заключается в извлечение любых данных, которые могут быть в памяти, во время криминалистического исследования. В определенный момент любая информация должна оказаться в открытом виде.

Я читал книгу Art Of Memory Forensics (если не читали, настоятельно рекомендую), и на одной из страниц речь зашла об извлечение паролей, используемых в браузере. Когда вы проходите авторизацию на вебсайте при помощи стандартного метода, обычно отсылается POST-запрос, содержащий имя пользователя и пароль. В этом случае информация отсылается в открытом виде (я не говорю о SSL, хотя внутри SSL информация все так же в открытом виде).
В книге объясняется, как найти и извлечь POST-запросы. Этот метод полезен, если вы извлекаете информацию, когда пользователь только что авторизовался в браузере, но не очень полезен, если авторизация произошла при помощи сессии.

Во время чтения я заглянул в свой браузер и увидел обычную иконку плагина LastPass с номером 1, что говорит об одном наборе записей для домена, на котором я в данный момент нахожусь.


Рисунок 1: Иконка плагина LastPass

В определенный момент LastPass должен заполнить форму авторизации учетными данными в открытом виде для последующего формирования POST-запроса. Сия процедура целесообразна в тот момент, когда я нахожусь на странице авторизации с включенной функцией автозаполнения. Однако если домен загружается в активную вкладку, вне зависимости от страницы, эта подсказка все равно отображается (см. рисунок выше).

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

Настройка рабочей среды

Я собирался проводить исследования исключительно в памяти, а, значит, мне нужно было найти простой и надежный способ для поиска и изменения информации, а также отслеживание внесенных правок.

Самый очевидный метод – создавать дамп каждый раз, когда вносятся изменения, что легко сделать в виртуальной машине. Мы просто делаем снимок каждый раз при изменении какой-либо информации. Затем мне нужно было сравнивать два снимка с целью нахождения точного места, где произошли изменения.

Далее процесс установки довольно прост: несколько браузеров (Chrome, IE, FF), учетная запись LastPass и добавление аккаунтов для нескольких сайтов.

В плагинах для браузеров я оставил стандартные настройки и использовал встроенную функцию для генерации паролей различной длины. В паролях использовались буквенно-цифровые символы смешанного регистра.

Кроме того, я скопировал все сгенерированные пароли в отдельный документ на основном компьютере, чтобы использовать эту информацию в дальнейшем.

После того как пароли были продублированы на моей машине, я разлогинился из всех учетных записей, почистил историю и папку с временными файлами, перезапустил и выключил машину.

Методика исследования

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

  • Открыть браузер.
  • Авторизоваться в плагине LastPass (если произошло разлогинивание).
  • Авторизоваться на сайте.
  • Проверить память на присутствие паролей в открытом виде.
  • Что-нибудь поменять:
    • Закрыть вкладку.
    • Повторно использовать вкладку.
    • Разлогиниться.
  • Повторить.

Тест №1

Я знал все имена пользователей и пароли, так что первый шаг был довольно очевидным. Я авторизовался на первом сайте при помощи тестовой учетной записи на FaceBook. После авторизации я прогулялся по двум страница и далее, оставив вкладку открытой, сделал первый снимок.

Мой первый поисковый запрос был простым:

grep -a 03rRJaYNMuoXG7hs Win7x64-MemTesting-Snapshot3.vmem | strings > ~/Desktop/fb.txt

Параметр –а говорит утилите grep о том, что бинарный дамп нужно обрабатывать как текст, а утилита string немного очищает выходные данные перед записью в текстовый файл.

В полученном текстовом файле сразу же видим незашифрованный пароль:


Рисунок 2: Содержимое снимка памяти во время работы с учетной записью в FaceBook

Два момента сразу же привлекают внимание:

Первый - объект JSON с паролем, именем домена, временными метками и другой информацией, которая, скорее всего, имеет отношение к автоматическому заполнению полей формы.

 {"reqinfo":{"from":"fillfield_A","index":28,"time":1475875701411,"uniqid":85097549},"docid":0,"sharedsite":0,"automaticallyFill":1,"is_launch":false,"manualfill":false,"name":"pass","value":"O3rRJaYNMuoXG7hs","type":"password","checked":false,"otherfield":false,"doconfirm":1,"allowforce":0,"from_iframe":0,"humanize":false,"v2humanize":false,"delayquants":0,"force_fillbest":false,"originator":"FILL_F4","cmd":"fillfield","clearfilledfieldsonlogoff":0,"dontfillautocompleteoff":0,"realurl":"https://www.facebook.com/","aid":"607245038900433242","tabid":2,"custom_js":"","domains":"facebook.com,facebook.com,messenger.com","formname":"","topurl":"https://www.facebook.com/","urlprefix":"chrome-extension://hdokiejnpimakedhajhdlcegeplioahd/","lplanguage":""}

Второй – выглядит немного оторванным от остальной информации.

passO3rRJaYNMuoXG7hspassword

Продолжаем исследование.

Тест №2

В следующем снимок делался во время авторизации на нескольких сайтах. Вкладки оставались открытыми. Далее происходило разлогинивание из всех учетных записей перед выключением и повторным запуском виртуальной машины. Я хотел сделать снимок памяти настолько чистым, насколько возможно.

Кроме того, чтобы убедиться, что браузер сам по себе не хранит данную информацию, я полностью почистил историю.

Рисунок 3: Полное удаление истории браузера

На скриншоте ниже видно, что все вкладки загружены и залогинены за исключением QNAP. Я зашел на главную страницу, и плагин LastPass показал, что есть одно совпадение учетных записей, но я еще не загрузил страницу с формой, и, соответственно, не произошло никакого автозаполнения.


Рисунок 4: Индикация совпадения одной учетной записи в тот момент, когда форма еще не загружена

При исследовании новых снимков использовались те же команды для всех доменов в открытых вкладках. По всем доменам, на которых я логинился, в памяти хранилась одна и та же структура данных.

 {"reqinfo":{"from":"fillfield_A","index":157,"time":1475878291419,"uniqid":65765520},"docid":0,"sharedsite":0,"automaticallyFill":1,"is_launch":false,"manualfill":false,"name":"ca414a13646af9ceb5293a5eeded1704","value":"5DAhhkOvZDTC0MYA14","type":"password","checked":false,"otherfield":false,"doconfirm":1,"allowforce":0,"from_iframe":0,"humanize":false,"v2humanize":false,"delayquants":0,"force_fillbest":false,"originator":"FILL_F4","cmd":"fillfield","clearfilledfieldsonlogoff":0,"dontfillautocompleteoff":0,"realurl":"http://androidforums.com/login/login/register","aid":"5988558277865511241","tabid":14,"custom_js":"","domains":"androidforums.com","formname":"","topurl":"http://androidforums.com/","urlprefix":"chrome-extension://hdokiejnpimakedhajhdlcegeplioahd/","lplanguage":""}

Кроме того, я заметил пару других структур данных:

 {"cmd":"save","url":"https://www.phpbb.com/community/ucp.php?mode=login","formdata":"login\tusername\tpeters.lastpass%40gmail.com\ttext\tseen\nlogin\tpassword\tSG5P2GRgqYeL4nvzi8C1XnZs\tpassword\tseen\nlogin\tautologin\ton-0\tcheckbox\tseen\nlogin\tviewonline\ton-0\tcheckbox\tseen\nlogin\tredirect\t.%2Fucp.php%3Fmode%3Dlogin\thidden\tnotseen\nlogin\tsid\t32ff2e6ecf53aaac43b88f123ad86b04\thidden\tnotseen\nlogin\tredirect\tindex.php\thidden\tnotseen\n0\taction\thttps%3A%2F%2Fwww.phpbb.com%2Fcommunity%2Fucp.php%3Fmode%3Dlogin\taction\n0\tmethod\tpost\tmethod\n","current_pw_field_name":"","docnum":0,"timestamp":1475878195546,"username":"peters.lastpass@gmail.com","password":"SG5P2GRgqYeL4nvzi8C1XnZs","tld":"phpbb.com"}
В структуре выше имя пользователя, имя домена и пароль хранятся как обычный текст.

Информация по сайту QNAP, который был просто загружен, но без заполнения формы, в памяти отсутствовала.

Во время поиска в памяти других интересных деталей я натолкнулся на интересную информацию:


Рисунок 5: Область данных, помеченная как LastPassPrivateKey

Найденная мной информация помечена как LastPassPrivateKey. На данный момент я занимаюсь выяснением, можно ли при помощи этой информации получить мастер-пароль или расшифровать файл с хранилищем.

Во время размышлений о возможностях использования содержимого PrivateKey меня осенило, что еще не проверено, присутствует сам мастер-пароль в памяти. Я предполагал, что мастер-пароль удаляется сразу же после расшифровки информации.

Используя grep, я нашел имя пользователя и пароль в открытом виде только в одном из снимков.

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

Что касается повторно используемых, неактивных и закрытых вкладок другими доменами, то здесь уже сложнее найти нужные структуры данных. Информация находится в памяти, и если вы знаете конкретные значения, то найти нужные структуры можно, в противном случае процесс напоминает поиск иголки в стоге сена.

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

Пару лет назад Брайан Баскин (Brian Baskin) опубликовал статью с описанием плагина Volatility, который использует YARA-правила для поиска и извлечения информации из памяти. Именно данная технология легла в основу моего плагина.

Далее нужно было применить несколько YARA-правил и впоследствии обработать полученную информацию, чтобы собрать результаты воедино.

После обработки снимка памяти вы получите нечто следующее:

 localadmin@tech-server:~$  vol.py --plugins=/home/localadmin/github/volatility_plugins/lastpass  --profile=Win7SP1x86 -f /home/localadmin/Desktop/lastpass-mem.vmem lastpass
Volatility Foundation Volatility Framework 2.5
Searching for LastPass Signatures
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3400)
Found pattern in Process: chrome.exe (3840)
Found pattern in Process: chrome.exe (3840)
Found pattern in Process: chrome.exe (3840)
Found pattern in Process: chrome.exe (3840)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (3912)
Found pattern in Process: chrome.exe (4092)
Found pattern in Process: chrome.exe (4092)
Found pattern in Process: chrome.exe (4092)
Found pattern in Process: chrome.exe (4092)
Found pattern in Process: chrome.exe (2036)
Found pattern in Process: chrome.exe (2036)
Found pattern in Process: chrome.exe (2036)

Found LastPass Entry for hackforums.net
UserName: peters.lastpass
Pasword: jRvTpQoTHS4OTcl

Found LastPass Entry for facebook.com
UserName: peters.lastpass@gmail.com
Pasword: Unknown

Found LastPass Entry for sainsburys.co.uk
UserName: peters.lastpass@gmail.com
Pasword: mt5JwaPctWFzBj

Found LastPass Entry for leakforums.net
UserName: peterslastpass
Pasword: rmH61HSabrVJ9a2

Found LastPass Entry for facebook.com,facebook.com,messenger.com
UserName: Unknown
Pasword: O3rRJaYNMuoXG7hs

 

Found Private Key
LastPassPrivateKey<308204BD020100300D06092A864886F70D0101010500048204A7308204A30201000282010100D0D534BEA030F199144DD4B1B0A69D6462BC13CF074B77CDEC0B4C06D3773B39F0D3353D58732D35809E2A45C9A70B94C366DE4E8B591178F5366A4328C96A82A51E8B1573A9546F859EA6C13EB1E08F1F69749598429244B96AFCAE0787CFC4CC19311D80F90679CE4C395FDBF22F9201381E0AEC345C724E1E61CE8EEE0A37EE38B04D5EEA1AB2562D815242E4D6379D23940ACD800921853787F0F1B37F249DE284780CE1D1FFF10FFCE778CD03A442C7A487C47A27D4F11EE98CF5E8B2AA8A7DEE0710B9C2D430CB33EC747E37298E16103493C6DF8A539F4893F30CCFA74D84E5FC40E1ED39316EA038D16748F58AE873704DD61B028940ECB083E7F1790940D4BD2A01C73DBA4AC26A2BB98CE7A2CDF02011102820100624636F04B62539354D955085321324102818100D05799FCC7514DBFC0DEC6E06E2A8715E9E46911DBBFCC59F1569A82930FDBD195A685C1BF13EABB75B46CC8484EB3771E102E76CE3D3756CEF13666C6581861EE23EC11ABB658BA2F815EF2D406FDD85830F6B599443004CEA4B1A79DAAAAEE86755FE354498C770EF3BE2077DD19EE3E7E53A9935FC0D76BD90D3B887F50575FA01A617A43F5D2C44815098207299381229DDA8F91713B7012D8F29A087A3918A2F76A222BA4202E8A0997D63D1EEF02F246DC0A5C0AC869191B9231DCD6D657FB4E6591DDFAF3026522F84E2D1EF2D5C05289EFF9D7E2F2A722374E0204C8FAA326024DF520B97505146AFB1AF7469B862977B1152430911BFA112E76A51C352D7F1B2C39669B4CF102818100FCFCA8B2F2074C1FB357A859AA583651D5DC9EA0446E0B33A7B41D9B7C9955832BEFB4E2151D17DDB851A1F46B16E26ECC6515BCB1C802DD73DA4ACD89083168E2678DE363EF1B45BAA1BA40F845D8396AFC269503F9A4F04D39271F02819A665D47036F0CA3628D78987102818100CEFC910EF956B3590A9A0907F59EB44CD25FF10032DAFE48C359057F75FBA5AF1CC1C6E11E37CF4F825D0E1540B5DA77FF6777FEE55621C1D0EF85D3C12702150D542A90CC8021FA132EF383835DA4358A0781E168897C779F2DA6A834DA20DBFDA4F643738B4DF6BBDD768947D9EC577466E18100D351EC8A77C7582E0A78C5ACA9D86068BB82D721B0841962F959A25A01FA80FFB765DE228798>LastPassPrivateKey

Found Private Key
LastPassPrivateKey<\x00\xb2\x88\x10\x02N;$\x02&\x00\x00\x00>LastPassPrivateKey
localadmin@tech-server:~$

Мне нужно еще многое доработать, чтобы полностью доделать плагин. Текущую версию можно взять на Github: https://github.com/kevthehermit/volatility_plugins/tree/master/lastpass

Устали от того, что Интернет знает о вас все?

Присоединяйтесь к нам и станьте невидимыми!