information security
76,88
рейтинг
29 июля 2014 в 00:57

Разработка → Анализ sms-бота для Android. Часть I

Анализ sms-бота для Android. Часть I.


image

Введение
Разбор smsBot (Android) с целью выявления принципа работы и интересного функционала.
Бот реализован для платформы Android, алгоритм вскрытия приложения таков:
  • Скачиваем APK-файл;
  • Извлекаем файл манифеста;
  • Декомпилируем приложение в читаемый исходный или байт-код;
  • Анализируем манифест и код.

Инструментарий:
  • Apktool – Используем для того, чтобы вытащить манифест и ресурсы;
  • Dex2jar – Декомпилируем APK-файл в байт-код;
  • Jd-gui – Байт-код переводим в читабельный код.


Знакомимся с манифестом

Открыв манифест, сразу же обратим внимание на системные разрешения, которые показались мне более интересными:
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.CALL_PHONE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission android:name="android.permission.WRITE_SMS" />
<uses-permission android:name="android.permission.READ_SMS" />
<uses-permission android:name="android.permission.RECEIVE_SMS" />
<uses-permission android:name="android.permission.SEND_SMS" />
<uses-permission android:name="android.permission.READ_CONTACTS" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />

Итак, наш бот считывает состояние телефона, обрабатывает звонки, производит запись на флешку, писать/читать/получать/отправлять СМС-ки, читать базу контактов и записывать аудио. Интересно…

Далее, по манифесту. Видим следующий код:
…
<service android:name="com.soft360.iService.AService" android:enabled="true" android:exported="false" />
<service android:name="com.soft360.iService.webService" android:enabled="true" android:exported="false" />
<receiver android:name="com.soft360.iService.Alarm" android:enabled="true" android:exported="false" />
<receiver android:name="com.soft360.iService.AutoStart" android:enabled="true" android:exported="false">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED" />
           </intent-filter>
</receiver>
<activity android:theme="@*android:style/Theme.Translucent" android:name="com.BioTechnology.iClientsService.IncomingCallActivity" />
<receiver android:name="com.soft360.Receiver.MyPhoneReceiver">
            <intent-filter>
                <action android:name="android.intent.action.PHONE_STATE" />
            </intent-filter>
</receiver>
<receiver android:name="com.soft360.web.MyAdmin" android:permission="android.permission.BIND_DEVICE_ADMIN">
            <intent-filter>
                <action android:name="android.app.action.DEVICE_ADMIN_ENABLED" />
            </intent-filter>
            <meta-data android:name="android.app.device_admin" android:resource="@layout/policies" />
</receiver>
…


Видим, что объявлены:
  • сервисы AService и webService,
  • ресиверы Alarm, AutoStart, MyPhoneReceiver(следит за состоянием телефона, скорее всего за звонками), MyAdmin (бот хочет админить устройство).

Анализ манифеста на этом закончим. Просмотрел файлы ресурсов, ничего интересного не нашел. Теперь давайте перейдем к анализу полученного java-кода.

Анализируем код

Бот состоит как минимум из 19 основных рабочих классов. В результате анализа я выделил самые основные и интересные классы, которые отвечают за вредительскую деятельность бота:
  • — AutoStart.java;
  • — aService.java;
  • — smsParser.java;
  • — smsReciever.java;
  • — webServiceRobot.java;


MainActivity.java

Перед тем как начать анализ вышеуказанных классов, давайте заглянем в класс MainActivity. Посмотрим, что там есть интересного.
Intent localIntent1 = new Intent("android.provider.Telephony.SMS_RECEIVED");
localIntent1.setClass(this, SmsReciever.class);
sendBroadcast(localIntent1);
Intent localIntent2 = new Intent(this, AService.class);
startService(localIntent2);
Intent localIntent3 = new Intent(this, webService.class);
startService(localIntent3);


Сразу же при загрузке, бот пытается:
  • Все приходящие СМС-ки направить в SmsReciver;
  • Запускает службы AService и webService.


Далее, по коду видим еще интересную вещь:
Intent localIntent4 = new Intent("android.app.action.ADD_DEVICE_ADMIN");
localIntent4.putExtra("android.app.extra.DEVICE_ADMIN", this.compName);
localIntent4.putExtra("android.app.extra.ADD_EXPLANATION", "Additional text explaining why this needs to be added.");
startActivityForResult(localIntent4, 1);

Видно, что бот пытается добавить себя как еще одного администратора устройства.

Внимание! Обманный маневр.
Дальше в MainActivity.java запускает много разных шаблонов для отвода глаз пользователя, прикидываясь при этом приложением, которое якобы сканирует телефон на всякого рода мобильные уязвимости, а также якобы самообновляется. И вся эта красота дается на португальском языке, с указанием какого-то австралийского банка.

На самом деле не происходит никакого сканирования телефона, скачивания сертификатов и т.д. Запускаются лишь шаблоны пустышки, которые имитируют бурную деятельность. Вот пример такой пустышки:
 private class template4_task
    extends AsyncTask<Void, Void, Void>
  {
    private template4_task() {}
    protected Void doInBackground(Void... paramVarArgs)
    {
      try
      {
        TimeUnit.SECONDS.sleep(5L);
        return null;
      }
      catch (InterruptedException localInterruptedException)
      {
        for (;;)
        {
          localInterruptedException.printStackTrace();
        }

Запускается Асинтаск, а там таймер, который просто запускается и… ничего не делает!

Ресивер AutoStart

Данный ресивер начинает свою работу сразу же после загрузки телефона и запускает те же действия, что были MainActivity:
      Intent localIntent = new Intent("android.provider.Telephony.SMS_RECEIVED");
      localIntent.setClass(paramContext, SmsReciever.class);
      paramContext.sendBroadcast(localIntent);
      paramContext.startService(new Intent(paramContext, AService.class));
      paramContext.startService(new Intent(paramContext, webService.class));


Служба aService

Данный сервис, фильтруя события, регистрирует и запускает ресивер smsReciever, который в свою очередь будет получать и обрабатывать все полученные СМС-ки (но о нем чуть позже).
Вот и доказательства:
…
final IntentFilter smsFilter = new IntentFilter("android.provider.Telephony.SMS_RECEIVED");
…
    this.smsFilter.setPriority(999);
    this.smsReceiver = new SmsReciever();
    registerReceiver(this.smsReceiver, this.smsFilter);


smsReceiver и smsParser

Теперь переходим к более интересным кускам кода бота. Это ресивер smsReceiver и отдельный класс для идентификации кодов из СМС-ок и веб-админки.

Привожу очень урезанный кусок кода из smsReceiver:
public void onReceive(Context paramContext, Intent paramIntent)
  {
…
    for (;;)
    {
…
      {
        smsParser localsmsParser = smsParser.getInstance();
        localsmsParser.setSMSMessage(localSmsMessage.getMessageBody());
        if (localsmsParser.isStartSMS()) {
          localdbActions.setStartSMS();
        }
…
            if (localsmsParser.isStopSMS())
            {
              localdbActions.setStopSMS();
            }
            else if (localsmsParser.isStartCALL())
            {
              try
              {
                localdbActions.setStartCALL();
              }
…
            else if (localsmsParser.isStopCALL())
            {
              try
              {
                localdbActions.setStopCALL();
              }
…
            else if (localsmsParser.isSmsList())
            {
              localdbActions.sent_smslist_to_server();
            }
            else if (localsmsParser.isCallList())
            {
              localdbActions.sent_Call_Details();
            }
            else if (localsmsParser.isStartRecord())
            {
              if (webServiceRobot.AR != null) {
                try
                {
                  webServiceRobot.AR.stop();
                  webServiceRobot.AR = null;
                  return;
                }
…
              if (localsmsParser.isStopRecord())
              {
                localdbActions.setStopRecord();
                if (webServiceRobot.AR == null) {
                  break;
                }
                try
                {
                  webServiceRobot.AR.stop();
                  webServiceRobot.AR = null;
                }
…
              }
              if (localsmsParser.isSmsSend())
              {
                localdbActions.SendSMS(localSmsMessage.getMessageBody());
              }
              else if (localsmsParser.isContactList())
              {
                localdbActions.sent_call_list_details();
              }
              else
              {
                if (!localsmsParser.isWipeData()) {
                  break label592;
                }
                localdbActions.make_wipe_data();
...
        paramContext.startService(new Intent(paramContext, AService.class));
        paramContext.startService(new Intent(paramContext, webService.class));
…


Я думаю, что подробные комментарии не нужны. Из кода видно что:
  • Устанавливаются флажки на начало/остановку записей телефонных звонков;
  • Отправка СМС;
  • Отправка списка смс-ок;
  • Отправка списка звонков;
  • Затирании инфы и др.


localsmsParser ключевой элемент. Поэтому дальше давайте поглядим на класс smsParser:
  private static final String COMMAND_GET_CALL_LIST = "call list";
  private static final String COMMAND_GET_CONTACT_LIST = "contact list";
  private static final String COMMAND_GET_SMS_LIST = "sms list";
  private static final String COMMAND_PING = "ping";
  private static final String COMMAND_SEND_SMS = "sendSMS";
  private static final String COMMAND_START_RECORD = "start record";
  private static final String COMMAND_STOP_RECORD = "stop record";
  private static final String COMMAND_WIPE_DATA = "wipe data";
  private static final String startCALL = "call start";
  private static final String startSMS = "sms start";
  private static final String stopCALL = "call stop";
  private static final String stopSMS = "sms stop";
  private static final String changeNUM = "change num";
  private static final int COM_CALL_LIST = 6;
  private static final int COM_CONTACT_LIST = 10;
  private static final int COM_NULL = -1;
  private static final int COM_PING = 12;
  private static final int COM_SEND_SMS = 9;
  private static final int COM_SMS_LIST = 5;
  private static final int COM_START_CALL = 3;
  private static final int COM_START_RECORD = 7;
  private static final int COM_START_SMS = 1;
  private static final int COM_STOP_CALL = 4;
  private static final int COM_STOP_RECORD = 8;
  private static final int COM_STOP_SMS = 2;
  private static final int COM_WIPE_DATA = 11;
  private static smsParser parser = null;

По этим константам мы можем понять какие функции может выполнять наш бот. Одни и те же команды даны в строковом и цифровом виде. Скорее всего, происходит проверка на то, из какого источника идут команды (СМС или интернет).

webServiceRobot

Данный класс похож на smsReceiver с тем отличием, что обрабатывает http-запросы. Выполняются практически все те же действия:
  • Отправка СМС;
  • Отправка списка смс-ок;
  • Отправка списка звонков;
  • Затирании инфы и др.

Плюс отправка полной информации об устройстве на сервер.

Выводы

Ну что же, основные куски кода мы рассмотрели. Теперь давайте сделаем выводы. Бот написан неплохо и выполняет очень обширное количество функций. Собственно, объявление с одного из форумов о продаже данного бота:
Уважаемые господа, рады Вам предложить бота под мобильные устройства. В данный момент бот реализован под операционную систему Android, так же рады вам сообщить, что разработка Blackberry ведется полным ходом, и первые бета версии будут в ближайший месяц, всем клиентам по Android боту на Blackberry будут существенные скидки.
Теперь вкратце расскажу как это работает, для тех кто не знает, после установки на мобильное устройство, приложение моментально отстукивает в удобную web-panel при наличии 3g или wi-fi, а так же отсылает SMS на управляющий номер с текстом I am (ICCID+MODEL PHONE). Наш бот реализован таким образом, что после попадания в систему юзер продолжает спокойно пользоваться своим телефоном, все функции ему доступны в штатном режиме. В отличии от знаменитого Perkele у нас нет заточки под определенные номера для перехвата, наш бот работает через систему команд. Команды даются любым удобным для Вас способом, либо из web panel при наличии интернета, либо SMS с управляющего номера.


Функционал:

  • Грабинг всей информации о жертве (Phone Number,ICCID,IMEI,IMSI,Model,OS)
  • Перехват всех входящих SMS и отправка их в web-panel и на управляющий номер.
  • Переадресация звонков на любой номер
  • Грабинг всех входящих и исходящих SMS
  • Грабинг всех входящих и исходящих ВЫЗОВОВ
  • Запись аудиофайла, отправка его на сервер( знаем, что происходит вокруг)
  • Отправка SMS на любой номер без ведома владельца
  • Удобная Web Panel

Итак, данный софт продается, цена бота 4к, в комплекте вы получаете админскую панель настроенную на вашем сервере+управляющий веб номер+файл .apk с уникальным интерфейсом, разработанным под Ваши нужды, а так же постоянную поддержку продукта. Так же, готовы рассмотреть варианты аренды и совместной работы за процент (просьба не стучать, если у вас нету инжектов и вы не знаете, как это применять). За более подробной информацией пишите мне в ПМ свой jabber для контакта, GPG и OTR жизненно необходимы.

Уважаемые господа. Вышел UPDATE под Android. Всем клиентам стукнуть за обновлением и ждем новых клиентов.
Что нового?
  • Теперь наше приложение крайней сложно удалить. При установке приложения софт запрашивает права админа устройства, если холдер ему их предоставляет, то приложение будет удалить крайне муторно, службы будут перезапускаться и вы не потеряете данного бота. Если же не предоставят, то приложение как и раньше будет работать в штатном режиме. Для вашего удобства в админ панели появился индикатор, показывающий даны админ права или нет.
  • Если предоставили права админа, то есть возможность снести телефон командой до заводских настроек


Название смс бота у антивирусных вендоров: Trojan-Spy.AndroidOS.Zbot.a / Android.Smssniffer / Android/SpySMS / AndroidOS_SMSREP.B

Набиев Нурлан (Казахстан), отдел расследования киберпреступлений, PentestIT
Автор: @pentestit-team
Pentestit
рейтинг 76,88
information security
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Реклама

Комментарии (10)

  • +1
    Довольно любознательно, спасибо. И с ходу вопрос — а как распространяют данное по? Вшивают в ломанные apk, маскируют под что-либо в Google Play, или?..
    • +3
      Путей распространения несколько — как перечисленные Вами, так и рассылка в виде ссылок на приложение, атаки на Android устройства и т.д.
  • +3
    Очень интересно, спасибо. Что-то похожее я рассказывал на последней киевской конференции OWASP (доклад «The Hunt for an Android botnet»). Только malware был сложнее устроен, а его анализ включал взлом и перехват контроля над Command & Control Center с последующей идентификацией личности владельца. В целом тема очень интересная, и я надеюсь не только мне. Большое спасибо за статью.
    • +3
      В контексте разбора этого бота не стояла задача получить контроль на командным центром и установить личность хозяина ботнета.
      • +1
        Ну да, задачи в каждом конкретном случае конечно могут стоять разные :)
  • –3
    Насколько я знаю, в андроиде 4.4 теперь нельзя перехватывать смс, т.е. все входящие смс будут выскакивать и юзер их увидит. В таком случае элементарно спалить бота. Так что всем совет — обновляйтесь до последнего андроида.
    • 0
      не у всех есть такая возможность…
  • 0
    В свое время анализировал подобный вирус :) habrahabr.ru/company/appsministry/blog/168573/
  • 0
    Вы не могли бы отформатировать код и использовать тэг <source>? Спасибо!

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

Самое читаемое Разработка