【OPTEE开发】从TA到安全驱动的功能设计

一、功能需求

实现普通TA通过系统调用到增加的Driver侧功能,实现完整的通路。
功能:在TA中通过系统调用安全驱动中的write和read功能,增加rot service系统服务,封装libutee对TA提供的对外接口,实现完整的通路功能。

本篇主要是通过增加这个功能,来加深对TA调用通路的理解,当然也可以不采用此通路设计,可以直接设计成TA调用PTA完成基本功能。

原创不易,转载请注明出处:https://blog.csdn.net/jackone12347/article/details/122487418

二、TA到Driver层的架构

1. 软件层架构

在这里插入图片描述

2. 实现思路

为了实现这个功能,需要完成如下几个子模块的设计和实现。

2.3 封装libutee层系统API

在libutee中增加对TA调用的系统接口,方便普通的TA通过libutee库进行调用。

2.2 core中增加系统服务层

libutee中的接口封装OK后,需要在core serivce中增加自己的service,衔接libutee到 driver的功能。
增加的service本身也可以init初始化一些自己的基本功能,类似android的Framework中的serivce。
同时,可以增加core service有一个好处是将driver侧的实现细节屏蔽掉,只提供一个对外的接口。

2.1 Driver侧接口和实现

driver侧的功能用途:一般driver侧用来初始化一些私有的数据和操作安全设备。
我们这里增加rot的write和read功能。

三、详细实现

下面是详细的设计实现。

1. 修改清单

下面是所有的涉及到的文件修改列表:
在这里插入图片描述
对应的git修改列表:

        modified:   core/arch/arm/tee/arch_svc.c
        modified:   core/drivers/sub.mk
        modified:   core/tee/sub.mk
        modified:   lib/libutee/arch/arm/utee_syscalls_asm.S
        modified:   lib/libutee/include/tee_api.h
        modified:   lib/libutee/include/tee_syscall_numbers.h
        modified:   lib/libutee/include/utee_syscalls.h
        modified:   lib/libutee/tee_api.c
        modified:   mk/config.mk

        core/drivers/driver_rot.c
        core/include/drivers/driver_rot.h
        core/include/tee/tee_rot.h
        core/tee/tee_rot.c

2. 详细设计

2.1 libutee对外接口设计

这里直接修改原始的tee_api.h,当然也可以不这么设计,可以直接添加和libutee同级别的lib库也是可以的。

TA调用接口:\lib\libutee\include\tee_api.h中增加三个调用接口:

TEE_Result Tee_Rot_Write(void *buf, size_t blen, size_t offset);

TEE_Result Tee_Rot_Read(void *buf, size_t blen, size_t offset);

TEE_Result Tee_Rot_Dump(void *buf, size_t blen);

三个接口实现:optee_os\lib\libutee\tee_api.c


TEE_Result Tee_Rot_Write(void *buf, size_t blen, size_t offset)
{
	TEE_Result res = TEE_SUCCESS;

	res = _utee_rot_driver_write(buf, blen, offset);

	return res;
}

TEE_Result Tee_Rot_Read(void *buf, size_t blen, size_t offset)
{
	TEE_Result res = TEE_SUCCESS;

	res = _utee_rot_driver_read(buf, blen, offset);

	return res;
}

TEE_Result Tee_Rot_Dump(void *buf, size_t blen)
{
	TEE_Result res = TEE_SUCCESS;
	
	res = _utee_rot_driver_dump(buf, blen);
	
	return res;
}

其中_utee_rot_driver_write、_utee_rot_driver_read、_utee_rot_driver_dump需要在core中继续封装和实现,tee_rot的封装如下:
@core/include/tee/tee_rot.h


#include <drivers/driver_rot.h>

struct rot_service_ops {
    const char* name;
    struct rot_driver_ops_s rot_driver;
};

extern TEE_Result syscall_rot_driver_write(void *buf, size_t blen, size_t offset);
extern TEE_Result syscall_rot_driver_read(void *buf, size_t blen, size_t offset);
extern TEE_Result syscall_rot_driver_dump(void *buf, size_t blen);

@core/tee/tee_rot.c实现如下:

#include <drivers/driver_rot.h>
#include <tee/tee_rot.h>
#include <tee/tee_svc.h>
#include <trace.h>

TEE_Result syscall_rot_driver_write(void *buf, size_t blen, size_t offset);
TEE_Result syscall_rot_driver_read(void *buf, size_t blen, size_t offset);
TEE_Result syscall_rot_driver_dump(void *buf, size_t blen);

struct rot_service_ops rot_ops = {
    .name = "RotDriver",
	.rot_driver = {
        .device_init = device_init,
        .write_rot = write_rot,
        .read_rot = read_rot,
        .driver_dump = driver_dump,
	},
};


TEE_Result syscall_rot_driver_write(void *buf, size_t blen, size_t offset)
{
    uint8_t* src = NULL;
	DMSG("pis syscall_rot_driver_write entry.\n");
    src = malloc(blen);

	memcpy(src, buf, blen);
    rot_ops.rot_driver.write_rot(src, blen, offset);
    free(src);
   
    return TEE_SUCCESS;
}


TEE_Result syscall_rot_driver_read(void *buf, size_t blen, size_t offset)
{
    uint8_t* dst = NULL;
	
	DMSG("pis syscall_rot_driver_read entry.\n");
    dst = malloc(blen);
    rot_ops.rot_driver.read_rot(dst, blen, offset);

	memcpy(buf, dst, blen);

    free(dst);
    return TEE_SUCCESS;

}

TEE_Result syscall_rot_driver_dump(void *buf, size_t blen)
{
    uint8_t* dst = NULL;
    dst = malloc(blen);
    rot_ops.rot_driver.driver_dump(dst, blen);

	memcpy(buf, dst, blen);

    free(dst);
    return TEE_SUCCESS;
}


static TEE_Result tee_rot_init(void)
{
    DMSG("Strat to start rot servie\n");
	if (rot_ops.rot_driver.device_init)
		rot_ops.rot_driver.device_init();
    DMSG("rot servcie initial is ok\n");
	return TEE_SUCCESS;
}

service_init(tee_rot_init);

这里有两个地方需要重要注意:
rot_service_ops是core serivce中定义的结构体,而rot_driver_ops_s是driver对外的结构体;
service_init(tee_rot_init)是我们新的rot service的初始化的地方。

2.2 core服务设计

core service一般在OPTEE的initcall段的代码启动和初始化。
所以,这里我们增加两个文件,tee_rot.h和tee_rot.c文件,起到承上启下的作用。

在2.1章节中调用了_utee_rot_driver_write等函数,普通TA是运行在用户空间,不能直接调用到core service侧,需要syscall转化一下。
所以,先增加syscall通路,列表如下:

    modified:   lib/libutee/include/utee_syscalls.h
    modified:   lib/libutee/arch/arm/utee_syscalls_asm.S
    modified:   core/arch/arm/tee/arch_svc.c
    modified:   lib/libutee/include/tee_syscall_numbers.h

内容分别如下:
@lib/libutee/include/utee_syscalls.h

	TEE_Result _utee_rot_driver_write(uint8_t *data, size_t len, size_t offset);
	TEE_Result _utee_rot_driver_read(uint8_t *dst, size_t len, size_t offset);
	TEE_Result _utee_rot_driver_dump(void *buf, size_t blen);

@lib/libutee/arch/arm/utee_syscalls_asm.S,第三个参数表示参数的个数。

    UTEE_SYSCALL _utee_rot_driver_write, TEE_SCN_ROT_DRIVER_WRITE, 3
    UTEE_SYSCALL _utee_rot_driver_read, TEE_SCN_ROT_DRIVER_READ, 3
    UTEE_SYSCALL _utee_rot_driver_dump, TEE_SCN_ROT_DRIVER_DUMP, 2

@core/arch/arm/tee/arch_svc.c,增加三个syscall函数

static const struct syscall_entry tee_svc_syscall_table[] = {
...
	SYSCALL_ENTRY(syscall_rot_driver_write),
	SYSCALL_ENTRY(syscall_rot_driver_read),
	SYSCALL_ENTRY(syscall_rot_driver_dump),
}

@lib/libutee/include/tee_syscall_numbers.h 增加三个syscall,MAX修改为73

#define TEE_SCN_ROT_DRIVER_WRITE        71
#define TEE_SCN_ROT_DRIVER_READ         72
#define TEE_SCN_ROT_DRIVER_DUMP         73
#define TEE_SCN_MAX				73

2.3 Driver驱动侧设计

最后再增加driver侧的实现

    core/drivers/driver_rot.c
    core/include/drivers/driver_rot.h

头文件的定义:
@core/include/drivers/driver_rot.h

#ifndef MOUDLE_ROT_DRIVER_H_
#define MOUDLE_ROT_DRIVER_H_

#include <assert.h>
#include <stdlib.h>
#include <string.h>
#include <utee_defines.h>
#include <trace.h>
#include <tee_api_types.h>
#include <string_ext.h>
#include <util.h>
#include <kernel/panic.h>

struct rot_driver_ops_s {
    TEE_Result (*device_init)(void);
    TEE_Result (*write_rot)(uint8_t *data, size_t len, size_t offset);
    TEE_Result (*read_rot)(uint8_t *dst, size_t len, size_t offset);
    TEE_Result (*driver_dump)(uint8_t *data, size_t len);
};


#ifndef MOUDLE_ROT_DRIVER_C_

extern TEE_Result device_init(void);
extern TEE_Result write_rot(uint8_t *data, size_t len, size_t offset);
extern TEE_Result read_rot(uint8_t *dst, size_t len, size_t offset);
extern TEE_Result driver_dump(uint8_t *data, size_t len);


#endif
#endif  /* MOUDLE_ROT_DRIVER_H_*/

syscall_rot_driver_write是core serivce中对应的,这样TA -》core serivce -> TA driver就完整的实现了通路。

下面是driver_rot.c的实现的完整代码:
@core/drivers/driver_rot.c

#define MOUDLE_ROT_DRIVER_C_

#include <assert.h>
#include <stdlib.h>
#include <string.h>
#include <utee_defines.h>
#include <trace.h>
#include <tee_api_types.h>
#include <string_ext.h>
#include <util.h>
#include <kernel/panic.h>
#include <kernel/thread.h>
#include <kernel/thread_spmc.h>
#include <tee/tee_svc.h>
#include <trace.h>

TEE_Result device_init(void);
TEE_Result write_rot(uint8_t *data, size_t len, size_t offset);
TEE_Result read_rot(uint8_t *dst, size_t len, size_t offset);
TEE_Result driver_dump(uint8_t *data, size_t len);

uint8_t g_buffer[64] = {0};

TEE_Result device_init(void)
{
    DMSG("pis driver device rot init.\n");
    memset(g_buffer, 0, 64);
    return TEE_SUCCESS;
}

TEE_Result write_rot(uint8_t *data, size_t len, size_t offset)
{
    DMSG("pis driver write rot entry ====\n");

	memset(g_buffer, 0, 64);
    memcpy(&(g_buffer[offset]), data, len);

	size_t j = 0;
	for(; j < len; j++)
	{
		DMSG("pis driver write_rot:0x%x\n", g_buffer[j]);
	}

	DMSG("pis driver write rot done ==== \n");

    return TEE_SUCCESS;
}

TEE_Result read_rot(uint8_t *dst, size_t len, size_t offset)
{
    DMSG("pis driver read rot entry ====\n");

    memcpy(dst, &(g_buffer[offset]), len);

	size_t i = 0;
	for(; i < len; i++)
	{
		DMSG("pis driver read_rot:0x%x\n", dst[i]);
	}

	DMSG("pis driver read rot done.\n");
    return TEE_SUCCESS;
}

TEE_Result driver_dump(uint8_t *data, size_t len)
{
    DMSG("pis driver rot dump.\n");
    memcpy(data, &(g_buffer[0]), len);

    return TEE_SUCCESS;
}

2.4 TA应用侧实现

有了以上三个部分的实现后,TA中的调用就比较简单了,就可以和普通的lib库一样调用即可。
比起TA通过openTAsession等函数方便多了~~~

测试代码如下,实现了写入和读取数据,数据是存在driver中的全局变量。

#include <tee_internal_api.h>
#include <tee_internal_api_extensions.h>
#include <tee_api_types.h>

TEE_Result get_rot_data()
{
	TEE_Result res = TEE_SUCCESS;

	DMSG("pis 1 get_rot_data entry. \n");
	res = Tee_Rot_Write((void *)"aaaabbbbccccdddd1111222233334444aaaabbbbccccdddd1111222233334444", 64, 0);
	DMSG ("pis 22 Tee_Rot_Write result:%d", res);

	uint8_t *temp = NULL;
	temp = malloc(65);

	res = Tee_Rot_Read(temp, 64, 0);
	DMSG ("pis 1 Tee_Rot_Read result:%d", res);
	int i = 0;
	for(; i < 64; i++) {
		DMSG ("pis Tee_Rot_Read content:0x%x", temp[i]);
	}

	free(temp);

	DMSG("pis 1 get_rot_data done. \n");

	return res;
}

运行结果:
rot service在OPTEE启动的时候的打印,可以看到rot service正常启动和init初始化了。

D/TC:4 0 call_initcalls:21 level 3 tee_rot_init()
D/TC:4 0 tee_rot_init:76 Strat to start rot servie
D/TC:4 0 device_init:29 pis driver device rot init.
D/TC:4 0 tee_rot_init:79 rot servcie initial is ok

写ROT数据:

D/TA:  get_rot_data:1514 pis get_rot_data entry.
F/TC:? 0 trace_syscall:155 syscall #71 (syscall_rot_driver_write)
D/TC:? 0 syscall_rot_driver_write:35 pis syscall_rot_driver_write entry.
D/TC:? 0 write_rot:36 pis driver write rot entry ====
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x61
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x62
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x63
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x64
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x31
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x32
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x33
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:44 pis driver write_rot:0x34
D/TC:? 0 write_rot:65 pis driver write rot done ====
D/TA:  get_rot_data:1518 pis Tee_Rot_Write result:0

再读取ROT数据

F/TC:? 0 trace_syscall:155 syscall #72 (syscall_rot_driver_read)
D/TC:? 0 syscall_rot_driver_read:50 pis syscall_rot_driver_read entry.
D/TC:? 0 read_rot:72 pis driver read rot entry ====
D/TC:? 0 read_rot:82 pis driver read rot done.
D/TA:  get_rot_data:1524 pis 1 Tee_Rot_Read result:0
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x61
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x62
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x63
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x64
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x31
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x32
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x33
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1527 pis Tee_Rot_Read content:0x34
D/TA:  get_rot_data:1532 pis 1 get_rot_data done.

为方便与大家及时交流,弄了一个微信公众号,欢迎大家留言沟通~
在这里插入图片描述

  • 4
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值