понедельник, 7 ноября 2011 г.

Как ускорить эмулятор Android на 400%

Последние несколько месяцев я работал над SDK для Android, входящим в платформу управления контентом Nuxeo. Особенно много работы было в последнее время, с приближением официального релиза SDK. Я хочу поделиться несколькими практическими советами по поводу разработки под Android, в частности тестирования и эмуляции. Уже после нескольких дней разработки я понял, что работа с эмулятором Android — не сахар, потому что он чудовищно медленный.



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

Тонкая настройка параметров Qemu не слишком помогла — скорость работы эмулятора осталась медленной, возможно именно поэтому большинство разработчиков предпочитает использовать реальные устройства, подключенные по USB.

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

Эмуляция против симуляции


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

Одна из причин состоит в том что он работает не как «настоящий симулятор», т.к. инструкции CPU, используемые в симуляторе iPhone такие же, как у компьютера, на котором запущен симулятор (x86).

Android, с другой стороны, вынужден эмулировать настоящий процессор архитектуры ARM поверх процессора x86. Это добавляет довольно значительный оверхед в плане производительности.

По крайней мере для демонстрации приложения мне ни к чему эмулировать ARM, мне нужна только возможность запустить Android и моё приложение.

Android_x86


К счастью, существует open source проект по портированию Android на процессоры x86: http://www.android-x86.org/.

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

Настройка Android_x86 внутри VirtualBox


Первый шаг: загрузить ISO-образ Android_x86. Я использовал android-x86-2.3-RC1-eeepc.iso, который может быть загружен с http://www.android-x86.org/download.

Следующий шаг: создание виртуальной машины, способной запускать этот образ.

Я использовал VirtualBox, но слышал что QEmu тоже неплохо подходит.

Итак, в VirtualBox необходимо создать новую машину:
целевая OS: choose Linux
  • версия целевой OS: другая
  • Я использовал 1GB RAM и 1 CPU (остальные настройки оставил по умолчанию)
  • добавить жёсткий диск: VDI drive, динамический размер, 512 Mio
  • добавить CDROM, в который загружен скачанный ISO
В загрузочном меню выбираем установку на жёсткий диск:
В процессе установки придётся сделать следующее:
  • создать новый раздел на жёстком диске
  • отформатировать его в ext3
  • выбрать этот раздел для инсталляции Android
Когда установка завершится:
  • выключить виртуальную машину
  • удалить устройство CDROM, указывающее на ISO образ (в окне конфигурации VirtualBox)
Загружаем виртуальную машину: у Вас теперь есть работающий образ Android x86.

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

Теперь нам необходимо изменить конфигурацию под экран телефона.

Выключаем VM и VirtualBox.

Первый шаг: создать новые режимы разрешения. Я определил 3 режима:

VBoxManage setextradata "Android2.3" "CustomVideoMode1" "320x480x16"
VBoxManage setextradata "Android2.3" "CustomVideoMode2" "640x960x16"
VBoxManage setextradata "Android2.3" "CustomVideoMode3" "480x720x16"

Здесь Android2.3 это имя созданной виртуальной машины.

Теперь, когда мы объявили новые режимы, необходимо их использовать. Для этого придётся изменить параметры ядра.

Чтобы это сделать, необходимо перезапустить виртуальную машину и в мню загрузки выбрать Debug mode, чтобы Android загрузился с командной строкой.

Запускаем виртуальную машину.

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

mount -o remount,rw /mnt

После этого можно будет редактировать файл menu.lst.

vi /mnt/grub/menu.lst

Теперь дублируем первый пункт меню (3 строки) и редактируем параметры ядра (первую запись «title» и две следующих строки).

Параметры по умолчанию таковы:

quiet root=/dev/ram0 androidboot_hardware=eeepc acpi_sleep=s3_bios,s3_mode DPI=240 SRC=/android-2.3-RC1

Параметры, которые я использовал:

quiet root=/dev/ram0 androidboot_hardware=generic_x86 acpi_sleep=s3_bios,s3_mode DPI=240 UVESA_MODE=480x720 SRC=/android-2.3-RC1

Название впишите какое понравится.

Если хотите выбирать разрешение при загрузке, можно сделать так:

quiet root=/dev/ram0 androidboot_hardware=generic_x86 acpi_sleep=s3_bios,s3_mode vga=ask SRC=/android-2.3-RC1

Сохраните свой menu.lst (:wq) и перезапустите виртуальную машину используя меню VirtualBox.

Теперь можно будет запустить виртуальную машину Android, которая будет выглядеть как телефон.

Несколько советов по использованию виртуальной машины:
  • Если не видите мышь на экране Android, используйте меню VirtualBox чтобы выключить mouse integration (кнопка Host+I).
  • Кнопка Windows соответствует кнопке Home в Android.
  • Esc соответствует кнопке «назад» в Android
  • F2 соответствует кнопке Menu
  • F3 соответствует кнопке поиска
  • Alt+F1 — переключение в консольный режим
  • Alt+F7 — переключение в режим GUI

Соединение виртуальной машины Android, AVD и Eclipse


Целью была возможность использовать новую виртуальную машину из Eclispe для тестирования и отладки приложений. Чтобы это сработало, нудно настроить сетевое соединение между основной операционной системой (где работает Eclipse) и гостевой VM. Для этого в VirtualBox есть несколько настроек в Network settings:
  • use bridge mode: он должен работать но для него может потребоваться запуск DHCP в основной ОС
  • host only network: создаёт виртуальную сеть между основной и гостевой машинами; это самый простой в использовании вариант
Когда сеть будет настроена, перезапустите виртуальную машину, войдите в режим командной строки (Alt+F1) и введите:
netcfg

Это выведет текущий IP виртуальной машины. Обычно это будет что то вроде 192.168.56.101 для гостевой машины, основная получает адрес 192.168.56.1.

На основной машине открываем командную строку, переходим в директорию platform-tools для Android:

./adb connect 192.168.56.101

Это зарегистрирует виртуальную машину в качестве нового устройства:
Теперь можно запускать и отлаживать Ваше приложение прямо из Eclipse.

Как видите, прирост скорости весьма заметный:
  • Запуск VM занимает 2 секунды вместо 30
  • Приложения запускаются очень быстро, даже в режиме отладки (нет тормозов, присущих эмулятору ARM)

Добавляем SD карту


Используйте документацию, расположенную по адресу http://www.android-x86.org/documents/sdcardhowto.

Используем файл в качестве SD карты


Из командной строки Android:

dd if=/dev/zero of=/data/sdcard.img bs=1024 count=65536 (64MB image)
losetup /dev/block/loop7 /data/sdcard.img
newfs_msdos /dev/block/loop7

Теперь перезапускаем VM в режиме отладки, перемонтируем раздел в режиме чтение+запись и редактируем menu.lst чтобы добавить один параметр ядра:

SDCARD=/data/sdcard.img

Используем отдельный раздел


Здесь потребуется чуть больше работы.

Для начала придётся создать новый жёсткий диск в VirtualBox и подключить его к виртуальной машине.

Теперь запускаем машину в режиме отладки. Используем fdisk чтобы создать раздел. Когда раздел создан, надо его отформатировать:

newfs_msdos /dev/sdb1

Теперь редактируем menu.lst и добавляем параметр:

SDCARD=sdb1


Впечатления от использования Android_x86 в качестве окружения для тестирования



Использование


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

Единственный заметный глюк: приложение галереи (Cooliris) сломано, я пробовал с последней ночной сборкой образа — стало немного лучше, но проблемы всё равно остаются.

Ещё одна странность: примерно в 10% случаев виртуальная машина не загружается и её приходится перезагружать. Так как загрузка происходит очень быстро, это не особо мешает, но я всё равно постараюсь понять в чём тут дело.

Скорость


Тут различия видны невооружённым глазом.

Вот немного цифр, чтобы было понятнее насколько всё ускорилось:

Эмулятор Android на ARM работает примерно наполовину медленнее чем Nexus One, а Android x86 — примерно в два раза быстрее.
источник: http://habrahabr.ru/


Unity3D, 2D платформер, персонаж прилипает к стене после прыжка.

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