optee各组件支持32位系统

发布时间 2023-09-08 09:49:13作者: xiululu

问题:

export USE_A32=true之后编译32位安卓版本时,出现无法开机问题。

现象表现在手机卡在开机LOGO界面,从log看是optee keymaster 3.0 start失败导致的。

库上的optee方案集成思路:

conf.mk的默认配置为:ta-targets := ta_arm64

toolchain用了64位的。

aosp版本,optee的组件采用闭源方式。

REE侧的service和tee-supplicant,是通过mma编译完了之后,将生成物搜集到一起,同时生成一个Android.mk,通过prebuilt的方式将这些组件集成到vendor.img中。

梳理:

prebuilt生成物的搜集过程,默认是在64bit配置下编译的。

在32bit的out目录下,通过file命令,如optee-keymaster,optee-gatekeeper等文件(vendor/bin/hw下面),都是32bit。

产品要求在默认64bit的配置下,能同时生成64位和32位的prebuilt组件。

解决过程:

通过拉取源码,在aosp代码下,export USE_A32=true之后编译的32位版本,烧写之后开机成功。

REE侧的几个bin,包括gatekeeper,keymaster和wait-for-keymaster这3个组件,增加LOCAL_MULTILIB的配置,确保32位和64位生成物生成。

同时修改搜集生成物的脚本,形成配套的Android.mk。

开机之后,发现还是无法启动。

串口log看还是在init时keymaster服务一直无法启动。

这时,通过ps -A |grep tee-supplicant,发现该服务没有启动。

串口log中显示supplicant服务启动异常log。

4017 01-02 02:57:57.987     0     0 I init    : processing action (fs) from (/vendor/etc/init/tee-supplicant.rc:6)
4018 01-02 02:57:58.039     0     0 I init    : starting service 'tee-supplicant'...
4019 01-02 02:57:58.050     0     0 E init    : cannot execv('/vendor/bin/tee-supplicant'). See the 'Debugging init' section of init's README.md for tips: No such file or directory
4023 01-02 02:57:58.099     0     0 I init    : Service 'tee-supplicant' (pid 322) exited with status 127
4024 01-02 02:57:58.106     0     0 I init    : Sending signal 9 to service 'tee-supplicant' (pid 322) process group...

于是同步修改了tee-supplicant的mk和release组件过程,让tee-supplicant也同时支持LOCAL_MULTILIB:=both配置。

修改后编译启动成功。

修改点示例:

以gatekeeper为例。

Android.mk:

黄色部分是新增的。

include $(CLEAR_VARS)

LOCAL_MODULE := android.hardware.gatekeeper@1.0-service.optee
LOCAL_INIT_RC := android.hardware.gatekeeper@1.0-service.optee.rc
LOCAL_MODULE_RELATIVE_PATH := hw
LOCAL_MODULE_TAGS := optional
LOCAL_VENDOR_MODULE := true
LOCAL_VINTF_FRAGMENTS := android.hardware.gatekeeper@1.0-service.optee.xml
LOCAL_OVERRIDES_MODULES := android.hardware.gatekeeper@1.0-service.software

LOCAL_CFLAGS = -Wall -Werror
LOCAL_CFLAGS += -DANDROID_BUILD

LOCAL_SRC_FILES := \
    service.cpp \
    optee_gatekeeper_device.cpp \
    optee_ipc.cpp

LOCAL_C_INCLUDES := \
    $(LOCAL_PATH)/ta/include
LOCAL_C_INCLUDES += $(LOCAL_PATH)/../../optee_client/include

LOCAL_SHARED_LIBRARIES := \
    liblog \
    libcutils \
    libteec \
    libhardware \
    libhidlbase \
    libhidltransport \
    libutils \
    android.hardware.gatekeeper@1.0

#LOCAL_MULTILIB := 64

LOCAL_MULTILIB := both
LOCAL_MODULE_STEM_32 := $(LOCAL_MODULE)32
LOCAL_MODULE_STEM_64 := $(LOCAL_MODULE)64
include $(BUILD_EXECUTABLE)

搜集生成物的脚本:

#!/bin/bash

usage () {
cat <<USAGE
    copy releaseed files from outbin_dir to dstdir
    usage:$(basename $0) dst_dir outbin_dir [system|vendor]
USAGE
}

if [ $# -eq 0 ]; then
    usage
    exit
fi

DST=$1/gatekeeper

PART=$3

if [ "NULL$PART" = "NULL" ]; then
    PART=vendor
fi

BINDIR=$2/$PART

if [ -e $DST ]; then
    echo "error: $DST exist! DO NOTHING!!!!"
    exit -1
fi

binlist=(
etc/init/android.hardware.gatekeeper@1.0-service.optee.rc
-bin/hw/android.hardware.gatekeeper@1.0-service.optee
+bin/hw/android.hardware.gatekeeper@1.0-service.optee32
+bin/hw/android.hardware.gatekeeper@1.0-service.optee64
lib/optee_armtz/4d573443-6a56-4272-ac6f-2425af9ef9bb.ta
etc/vintf/manifest/android.hardware.gatekeeper@1.0-service.optee.xml
)
include \$(CLEAR_VARS)
LOCAL_VENDOR_MODULE := true
LOCAL_MODULE := android.hardware.gatekeeper@1.0-service.optee
-LOCAL_SRC_FILES:= android.hardware.gatekeeper@1.0-service.optee
LOCAL_MODULE_RELATIVE_PATH := hw
LOCAL_MODULE_TAGS := optional
LOCAL_MODULE_CLASS := EXECUTABLES
LOCAL_INIT_RC := android.hardware.gatekeeper@1.0-service.optee.rc
LOCAL_VINTF_FRAGMENTS := android.hardware.gatekeeper@1.0-service.optee.xml
LOCAL_OVERRIDES_MODULES := android.hardware.gatekeeper@1.0-service.software
+LOCAL_MULTILIB := both
+LOCAL_SRC_FILES_32  := \$(LOCAL_MODULE)32
+LOCAL_SRC_FILES_64  := \$(LOCAL_MODULE)64
include \$(BUILD_PREBUILT)

#gatekeeper ta
include \$(CLEAR_VARS)
................
include \$(BUILD_PREBUILT)
AndroidINFO
}

echo "cp binary files"
mkdir -p $DST
for file in ${binlist[@]}; do
    echo "cp $file $DST/$(dirname $file)"
    if [ ! -e $BINDIR/$file ];then
        echo "error: $BINDIR/$file NOT EXIST!!!"
        exit -2
    fi
    cp $BINDIR/$file $DST/
done