понедельник, 3 октября 2016 г.

Двойная прошивка андроид. 5 вариантов dual boot.



В этой статье мы поговорим о подходах, которые можно использовать для получения возможности загрузки нескольких ОС на одном смартфоне или планшете. Сразу оговорюсь, что вначале будет много теории, которая необходима для понимания самого процесса, что позволяет повторить его, не прибегая к сторонним инструментам. Если подобная информация тебя не интересует, можешь смело перелистнуть страницу и начать чтение с раздела «MultiROM». Всех остальных читателей приглашаю окунуться в странный и причудливый мир случайных инженерных находок, костылей и хаков.
ТРУДНОСТИ DUAL BOOT

 
Начнем с того, что попробуем разобраться, что же такое пресловутый dual boot и почему он прекрасно работает на ПК, но не может быть реализован на мобильном устройстве без костылей
и перекладин. Как происходит загрузка нескольких ОС на обычном ПК? В MBR прошивается специальный загрузчик, позволяющий выбирать раздел, с которого будет продолжена загрузка
системы. Включив комп, пользователь выбирает в меню нужный пункт меню, и загрузчик выполняет код, прописанный в начале раздела; обычно там располагается собственный загрузчик ОС, который передает управление ядру ОС, и дальше происходит загрузка самой ОС.
На деле все может быть несколько сложнее. Например, загрузчик Linux не передает управление коду в начале раздела, а самостоятельно загружает ядро из нужного раздела в память и передает ему управление, но в нашем случае это неважно.
А важно то, что для настольной ОС обычно достаточно всего одного раздела, размер и наличие которого в системе определяет сам пользователь. Нужны три ОС на одном диске — разбиваешь диск на три раздела и ставишь в каждый из них нужную операционку (для никсов обычно отводят по три-четыре раздела, но можно установить и на один).
В гаджетах, основанных на Android, все иначе. Разметка внутренней NAND-памяти устройства обычно определяется еще на этапе проектирования смартфона и зашивается вместе с первичным загрузчиком в постоянную память. По правилам память должна содержать как минимум шесть поименованных разделов: boot, system, data, cache, misc и recovery, каждый из которых, за исключением двух последних, необходим для корректной работы Android.
Чтобы получить возможность корректной установки на такую систему двух разных ОС, необходимо, во-первых, переразбить память на разделы, что возможно, только если перезаписать
первичный загрузчик, а во-вторых, создать еще несколько разделов для других ОС, не говоря уже о том, что придется найти способ переключения между ОС. Однако выполнить ни тот ни другой пункт не получится, так как первичный загрузчик в большинстве случаев изменить невозможно, а если даже и возможно, делать это крайне не рекомендуется: малейшая ошибка в загрузчике окирпичит смартфон так, что его придется нести в сервисный центр. Как же быть и почему тогда существуют системы, позволяющие грузить несколько систем на одном гаджете? Правильно, все дело в хаках.
СПОСОБ НОМЕР 1. МОДИФИЦИРОВАННЫЙ RECOVERY + SD-КАРТА
В обычной ситуации загрузка Android происходит следующим образом. Юзер нажимает кнопку включения, активируется первичный загрузчик, который проверяет таблицу разделов и передает управление коду, расположенному в начале раздела boot.
Этот код делает бутстрап ядра; получив управление, оно подключает расположенный в том же разделе boot RAM-диск, из которого запускается процесс init, подключает остальные разделы, описанные в специальном файле внутри ram-диска, и загружает ОС.
Казалось бы, все просто, но есть тут одна особенность: если первичный загрузчик обнаружит, что вместе с кнопкой включения была нажата кнопка уменьшения громкости (или другая кнопка, в разных устройствах по-разному) или что в раздел misc прописана специальная метка, он передаст управление не boot, а recovery! Последний, как ты знаешь, содержит консоль восстановления, но соль не в этом, а в том, что и по размеру, и по содержимому раздел recovery очень похож на boot.
Что это нам дает? Правильно, в recovery можно залить образ boot-раздела другой прошивки и заставить ее подключить остальные разделы системы не из внутренней памяти устройства, а с предварительно разбитой на разделы SD-карты. Это самый простой и очень древний способ настройки dual boot, который появился еще во времена первых версий Android, а сегодня используется для организации двойной загрузки Android/Ubuntu (настольной версии) на планшетах и в инсталляторе Ubuntu Touch (поддерживаются только нексусы).
Плюс данного способа в чрезвычайной простоте реализации. Все, что нужно сделать, — это разбить SD-карту на разделы (два в случае с Android — system и data, раздел cache используется стандартный) с файловой системой ext4, распаковать образ boot-раздела второй прошивки, изменить несколько строк в файле fstab внутри RAM-диска, запаковать образ и прошить в раздел recovery. А вот минусов у способа множество. Это и невозможность получить доступ к recovery
(на самом деле возможно, если прошить образ recovery прямо из работающей системы, но это извращение), ограничение на одну стороннюю ОС и необходимость наличия слота для карт памяти в устройстве. К счастью, есть более удобная модификация данного способа.
MultiROM не умеет работать с зашифрованным разделом data («Опции Безопасность Зашифровать данные»).
СПОСОБ НОМЕР 2. ДИНАМИЧЕСКАЯ ПЕРЕЗАПИСЬ BOOT
У раздела boot есть одна особенность, которая уже должна была стать понятной по ходу повествования: все его содержимое загружается в оперативную память на этапе инициализации, поэтому после окончания первого этапа загрузки необходимость в нем отпадает ровно до следующей перезагрузки.
Благодаря этой особенности мы можем реализовать модифицированный вариант первого способа, который не потребуетперезаписи recovery.
Основная идея здесь остается той же: карта памяти с нужными разделами и модифицированный образ boot-раздела. Однако вместо перманентного размещения boot в разделе recovery применяется следующий трюк. Карта памяти разбивается, и на нее устанавливается нужная система, а в свободное пространство на карте кладется образ boot-раздела этой системы. В самом смартфоне при этом ничего не меняется, но, если возникает потребность загрузки второй ОС, образ boot-раздела второй системы записывается в раздел boot прямо во время работы Android и происходит перезагрузка. Как результат, в следующий раз система загружает boot-раздел второй системы и, соответственно, загрузка ОС происходит с карты памяти. Для возврата к первой системе применяется обратная операция (запись образа boot первой системы).
Этот способ хоть и не идеален, но достаточно популярен. Однако большинство решений все-таки используют следующую его модификацию.
СПОСОБ НОМЕР 3. ОТКАЗ ОТ КАРТЫ ПАМЯТИ
Способ, предполагающий установку ОС на карту памяти, хорошо работает, но имеет ряд неиллюзорных проблем. Вопервых, смартфон должен иметь слот для этой самой карты, поэтому Nexus’ы и многие другие современные смартфоны сразу оказываются в пролете. Во-вторых, сам факт необходимости форматирования карты памяти отпугивает многих юзеров, особенно тех, кто боится потерять доступ к карте из Windows. В-третьих, при необходимости установки нескольких ОС есть шанс просто запутаться в многообразии разделов на карте.
Для решения этой проблемы можно использовать следующий трюк. В ядре Linux еще со времен правления Ельцина есть механизм, называемый loop-монтированием. Если кратко, он позволяет подключить файловую систему не с реального раздела, а из его образа, записанного в обычный файл. Такая возможность доступна в большинстве ядер для смартфонов под управлением Android, и для ее использования достаточно лишь изменить образ boot-раздела (файл fstab) вторичной прошивки так, чтобы перед подключением основных разделов он монтировал карту памяти или раздел /data, в котором хранятся образы раздела прошивки, и затем подключал их, используя механизм loop.
Способ хорош тем, что позволяет установить на смартфон неограниченное количество прошивок, число которых будет зависеть только от вместимости карты памяти или внутренней памяти смартфона. Однако, как и все перечисленные выше методы, он до сих пор зависит от грязного хака с перезаписью раздела boot для загрузки другой прошивки. В результате, если одна из прошивок откажется загружаться, восстановить другую удастся только с помощью загрузки recovery и записи boot-раздела другой прошивки вручную через ADB. Что не очень удобно, а многим просто не по силам.
СПОСОБ НОМЕР 4.KEXEC + ВТОРИЧНЫЙ ЗАГРУЗЧИК
И вот мы подошли к самому правильному и адекватному методу двойной загрузки из всех, что энтузиасты смогли придумать. По сути, это все тот же третий способ, но с одним очень и очень важным дополнением — задействованием механизма kexec вместо перезаписи boot-раздела. Kexec — это одна из функций ядра Linux, которая позволяет загрузить другое ядро, не перезагружая всю систему. Работает этот метод примерно так. В раздел boot основной прошивки встраивается специальный код, который содержит в себе так называемый вторичный загрузчик.
Все дополнительные прошивки устанавливаются на манер предыдущего метода, а информация о местоположении образов их boot-разделов прописывается в настройки загрузчика. Когда пользователь включает смартфон, вторичный загрузчик получает управление и выводит на экран меню с выбором загружаемой прошивки. Юзер тапает по одному из пунктов меню, загрузчик находит boot-раздел выбранной прошивки, извлекает из него и загружает в память ядро и RAM-диск, а затем передает этому ядру управление с помощью kexec. Если же выбрана основная прошивка, загрузка продолжается как обычно.
По сути, это аналог механизма двойной загрузки, который доступен в настольных ПК. Никаких перезаписей boot-раздела (если одна из прошивок перестанет работать, всегда можно перезагрузить смартфон и выбрать другую), никаких карт памяти, все просто и элегантно. Но даже у этого способа есть две проблемы.
Проблема первая: для корректного обновления основной прошивки нужен специальный recovery, который внедрит в boot-раздел вторичный загрузчик после прошивки обновления. Проблема вторая: дополнительные прошивки до сих пор необходимо модифицировать, то есть изменять файл fstab в их boot-разделах, чтобы они монтировали файловые системы не из разделов NAND-памяти, а из образов, расположенных на карте памяти или в разделе data. К счастью, и та и другая проблемы уже решены.
СПОСОБ НОМЕР 5. MULTIROM
MultiROM — лучшая реализация механизма двойной загрузки из доступных для Android. Система представляет собой реализацию четвертого метода и состоит из трех компонентов: вторичного загрузчика, модифицированного recovery, который позволяет правильно обновлять основную прошивку и устанавливать дополнительные ромы, автоматически модифицируя их для работы в режиме dual boot, и специального инсталлятора в виде Android-приложения, который все это устанавливает.
multiroom manager screen
Основной экран MultiROM Manager после установки ядра
  К сожалению, MultiROM доступен только для Nexus 4, 5 и 7 (обе версии планшета), а также в виде неофициальных портов для HTC One, HTC One X, Galaxy S4 и Droid DNA, поэтому будет полезен только для владельцев данных устройств.
multiroom setup screen
Окончание установки компонентов MultiROM
В следующем разделе я расскажу о другой реализации механизма dual boot для разных девайсов, а пока рассмотрим, как работает MultiROM и что нужно для его установки. По сути, все, что требуется, уже есть в приложении MultiROM Manager, доступном в Play Store, но я бы порекомендовал заранее позаботиться об установке кастомного ядра с поддержкой kexec. MultiROM может сделать это и самостоятельно, но прошьет далеко не лучший из имеющихся вариантов. А лучший — это franco.Kernel, который можно установить с помощью приложения franco.Kernel Updater из Play Store. Достаточно иметь установленную консоль восстановления TWRP и ClockworkMod — их можно поставить с помощью GooManager. Также следует сразу озаботиться скачиванием и копированием прошивок, которые мы хотим установить, на карту памяти. Подойдет абсолютно любая прошивка для твоего девайса: сток, CyanogenMod, Paranoid
Android, Firefox OS, WebOS…
multiroom ubuntu
Интерфейс установки Ubuntu Touch
Итак, после того как мы обзавелись новым ядром (или не обзавелись) и ZIP-архивами с прошивками, запускаем MultiROM Manager и ждем, пока он проверит наличие своих компонентов в системе. Если ты уже установил ядро, то неустановленными будут только загрузчик MultiROM (первая строка в плашке «Статус установки») и модифицированный recovery (вторая строка). Оба этих компонента можно установить, нажав кнопку «Установить» в плашке «Установка/Обновление» (опции отмечать не надо, приложение уже само поставило нужные галочки).
 Загрузчик MultiROM автоматиче- ски загружает основ- ную прошивку через пять секунд
Загрузчик MultiROM автоматиче-
ски загружает основную прошивку через
пять секунд
После этого приложение отправит девайс в перезагрузку, и при загрузке вместо привычного логотипа прошивки ты увидишь экран загрузчика MultiROM. В списке доступных прошивок будет только одна — Internal. Это основная прошивка, для загрузки которой достаточно тапнуть по ее имени. Однако пока загружать прошивку еще рано и необходимо установить дополнительные прошивки. Для этого открываем вкладку Misc в загрузчике и нажимаем Reboot to Recovery.
Теперь на экране должен появиться TWRP, озаглавленный MultiROM TWRP. Это стандартный TWRP с набором функций для установки и управления дополнительными прошивками.
Все эти функции находятся в разделе Advanced Чтобы установить дополнительную прошивку, переходим в этот раздел и нажимаем Add ROM, появится экран выбора опций: тип прошивки (Android, Ubuntu Touch или MultiROM Installer, это для прошивок в формате MultiROM), шаринг ядра между прошивками (всегда следует выбирать «Нет») и тип памяти для установки (внутренняя или карта памяти). Оставляем все как есть и нажимаем кнопку Next, а далее ZIP
file. Появится стандартный диалог выбора файла с прошивкой. Находим один из ранее скачанных ZIP-файлов с прошивкой, тапаем по нему и соглашаемся с прошивкой с помощью свайпа слева направо. В конце нажимаем Reboot и ждем, пока появится экран загрузчика. Теперь в нем должно быть две строки: Internal и имя второй установленной прошивки. Выбираем второй пункт и смотрим, как работает прошивка. Далее снова перезагружаемся и выбираем Internal.
Все должно работать как часы.
multiroom menu
Вкладка Misc в загрузчике MultiROM
Вернемся к приложению MultiROM Manager. Кроме установки компонентов MultiROM, он также имеет две другие полезные функции. Первая — возможность быстрой установки Ubuntu Touch (последняя плашка на главном экране). Здесь вообще ничего делать не надо, достаточно нажать «Установить», и приложение само выкачает последнюю версию Ubuntu из Сети и установит ее второй системой. Вторая — возможность переключаться на другую прошивку без необходимости самостоятельно перезагружать смартфон и выбирать ее в загрузчике. Просто открываем вкладку «Управл. прошивками», тапаем по нужному пункту и соглашаемся с перезагрузкой. Все просто и удобно.
MultiROM полностью совместим с системами OTA-обновления стоковых и кастомных прошивок. Обновлять по воздуху можно любые установленные прошивки, система сама позаботится об их модификации для работы в режиме dual boot (если речь идет об обновлении дополнительных прошивок) и модифицирует boot-раздел для внедрения вторичного загрузчика (если происходит обновление основной прошивки).
ДРУГИЕ РЕШЕНИЯ
MultiROM — единственное верное и доведенное до ума решение для организации режима dual boot из всех, что я смог найти. Однако это не значит, что других решений не существует вовсе. Они есть, но в большинстве своем представляют собой длинные инструкции, опубликованные на разных форумах, в результате исполнения которых ты получишь механизм двойной (тройной и так далее) загрузки, реализованный по принципу второго метода из начала данной статьи.

Некоторое время назад был популярен проект RomSwitcher, реализующий третий способ двойной загрузки, но, похоже, он окончательно умер, оставив после себя лишь устаревшие порты на несколько разных устройств. В том или ином виде от разных разработчиков он доступен для Galaxy S4 (goo.gl/dJezwu), HTC One (goo.gl/HSZabp), Xperia Z (goo.gl/wYEJi1) и Xperia ZL (goo.gl/jCVz3Z). Других сколько-нибудь внятных готовых решений мне найти, к сожалению, не удалось.

Комментариев нет:

Отправить комментарий