RPI3: 在树莓派3上运行ANDROID 8.1系统

Android 官方并没有提供可运行在树莓派3上的Android系统,而只提供了AndroidThings系统,并且还只是preview的版本。想在树莓派上运行Android 8.1系统,就需要自己动手修改。

幸好官方提供了AndroidThings preview 6的系统,这使得让树莓派3运行Android 8.1系统难度大大降低。

  • 准备工作

1. 官方提供的AndroidThing preview 6的镜像

2. Ubuntu 14.04系统,用于编译Android系统

3. Android 8.1源代码,这里使用的版本为android-8.1.0_r2, 源代码可以从(https://lug.ustc.edu.cn/wiki/mirrors/help/aosp)下载

  • 提取文件

这里我需要从AndroidThings preview 6中提取整个分区及system分区中的部份文件

用如下命令将镜像文件进行拆分:

#! /bin/bash

mkdir -v SPLIT

sgdisk -p iot_rpi3.img | tail -n +10 | while read line
do
	ARRAY=(${line})
	start=${ARRAY[1]}
	end=${ARRAY[2]}
	name=${ARRAY[6]}
	echo "=> START: ${start}, END: ${end}, NAME: ${name}"

	dd if=iot_rpi3.img of=SPLIT/${name}.img skip=${start} bs=512 count=$((${end} - ${start} + 1))
done

我们只需要保留如下分区文件:

boot_a.img  oem_a.img  rpiboot.img  system_a.img  vendor_a.img

从system_a.img中提取如下文件:

.
+-- fstab.rpi3
+-- init.rpi3.rc
+-- system
|   +-- bin
|   |   `-- surfaceflinger
|   `-- lib
|       +-- android.frameworks.displayservice@1.0.so
|       +-- android.frameworks.vr.composer@1.0.so
|       +-- android.hardware.boot@1.0.so
|       +-- android.hardware.configstore@1.0.so
|       +-- android.hardware.configstore-utils.so
|       +-- android.hardware.graphics.allocator@2.0.so
|       +-- android.hardware.graphics.bufferqueue@1.0.so
|       +-- android.hardware.graphics.common@1.0.so
|       +-- android.hardware.graphics.composer@2.1.so
|       +-- android.hardware.graphics.mapper@2.0.so
|       +-- android.hardware.media@1.0.so
|       +-- android.hardware.power@1.0.so
|       +-- android.hardware.usb@1.0.so
|       +-- android.hardware.wifi@1.0.so
|       +-- android.hardware.wifi@1.1.so
|       +-- android.hardware.wifi.supplicant@1.0.so
|       +-- android.hidl.token@1.0.so
|       +-- android.hidl.token@1.0-utils.so
|       +-- hw
|       |   +-- android.hidl.memory@1.0-impl.so
|       |   +-- audio.a2dp.default.so
|       |   +-- audio.primary.rpi3.so
|       |   +-- bluetooth.default.so
|       |   +-- bootctrl.bcb.so
|       |   +-- bootctrl.default.so -> bootctrl.bcb.so
|       |   +-- camera.v4l2.so
|       |   +-- gps.iot.so
|       |   +-- gralloc.rpi3.so
|       |   +-- keystore.default.so
|       |   +-- lights.rpi3.so
|       |   +-- memtrack.dummy.so
|       |   +-- peripheral_io.rpi3.so
|       |   `-- sensors.iot.so
|       `-- libsurfaceflinger.so
`-- ueventd.rpi3.rc
  • 从源代码开始编译Android系统

android-8.1.0_r2的代码从这里下载:https://lug.ustc.edu.cn/wiki/mirrors/help/aosp

设备相关的文件可以从这里下载:O-8.1.0_r2-rpi3b_device_brobwind_rpi3.tar.gz

文件结构如下:

O-8.1.0_r2-rpi3b/
`-- device
    `-- brobwind
        `-- rpi3
            +-- AndroidProducts.mk
            +-- BoardConfig.mk
            +-- init.mini-emulator.rc
            +-- mini_emulator_common.mk
            +-- overlay
            |   `-- frameworks
            |       `-- base
            |           `-- core
            |               `-- res
            |                   `-- res
            |                       `-- values
            |                           `-- config.xml
            +-- root
            |   +-- fstab.rpi3
            |   +-- init.rpi3.rc
            |   +-- system
            |   |   +-- bin
            |   |   |   `-- surfaceflinger
            |   |   `-- lib
            |   |       +-- android.frameworks.displayservice@1.0.so
            |   |       +-- android.frameworks.vr.composer@1.0.so
            |   |       +-- android.hardware.boot@1.0.so
            |   |       +-- android.hardware.configstore@1.0.so
            |   |       +-- android.hardware.configstore-utils.so
            |   |       +-- android.hardware.graphics.allocator@2.0.so
            |   |       +-- android.hardware.graphics.bufferqueue@1.0.so
            |   |       +-- android.hardware.graphics.common@1.0.so
            |   |       +-- android.hardware.graphics.composer@2.1.so
            |   |       +-- android.hardware.graphics.mapper@2.0.so
            |   |       +-- android.hardware.media@1.0.so
            |   |       +-- android.hardware.power@1.0.so
            |   |       +-- android.hardware.usb@1.0.so
            |   |       +-- android.hardware.wifi@1.0.so
            |   |       +-- android.hardware.wifi@1.1.so
            |   |       +-- android.hardware.wifi.supplicant@1.0.so
            |   |       +-- android.hidl.token@1.0.so
            |   |       +-- android.hidl.token@1.0-utils.so
            |   |       +-- hw
            |   |       |   +-- android.hidl.memory@1.0-impl.so
            |   |       |   +-- audio.a2dp.default.so
            |   |       |   +-- audio.primary.rpi3.so
            |   |       |   +-- bluetooth.default.so
            |   |       |   +-- bootctrl.bcb.so
            |   |       |   +-- bootctrl.default.so -> bootctrl.bcb.so
            |   |       |   +-- camera.v4l2.so
            |   |       |   +-- gps.iot.so
            |   |       |   +-- gralloc.rpi3.so
            |   |       |   +-- keystore.default.so
            |   |       |   +-- lights.rpi3.so
            |   |       |   +-- memtrack.dummy.so
            |   |       |   +-- peripheral_io.rpi3.so
            |   |       |   `-- sensors.iot.so
            |   |       `-- libsurfaceflinger.so
            |   `-- ueventd.rpi3.rc
            +-- rpi3.mk
            +-- system.prop
            +-- vendor.img
            `-- vendorsetup.sh

编译完成之后,我们只需要最终生成的system img.

  • 创建开机磁盘镜像

将上一步骤生成的system image替换掉SPLIT目录下的system_a.img, 然后执行如下脚本生成我们所需的磁盘镜像:

#! /bin/bash

#Disk iot_rpi3.img: 8912896 sectors, 4.2 GiB
#Logical sector size: 512 bytes
#Disk identifier (GUID): B4E0B8F7-2781-4463-B8F6-C5E9739823BC
#Partition table holds up to 128 entries
#First usable sector is 34, last usable sector is 8912862
#Partitions will be aligned on 8-sector boundaries
#Total free space is 13 sectors (6.5 KiB)
#
#Number  Start (sector)    End (sector)  Size       Code  Name
#   1              40          131111   64.0 MiB    FFFF  rpiboot
#   2          131112          133159   1024.0 KiB  FFFF  uboot_a
#   3          133160          135207   1024.0 KiB  FFFF  uboot_b
#   4          135208          200743   32.0 MiB    FFFF  boot_a
#   5          200744          266279   32.0 MiB    FFFF  boot_b
#   6          266280         1314855   512.0 MiB   FFFF  system_a
#   7         1314856         2363431   512.0 MiB   FFFF  system_b
#   8         2363432         2363559   64.0 KiB    FFFF  vbmeta_a
#   9         2363560         2363687   64.0 KiB    FFFF  vbmeta_b
#  10         2363688         2365735   1024.0 KiB  FFFF  misc
#  11         2365736         2496807   64.0 MiB    FFFF  vendor_a
#  12         2496808         2627879   64.0 MiB    FFFF  vendor_b
#  13         2627880         4086055   712.0 MiB   FFFF  oem_a
#  14         4086056         5544231   712.0 MiB   FFFF  oem_b
#  15         5544232         5552423   4.0 MiB     FFFF  oem_bootloader_a
#  16         5552424         5560615   4.0 MiB     FFFF  oem_bootloader_b
#  17         5560616         5626151   32.0 MiB    FFFF  factory
#  18         5626152         5658919   16.0 MiB    FFFF  factory_bootloader
#  19         5658920         8912847   1.6 GiB     FFFF  userdata
#  20         8912848         8912855   4.0 KiB     FFFF  gapps

#SGDISK=/data/O-8.1.0_r2-rpi3b/out/host/linux-x86/bin/sgdisk
SGDISK=sgdisk
GDISK=gdisk
DD=dd

source=iot_rpi3.img
target=iot.img

DINFO="`${SGDISK} --print ${source}`"

sectors=`echo "${DINFO}" | head -n 1 | sed 's/.*:[[:space:]]*\([[:digit:]]\+\).*/\1/g'`
sector_size=`echo "${DINFO}" | head -n 2 | tail -n 1 | sed 's/.*:[[:space:]]*\([[:digit:]]\+\).*/\1/g'`


if [ ! -f ${target} ] ; then
    dd if=/dev/zero of=${target} bs=${sector_size} count=${sectors}
fi

echo " => Clear partition table ..."

${SGDISK} --clear ${target}


echo " => Install GPT partition table ..."

${SGDISK} --set-alignment=1 $(echo "${DINFO}" | tail -n +10 | while read line
do
    ARRAY=(${line})
    num=${ARRAY[0]}
    start=${ARRAY[1]}
    end=${ARRAY[2]}
    label=${ARRAY[6]}
    uuid=`${SGDISK} --info ${num} ${source} | head -n 1 | sed 's/.*: \([0-9A-Z-]\+\).*/\1/g'`

    echo "--new=${num}:${start}:${end} --typecode=${num}:${uuid} --change-name=${num}:${label}"

done) ${target}


echo " => Install hybrid MBR partitoin table ..."

${GDISK} << EOF ${target}
r
h
1
N
06
N
N
w
Y
EOF

echo " => Install images ...."

echo "${DINFO}" | tail -n +10 | while read line
do
    ARRAY=(${line})
    start=${ARRAY[1]}
    end=${ARRAY[2]}
    label=${ARRAY[6]}

    if [ -f SPLIT/${label}.img ] ; then
        echo "     => Install: ${label} images ..."
        ${DD} if=SPLIT/${label}.img of=${target} conv=notrunc bs=${sector_size} count=$((${end} - ${start} + 1)) seek=${start}
    fi
done

最终会在当前目录下生成iot.img文件。

  • 写入磁盘镜像文件

将iot.img文件写入到TF卡中,可通过dd命令

 

 

《RPI3: 在树莓派3上运行ANDROID 8.1系统》有6个想法

  1. 当我在16G的内存卡里刷入androidthings iot-rpi3.img文件后 出现有10G左右未分配内存的情况 我应该怎么利用未分配空间呢

发表评论

电子邮件地址不会被公开。 必填项已用*标注