This is an automated email from the ASF dual-hosted git repository. xiaoxiang pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/nuttx-apps.git
commit 7b383d05625de11f4d8173252e37920aa905d423 Author: George Poulios <gpoul...@census-labs.com> AuthorDate: Sun May 11 02:06:01 2025 +0300 examples/optee_gp: Add a OP-TEE GP API client example Add an example app that opens a session with the devices pseudo-TA and enumerates the available devices (prints their UUIDs only) using the GlobalPlatform API and libteec. The example showcases: - initializing the context - opening a session - invoking a command using NULL references - invoking a command using temp shared memory - invoking a command using registered shared memory - closing the session - finalizing the context Enabled with CONFIG_EXAMPLES_OPTEE_GP. Signed-off-by: George Poulios <gpoul...@census-labs.com> --- examples/optee_gp/CMakeLists.txt | 33 +++++++ examples/optee_gp/Kconfig | 30 ++++++ examples/optee_gp/Make.defs | 25 +++++ examples/optee_gp/Makefile | 34 +++++++ examples/optee_gp/optee_gp_main.c | 190 ++++++++++++++++++++++++++++++++++++++ 5 files changed, 312 insertions(+) diff --git a/examples/optee_gp/CMakeLists.txt b/examples/optee_gp/CMakeLists.txt new file mode 100644 index 000000000..3e4d16f87 --- /dev/null +++ b/examples/optee_gp/CMakeLists.txt @@ -0,0 +1,33 @@ +# ############################################################################## +# apps/examples/optee_gp/CMakeLists.txt +# +# SPDX-License-Identifier: Apache-2.0 +# +# Licensed to the Apache Software Foundation (ASF) under one or more contributor +# license agreements. See the NOTICE file distributed with this work for +# additional information regarding copyright ownership. The ASF licenses this +# file to you under the Apache License, Version 2.0 (the "License"); you may not +# use this file except in compliance with the License. You may obtain a copy of +# the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations under +# the License. +# +# ############################################################################## + +if(CONFIG_EXAMPLES_OPTEE_GP) + nuttx_add_application( + NAME + ${CONFIG_EXAMPLES_OPTEE_GP_PROGNAME} + SRCS + optee_gp_main.c + STACKSIZE + ${CONFIG_EXAMPLES_OPTEE_GP_STACKSIZE} + PRIORITY + ${CONFIG_EXAMPLES_OPTEE_GP_PRIORITY}) +endif() diff --git a/examples/optee_gp/Kconfig b/examples/optee_gp/Kconfig new file mode 100644 index 000000000..6a2acc28e --- /dev/null +++ b/examples/optee_gp/Kconfig @@ -0,0 +1,30 @@ +# +# For a description of the syntax of this configuration file, +# see the file kconfig-language.txt in the NuttX tools repository. +# + +config EXAMPLES_OPTEE_GP + tristate "OP-TEE GP API client example" + depends on LIBTEEC + default n + ---help--- + Enable the OP-TEE GP API client example which uses libteec + +if EXAMPLES_OPTEE + +config EXAMPLES_OPTEE_GP_PROGNAME + string "Program name" + default "optee_gp" + ---help--- + This is the name of the program that will be used when the NSH ELF + program is installed. + +config EXAMPLES_OPTEE_GP_PRIORITY + int "OP-TEE GP task priority" + default 100 + +config EXAMPLES_OPTEE_GP_STACKSIZE + int "OP-TEE GP stack size" + default DEFAULT_TASK_STACKSIZE + +endif diff --git a/examples/optee_gp/Make.defs b/examples/optee_gp/Make.defs new file mode 100644 index 000000000..e732a4c5b --- /dev/null +++ b/examples/optee_gp/Make.defs @@ -0,0 +1,25 @@ +############################################################################ +# apps/examples/optee_gp/Make.defs +# +# SPDX-License-Identifier: Apache-2.0 +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. The +# ASF licenses this file to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance with the +# License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +# +############################################################################ + +ifneq ($(CONFIG_EXAMPLES_OPTEE_GP),) +CONFIGURED_APPS += $(APPDIR)/examples/optee_gp +endif diff --git a/examples/optee_gp/Makefile b/examples/optee_gp/Makefile new file mode 100644 index 000000000..02fb022cc --- /dev/null +++ b/examples/optee_gp/Makefile @@ -0,0 +1,34 @@ +############################################################################ +# apps/examples/optee_gp/Makefile +# +# SPDX-License-Identifier: Apache-2.0 +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. The +# ASF licenses this file to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance with the +# License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +# +############################################################################ + +include $(APPDIR)/Make.defs + +# OP-TEE GP API client built-in application info + +PROGNAME = $(CONFIG_EXAMPLES_OPTEE_GP_PROGNAME) +PRIORITY = $(CONFIG_EXAMPLES_OPTEE_GP_PRIORITY) +STACKSIZE = $(CONFIG_EXAMPLES_OPTEE_GP_STACKSIZE) +MODULE = $(CONFIG_EXAMPLES_OPTEE_GP) + +MAINSRC = optee_gp_main.c + +include $(APPDIR)/Application.mk diff --git a/examples/optee_gp/optee_gp_main.c b/examples/optee_gp/optee_gp_main.c new file mode 100644 index 000000000..b88aba694 --- /dev/null +++ b/examples/optee_gp/optee_gp_main.c @@ -0,0 +1,190 @@ +/**************************************************************************** + * apps/examples/optee_gp/optee_gp_main.c + * + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. The + * ASF licenses this file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance with the + * License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + ****************************************************************************/ + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include <nuttx/config.h> +#include <nuttx/tee.h> +#include <tee_client_api.h> +#include <teec_trace.h> +#include <uuid.h> + +/**************************************************************************** + * Pre-processor definitions + ****************************************************************************/ + +/* This UUID is taken from the OP-TEE OS built-in pseudo TA: + * https://github.com/OP-TEE/optee_os/blob/4.6.0/ + * lib/libutee/include/pta_device.h + */ +#define PTA_DEVICE_ENUM_UUID \ + { \ + 0x7011a688, 0xddde, 0x4053, \ + { \ + 0xa5, 0xa9, 0x7b, 0x3c, 0x4d, 0xdf, 0x13, 0xb8 \ + } \ + } + +#define PTA_CMD_GET_DEVICES 0x0 + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * optee_gp_main + ****************************************************************************/ + +int main(int argc, FAR char *argv[]) +{ + TEEC_Result res; + TEEC_Context ctx; + TEEC_Session sess; + TEEC_Operation op; + TEEC_UUID uuid = PTA_DEVICE_ENUM_UUID; + void *buf; + TEEC_SharedMemory io_shm; + uint32_t err_origin; + unsigned int count; + const uuid_t *raw_ta_uuid; + uuid_t ta_uuid; + char *ta_uuid_s; + + res = TEEC_InitializeContext(NULL, &ctx); + if (res != TEEC_SUCCESS) + { + EMSG("TEEC_InitializeContext failed with code 0x%08x\n", res); + goto exit; + } + + memset(&op, 0, sizeof(op)); + + /* Open a session with the devices pseudo TA */ + + res = TEEC_OpenSession(&ctx, &sess, &uuid, TEEC_LOGIN_PUBLIC, NULL, + &op, &err_origin); + if (res != TEEC_SUCCESS) + { + EMSG("TEEC_Opensession failed with code 0x%08x origin 0x%08x", res, + err_origin); + goto exit_with_ctx; + } + + /* Invoke command with NULL buffer to get required size */ + + op.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_TEMP_OUTPUT, TEEC_NONE, + TEEC_NONE, TEEC_NONE); + op.params[0].tmpref.buffer = NULL; + op.params[0].tmpref.size = 0; + + res = TEEC_InvokeCommand(&sess, PTA_CMD_GET_DEVICES, &op, &err_origin); + if (err_origin != TEEC_ORIGIN_TRUSTED_APP || + res != TEEC_ERROR_SHORT_BUFFER) + { + EMSG("TEEC_InvokeCommand failed: code 0x%08x origin 0x%08x", + res, err_origin); + goto exit_with_session; + } + + /* Invoke command using temporary memory */ + + op.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_TEMP_OUTPUT, TEEC_NONE, + TEEC_NONE, TEEC_NONE); + + op.params[0].tmpref.buffer = buf = malloc(op.params[0].tmpref.size); + if (!op.params[0].tmpref.buffer) + { + EMSG("Failed to allocate %zu bytes of memory to share with TEE", + op.params[0].tmpref.size); + goto exit_with_session; + } + + res = TEEC_InvokeCommand(&sess, PTA_CMD_GET_DEVICES, &op, &err_origin); + if (res != TEEC_SUCCESS) + { + EMSG("TEEC_InvokeCommand failed: code 0x%08x origin 0x%08x", + res, err_origin); + goto exit_with_buf; + } + + /* Invoke command using pre-allocated, pre-registered memory */ + + io_shm.size = op.params[0].tmpref.size; + io_shm.flags = TEEC_MEM_OUTPUT; + res = TEEC_AllocateSharedMemory(&ctx, &io_shm); + if (res != TEEC_SUCCESS) + { + EMSG("TEEC_AllocateSharedMemory failed: code 0x%08x", res); + goto exit_with_buf; + } + + op.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_WHOLE, TEEC_NONE, TEEC_NONE, + TEEC_NONE); + op.params[0].memref.parent = &io_shm; + + res = TEEC_InvokeCommand(&sess, PTA_CMD_GET_DEVICES, &op, &err_origin); + if (res != TEEC_SUCCESS) + { + EMSG("TEEC_InvokeCommand failed: code 0x%08x origin 0x%08x", + res, err_origin); + goto exit_with_shm; + } + + /* Sanity check that both outputs are the same */ + + if (memcmp(buf, io_shm.buffer, io_shm.size)) + { + EMSG("Different results with temp vs registered memory"); + goto exit_with_shm; + } + + /* Print results to stdout */ + + IMSG("Available devices:"); + + count = io_shm.size / sizeof(uuid_t); + raw_ta_uuid = (uuid_t *)io_shm.buffer; + + while (count--) + { + uuid_dec_be(raw_ta_uuid, &ta_uuid); + uuid_to_string(&ta_uuid, &ta_uuid_s, NULL); + + IMSG(" %s", ta_uuid_s); + + free(ta_uuid_s); + raw_ta_uuid++; + } + +exit_with_shm: + TEEC_ReleaseSharedMemory(&io_shm); +exit_with_buf: + free(buf); +exit_with_session: + TEEC_CloseSession(&sess); +exit_with_ctx: + TEEC_FinalizeContext(&ctx); +exit: + return res; +}