change tzdriver directory

Signed-off-by: YuanHao <yuanhao34@huawei.com>
This commit is contained in:
袁浩
2022-06-15 14:58:29 +08:00
parent 031a5b4346
commit f16b108a87
37 changed files with 2 additions and 13628 deletions
+2 -8
View File
@@ -30,15 +30,9 @@
import("//kernel/liteos_a/liteos.gni")
group("liteos") {
deps = [
"hievent",
"tzdriver",
]
deps = [ "hievent" ]
}
config("public") {
configs = [
"hievent:public",
"tzdriver:public",
]
configs = [ "hievent:public" ]
}
-56
View File
@@ -1,56 +0,0 @@
# Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
# Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
#
# Redistribution and use in source and binary forms, with or without modification,
# are permitted provided that the following conditions are met:
#
# 1. Redistributions of source code must retain the above copyright notice, this list of
# conditions and the following disclaimer.
#
# 2. Redistributions in binary form must reproduce the above copyright notice, this list
# of conditions and the following disclaimer in the documentation and/or other materials
# provided with the distribution.
#
# 3. Neither the name of the copyright holder nor the names of its contributors may be used
# to endorse or promote products derived from this software without specific prior written
# permission.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
# THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
# EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
# OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
# WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
# OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
import("//kernel/liteos_a/liteos.gni")
module_switch = defined(LOSCFG_DRIVERS_TZDRIVER)
module_name = get_path_info(rebase_path("."), "name")
kernel_module(module_name) {
sources = [
"src/agent.c",
"src/cmdmonitor.c",
"src/gp_ops.c",
"src/mailbox_mempool.c",
"src/mem.c",
"src/security_auth_enhance.c",
"src/smc_smp.c",
"src/tc_client_driver.c",
"src/tc_client_sub_driver.c",
"src/teek_client_api.c",
"src/tz_spi_notify.c",
"src/tzdebug.c",
"src/tzdriver_compat.c",
]
public_configs = [ ":public" ]
}
config("public") {
include_dirs = [ "include" ]
}
-6
View File
@@ -1,6 +0,0 @@
config DRIVERS_TZDRIVER
bool "Enable iTrustee tzdriver"
default n
depends on TEE_ENABLE
help
Enable iTrustee liteos tzdriver.
-41
View File
@@ -1,41 +0,0 @@
# Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
# Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
#
# Redistribution and use in source and binary forms, with or without modification,
# are permitted provided that the following conditions are met:
#
# 1. Redistributions of source code must retain the above copyright notice, this list of
# conditions and the following disclaimer.
#
# 2. Redistributions in binary form must reproduce the above copyright notice, this list
# of conditions and the following disclaimer in the documentation and/or other materials
# provided with the distribution.
#
# 3. Neither the name of the copyright holder nor the names of its contributors may be used
# to endorse or promote products derived from this software without specific prior written
# permission.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
# THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
# EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
# OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
# WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
# OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
# ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
include $(LITEOSTOPDIR)/config.mk
MODULE_NAME := $(notdir $(shell pwd))
LOCAL_SRCS := src/agent.c src/tzdebug.c src/security_auth_enhance.c src/mem.c \
src/mailbox_mempool.c src/cmdmonitor.c src/teek_client_api.c src/tc_client_driver.c \
src/tc_client_sub_driver.c src/gp_ops.c src/smc_smp.c src/tz_spi_notify.c src/tzdriver_compat.c \
LOCAL_INCLUDE := -I./include/ -I../../../third_party/mbedtls/include -I $(LITEOSTOPDIR)/../../$(LOSCFG_BOARD_CONFIG_PATH)/include
LOCAL_FLAGS := $(LOCAL_INCLUDE)
include $(MODULE)
-139
View File
@@ -1,139 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef AGENT_H
#define AGENT_H
#include "teek_ns_client.h"
#define AGENT_FS_ID 0x46536673 /* FSfs */
#define AGENT_MISC_ID 0x4d495343 /* MISC */
#define TEE_RPMB_AGENT_ID 0x4abe6198 /* RPMB */
#define AGENT_SOCKET_ID 0x69e85664 /* socket */
#define SECFILE_LOAD_AGENT_ID 0x4c4f4144 /* SECFILE-LOAD-AGENT */
#define TEE_SECE_AGENT_ID 0x53656345 /* test */
typedef enum {
AGENT_FALSE = -1,
AGENT_SUCCESS = 0,
} AgentErrCode;
typedef enum {
AGENT_ALIVE = 1,
AGENT_DEAD = 0,
} AgentStatusCode;
enum AgentStateType {
AGENT_CRASHED = 0,
AGENT_REGISTERED,
AGENT_READY,
};
struct SmcEventData *FindEventControl(unsigned int agentId);
/* for secure agent */
struct SmcEventData {
unsigned int agentId;
atomic_t agentReady;
wait_queue_head_t waitEventWq;
int retFlag; /* indicate whether agent is returned from TEE */
wait_queue_head_t sendResponseWq;
struct list_head head;
TcNsSmcCmd cmd;
TcNsDevFile *owner;
void *agentBuffKernel;
void *agentBuffUser; /* used for unmap */
unsigned int agentBuffSize;
atomic_t usage;
#ifdef CONFIG_TEE_SMP
wait_queue_head_t caPendingWq;
atomic_t caRun; /* indicate whether agent is allowed to return to TEE */
#endif
};
struct TeeAgentKernelOps {
const char *agentName; /* MUST NOT be NULL */
unsigned int agentId; /* MUST NOT be zero */
int (*teeAgentInit)(struct TeeAgentKernelOps *agentInstance);
int (*teeAgentRun)(struct TeeAgentKernelOps *agentInstance);
/* MUST NOT be NULL */
int (*teeAgentWork)(struct TeeAgentKernelOps *agentInstance);
int (*teeAgentStop)(struct TeeAgentKernelOps *agentInstance);
int (*teeAgentExit)(struct TeeAgentKernelOps *agentInstance);
int (*teeAgentCrashWork)(
struct TeeAgentKernelOps *agentInstance,
TcNsClientContext *context,
unsigned int devFileId);
LosTaskCB *agentThread;
void *agentData;
void *agentBuff;
unsigned int agentBuffSize;
struct list_head list;
};
static inline void GetAgentEvent(struct SmcEventData *eventData)
{
if (eventData != NULL) {
atomic_inc(&eventData->usage);
}
}
static inline void PutAgentEvent(struct SmcEventData *eventData)
{
if (eventData != NULL) {
if (atomic_dec_and_test(&eventData->usage)) {
free(eventData);
}
}
}
void AgentInit(void);
int AgentExit(void);
void SendEventResponse(unsigned int agentId);
int AgentProcessWork(const TcNsSmcCmd *smcCmd, unsigned int agentId);
int IsAgentAlive(unsigned int agentId);
int TcNsSetNativeHash(unsigned long arg, unsigned int cmdId);
int TcNsLateInit(unsigned long arg);
int TcNsRegisterAgent(TcNsDevFile *devFile, unsigned int agentId,
unsigned int bufferSize, void **buffer, bool userAgent);
int TcNsUnregisterAgent(unsigned int agentId);
void SendCrashedEventResponseAll(const TcNsDevFile *devFile);
int TcNsWaitEvent(unsigned int agentId);
int TcNsSendEventResponse(unsigned int agentId);
void SendEventResponseSingle(const TcNsDevFile *devFile);
int TcNsSyncSysTime(const TcNsClientTime *tcNsTime);
int TeeAgentClearWork(TcNsClientContext *context,
unsigned int devFileId);
int TeeAgentKernelRegister(struct TeeAgentKernelOps *newAgent);
bool IsSystemAgent(const TcNsDevFile *devFile);
void TeeAgentClearDevOwner(const TcNsDevFile *devFile);
extern int checkExtAgentAccess(LosTaskCB *caTask);
#endif /* AGENT_H */
-48
View File
@@ -1,48 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "teek_ns_client.h"
#ifndef _CMD_MONITOR_H_
#define _CMD_MONITOR_H_
#define TEMPORALLY_CHAGE_TIMEOUT (25 * MSEC_PER_SEC)
void CmdMonitorLog(const TcNsSmcCmd *cmd);
void CmdMonitorResetContext(void);
void CmdMonitorLogend(void);
void InitCmdMonitor(void);
void DoCmdNeedArchivelog(void);
bool IsThreadReported(unsigned int tid);
void TzDebugArchiveLog(void);
void CmdMonitorTaCrash(int32_t type);
#endif
-40
View File
@@ -1,40 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _GP_OPS_H_
#define _GP_OPS_H_
#include "tc_ns_client.h"
#include "teek_ns_client.h"
int TcUserParamValid(TcNsClientContext *clientContext, unsigned int index);
int TcClientCall(TcNsClientContext *clientContext,
TcNsDevFile *devFile, TcNsSession *session, uint8_t flags);
#endif
-65
View File
@@ -1,65 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _MAILBOX_MEMPOOOL_H
#define _MAILBOX_MEMPOOOL_H
#include <linux/kernel.h>
#include <linux/types.h>
#include "teek_ns_client.h"
#include "tzdriver_compat.h"
#define MAILBOX_POOL_SIZE SZ_1M
/* alloc options */
#define MB_FLAG_ZERO 0x1 /* set 0 after alloc page */
#define GLOBAL_UUID_LEN 17 /* first char represent global cmd */
struct MbCmdPack {
TcNsOperation operation;
#ifdef SECURITY_AUTH_ENHANCE
unsigned char loginData[MAX_SHA_256_SZ * NUM_OF_SO + HASH_PLAINTEXT_ALIGNED_SIZE + IV_BYTESIZE];
unsigned char token[TOKEN_BUFFER_LEN];
unsigned char secureParams[ALIGN_TZ(sizeof(struct SessionSecureParams),
CIPHER_BLOCK_BYTESIZE) + IV_BYTESIZE];
#else
unsigned char loginData[MAX_SHA_256_SZ * NUM_OF_SO + MAX_SHA_256_SZ];
#endif
};
void *MailboxAlloc(size_t size, unsigned int flag);
void MailboxFree(const void *ptr);
int MailboxMempoolInit(void);
void MailboxMempoolDestroy(void);
struct MbCmdPack *MailboxAllocCmdPack(void);
void *MailboxCopyAlloc(const void *src, size_t size);
#endif
-58
View File
@@ -1,58 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _MEM_H_
#define _MEM_H_
#include <linux/types.h>
#include "teek_ns_client.h"
int TcMemInit(void);
void TcMemDestroy(void);
TcNsSharedMem *TcMemAllocate(size_t len);
void TcMemFree(TcNsSharedMem *sharedMem);
static inline void GetSharememStruct(struct TagTcNsSharedMem *sharemem)
{
if (sharemem != NULL) {
atomic_inc(&sharemem->usage);
}
}
static inline void PutSharememStruct(struct TagTcNsSharedMem *sharemem)
{
if (sharemem != NULL) {
if (atomic_dec_and_test(&sharemem->usage)) {
TcMemFree(sharemem);
}
}
}
#endif
-47
View File
@@ -1,47 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _SECURITY_AUTH_ENHANCE_H_
#define _SECURITY_AUTH_ENHANCE_H_
#include <linux/types.h>
#include "teek_ns_client.h"
#define INC 0x01
#define DEC 0x00
#define UN_SYNCED 0x55
#define IS_SYNCED 0xaa
TeecResult UpdateTimestamp(const TcNsSmcCmd *cmd);
TeecResult UpdateChksum(TcNsSmcCmd *cmd);
TeecResult VerifyChksum(const TcNsSmcCmd *cmd);
TeecResult SyncTimestamp(const TcNsSmcCmd *cmd, uint8_t *token,
uint32_t tokenLen, bool global);
#endif
-79
View File
@@ -1,79 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _SMC_H_
#define _SMC_H_
#include "teek_client_constants.h"
#include "teek_ns_client.h"
enum TcNsCmdType {
TC_NS_CMD_TYPE_INVALID = 0,
TC_NS_CMD_TYPE_NS_TO_SECURE,
TC_NS_CMD_TYPE_SECURE_TO_NS,
TC_NS_CMD_TYPE_SECURE_TO_SECURE,
TC_NS_CMD_TYPE_SECURE_CONFIG = 0xf,
TC_NS_CMD_TYPE_MAX
};
#ifdef CONFIG_TEE_SMP
struct PendingEntry {
atomic_t users;
pid_t pid;
wait_queue_head_t wq;
atomic_t run;
struct list_head list;
};
#endif
#define RESLEEP_TIMEOUT 15
struct SessionCryptoInfo *GetSessionRootKeyInstance(void);
int SigkillPending(LosTaskCB *tsk);
int SmcInitData(void);
void SmcFreeData(void);
int TcNsSmc(TcNsSmcCmd *cmd);
int TcNsSmcWithNoNr(TcNsSmcCmd *cmd);
void SetCmdSendState(void);
int InitSmcSvcThread(void);
int SmcWakeupCa(pid_t ca);
int SmcWakeupBroadcast(void);
int SmcShadowExit(pid_t ca);
int SmcQueueShadowWorker(uint64_t target);
void FiqShadowWorkFunc(uint64_t target);
struct PendingEntry *FindPendingEntry(pid_t pid);
void ForeachPendingEntry(void (*func)(struct PendingEntry *));
void PutPendingEntry(struct PendingEntry *pe);
void ShowCmdBitmap(void);
void ShowCmdBitmapWithLock(void);
void WakeupTcSiq(void);
#endif
-44
View File
@@ -1,44 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TC_NS_CLIENT_DRIVER_H_
#define _TC_NS_CLIENT_DRIVER_H_
#include <linux/list.h>
#include "teek_ns_client.h"
mutex_t *GetServiceListLock(void);
struct TcNsDevList *GetTcNsDevList(void);
struct list_head *GetServiceList(void);
bool ScheduleWorkOn(int cpu, struct work_struct *work);
int TcNsLoadImage(TcNsDevFile *devFile, char *fileBuffer, unsigned int fileSize);
#endif
-92
View File
@@ -1,92 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TC_NS_CLIENT_DRIVER_SUB_H_
#define _TC_NS_CLIENT_DRIVER_SUB_H_
#include <securec.h>
#include "tc_ns_client.h"
#include "teek_ns_client.h"
#define CHECK_PATH_HASH_FAIL 0xff01
#define CHECK_SECLABEL_FAIL 0xff02
#define CHECK_CODE_HASH_FAIL 0xff03
#define ENTER_BYPASS_CHANNEL 0xff04
#define BUF_MAX_SIZE 1024
#define MAX_PATH_SIZE 512
#define SHA256_DIGEST_LENTH 32
char *GetProcessPath(LosTaskCB *task, char *tpath, int pathLen);
int CalcProcessPathHash(const unsigned char *data,
unsigned long dataLen, unsigned char *digest, unsigned int digLen);
int PackCaCert(char *caCert, const char *path,
LosTaskCB *caTask, int uid);
TcNsService *TcFindServiceInDev(TcNsDevFile *dev,
const unsigned char *uuid, int uuidSize);
TcNsService *TcRefServiceInDev(TcNsDevFile *dev, const unsigned char *uuid,
int uuidSize, bool *isFull);
TcNsService *TcFindServiceFromAll(const unsigned char *uuid, uint32_t uuidLen);
int AddServiceToDev(TcNsDevFile *dev, TcNsService *service);
void DelServiceFromDev(TcNsDevFile *dev, TcNsService *service);
TcNsSession *TcFindSessionWithOwner(struct list_head *sessionList,
unsigned int sessionId, TcNsDevFile *devFile);
void DumpServicesStatus(const char *param);
errno_t InitContext(TcNsClientContext *context,
const unsigned char *uuid, const unsigned int uuidLen);
#ifdef SECURITY_AUTH_ENHANCE
int GenerateRandomData(uint8_t *data, uint32_t size);
bool IsValidEncryptionHead(const struct EncryptionHead *head, const uint8_t *data, uint32_t len);
int GenerateChallengeWord(uint8_t *challengeWord, uint32_t size);
int SetEncryptionHead(struct EncryptionHead *head, uint32_t len);
TcNsSession *TcFindSession2(unsigned int devFileId, const TcNsSmcCmd *cmd);
void CleanSessionSecureInformation(TcNsSession *session);
int GetSessionSecureParams(TcNsDevFile *devFile, TcNsClientContext *context, TcNsSession *session);
#endif
int CloseSession(TcNsDevFile *dev, TcNsSession *session, const unsigned char *uuid,
unsigned int uuidLen, unsigned int sessionId);
void KillSession(TcNsDevFile *dev, const unsigned char *uuid,
unsigned int uuidLen, unsigned int sessionId);
int TcNsServiceInit(const unsigned char *uuid, uint32_t uuidLen, TcNsService **newService);
uint32_t TcNsGetUid(void);
int GetPackNameLen(TcNsDevFile *devFile, const uint8_t *certBuffer,
unsigned int certBufferSize);
int GetPublicKeyLen(TcNsDevFile *devFile, const uint8_t *certBuffer,
unsigned int certBufferSize);
bool IsValidTaSize(const char *fileBuffer, unsigned int fileSize);
int TcNsNeedLoadImage(unsigned int fileId, const unsigned char *uuid,
unsigned int uuidLen);
int LoadTaImage(TcNsDevFile *devFile, TcNsClientContext *context);
void ReleaseFreeSession(TcNsDevFile *devFile, TcNsClientContext *context, TcNsSession *session);
void CloseSessionInServiceList(TcNsDevFile *dev, TcNsService *service, uint32_t i);
void CloseUnclosedSession(TcNsDevFile *dev, uint32_t i);
void DelDevNode(TcNsDevFile *dev);
int NsClientCloseTeecdNotAgent(TcNsDevFile *dev);
int TcNsLoadSecfile(TcNsDevFile *devFile, const void __user *argp);
#endif
-193
View File
@@ -1,193 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TC_NS_CLIENT_H_
#define _TC_NS_CLIENT_H_
#include <linux/fs.h>
#include "teek_client_type.h"
#ifdef SECURITY_AUTH_ENHANCE
#define SCRAMBLING_KEY_LEN 4
#define TOKEN_BUFFER_LEN 42 /* token(32byte) + timestamp(8byte) + kernal_api(1byte) + sync(1byte) */
#define TIMESTAMP_BUFFER_INDEX 32
#define KERNAL_API_INDEX 40
#define SYNC_INDEX 41
#define UUID_LEN 16
#define PARAM_NUM 4
#define ADDR_TRANS_NUM 32
#define TEE_PARAM_ONE 0
#define TEE_PARAM_TWO 1
#define TEE_PARAM_THREE 2
#define TEE_PARAM_FOUR 3
#define TIMESTAMP_LEN_DEFAULT \
((KERNAL_API_INDEX) - (TIMESTAMP_BUFFER_INDEX))
#define KERNAL_API_LEN \
((TOKEN_BUFFER_LEN) - (KERNAL_API_INDEX))
#define TIMESTAMP_SAVE_INDEX 16
#endif
#ifndef ZERO_SIZE_PTR
#define ZERO_SIZE_PTR ((void *)16)
#define ZERO_OR_NULL_PTR(x) ((unsigned long)(x) <= (unsigned long)ZERO_SIZE_PTR)
#endif
typedef struct {
unsigned int method;
unsigned int mdata;
} TcNsClientLogin;
typedef union {
struct {
unsigned int buffer;
unsigned int bufferH;
unsigned int offset;
unsigned int offsetH;
unsigned int sizeAddr;
unsigned int sizeAddrH;
} memref;
struct {
unsigned int aAddr;
unsigned int aHaddr;
unsigned int bAddr;
unsigned int bHaddr;
} value;
} TcNsClientParam;
typedef struct {
int code;
unsigned int origin;
} TcNsClientReturn;
typedef struct {
unsigned char uuid[UUID_LEN];
unsigned int sessionId;
unsigned int cmdId;
TcNsClientReturn returns;
TcNsClientLogin login;
TcNsClientParam params[PARAM_NUM];
unsigned int paramTypes;
unsigned char started;
#ifdef SECURITY_AUTH_ENHANCE
void* teecToken;
unsigned int tokenLen;
#endif
unsigned int callingPid;
unsigned int fileSize;
union {
char *fileBuffer;
unsigned long long fileAddr;
};
} TcNsClientContext;
typedef struct {
unsigned int seconds;
unsigned int millis;
} TcNsClientTime;
enum SecfileTypeT {
LOAD_TA = 0,
LOAD_SERVICE,
LOAD_LIB,
};
struct LoadSecfileIoctlStruct {
enum SecfileTypeT secfileType;
unsigned char uuid[UUID_LEN];
unsigned int fileSize;
union {
char *fileBuffer;
unsigned long long file_addr;
};
};
struct AgentIoctlArgs {
unsigned int id;
unsigned int bufferSize;
union {
void *buffer;
unsigned long long addr;
};
};
#define TST_CMD_01 1
#define TST_CMD_02 2
#define TST_CMD_03 3
#define TST_CMD_04 4
#define TST_CMD_05 5
#define MAX_SHA_256_SZ 32
#define TC_NS_CLIENT_IOCTL_SES_OPEN_REQ \
_IOW(TC_NS_CLIENT_IOC_MAGIC, 1, TcNsClientContext)
#define TC_NS_CLIENT_IOCTL_SES_CLOSE_REQ \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 2, TcNsClientContext)
#define TC_NS_CLIENT_IOCTL_SEND_CMD_REQ \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 3, TcNsClientContext)
#define TC_NS_CLIENT_IOCTL_SHRD_MEM_RELEASE \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 4, unsigned int)
#define TC_NS_CLIENT_IOCTL_WAIT_EVENT \
_IO(TC_NS_CLIENT_IOC_MAGIC, 5)
#define TC_NS_CLIENT_IOCTL_SEND_EVENT_RESPONSE \
_IO(TC_NS_CLIENT_IOC_MAGIC, 6)
#define TC_NS_CLIENT_IOCTL_REGISTER_AGENT \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 7, struct AgentIoctlArgs)
#define TC_NS_CLIENT_IOCTL_UNREGISTER_AGENT \
_IO(TC_NS_CLIENT_IOC_MAGIC, 8)
#define TC_NS_CLIENT_IOCTL_LOAD_APP_REQ \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 9, struct LoadSecfileIoctlStruct)
#define TC_NS_CLIENT_IOCTL_NEED_LOAD_APP \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 10, TcNsClientContext)
#define TC_NS_CLIENT_IOCTL_ALLOC_EXCEPTING_MEM \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 12, unsigned int)
#define TC_NS_CLIENT_IOCTL_CANCEL_CMD_REQ \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 13, TcNsClientContext)
#define TC_NS_CLIENT_IOCTL_LOGIN \
_IO(TC_NS_CLIENT_IOC_MAGIC, 14)
#define TC_NS_CLIENT_IOCTL_TST_CMD_REQ \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 15, int)
#define TC_NS_CLIENT_IOCTL_TUI_EVENT \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 16, int)
#define TC_NS_CLIENT_IOCTL_SYC_SYS_TIME \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 17, TcNsClientTime)
#define TC_NS_CLIENT_IOCTL_SET_NATIVECA_IDENTITY \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 18, int)
#define TC_NS_CLIENT_IOCTL_LOAD_TTF_FILE_AND_NOTCH_HEIGHT \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 19, unsigned int)
#define TC_NS_CLIENT_IOCTL_LATEINIT \
_IO(TC_NS_CLIENT_IOC_MAGIC, 20)
#define TC_NS_CLIENT_IOCTL_GET_TEE_VERSION \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 21, unsigned int)
#define TC_NS_CLIENT_IOCTL_UNMAP_SHARED_MEM \
_IOWR(TC_NS_CLIENT_IOC_MAGIC, 22, unsigned int)
#endif
-83
View File
@@ -1,83 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef TC_NS_LOG_H_
#define TC_NS_LOG_H_
#include <linux/kernel.h>
enum {
TZ_DEBUG_VERBOSE = 0,
TZ_DEBUG_DEBUG,
TZ_DEBUG_INFO,
TZ_DEBUG_WARN,
TZ_DEBUG_ERROR,
};
#ifdef DEF_ENG
#define TEE_ENG_LOG_MASK 2
#define TEE_LOG_MASK TEE_ENG_LOG_MASK
#else
#define TEE_USR_LOG_MASK 3
#define TEE_LOG_MASK TEE_USR_LOG_MASK
#endif
#define tlogv(fmt, args...) \
do { \
if (TZ_DEBUG_VERBOSE >= TEE_LOG_MASK) \
pr_info("(%i, %s)%s: " fmt, OsCurrTaskGet()->taskID, OsCurrTaskGet()->taskName, __func__, ## args); \
} while (0)
#define tlogd(fmt, args...) \
do { \
if (TZ_DEBUG_DEBUG >= TEE_LOG_MASK) \
pr_info("(%i, %s)%s: " fmt, OsCurrTaskGet()->taskID, OsCurrTaskGet()->taskName, __func__, ## args); \
} while (0)
#define tlogi(fmt, args...) \
do { \
if (TZ_DEBUG_INFO >= TEE_LOG_MASK) \
pr_info("(%i, %s)%s: " fmt, OsCurrTaskGet()->taskID, OsCurrTaskGet()->taskName, __func__, ## args); \
} while (0)
#define tlogw(fmt, args...) \
do { \
if (TZ_DEBUG_WARN >= TEE_LOG_MASK) \
pr_warn("(%i, %s)%s: " fmt, OsCurrTaskGet()->taskID, OsCurrTaskGet()->taskName, __func__, ## args); \
} while (0)
#define tloge(fmt, args...) \
pr_err("(%i, %s)%s: " fmt, OsCurrTaskGet()->taskID, OsCurrTaskGet()->taskName, __func__, ## args)
#endif
-254
View File
@@ -1,254 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
/* @defgroup TEEC_API client(REE) interface
* @defgroup TEEC_BASIC_FUNC common interface
* @ingroup TEEC_API
*/
#ifndef _TEEK_CLIENT_API_H_
#define _TEEK_CLIENT_API_H_
#include "teek_client_type.h"
#include "teek_ns_client.h"
/*
* @ingroup TEEC_BASIC_FUNC
* Calculate the values of the transfer parameters between REE and TEE
*/
#define TEEC_PARAM_TYPES(param0_type, param1_type, param2_type, param3_type) \
(((param3_type) << 12) | ((param2_type) << 8) | \
((param1_type) << 4) | (param0_type))
/*
* @ingroup TEEC_BASIC_FUNC
* Get the index value in parmaTypes
*/
#define TEEC_PARAM_TYPE_GET(paramTypes, index) \
(((paramTypes) >> ((index) << 2)) & 0x0F)
/*
* @ingroup TEEC_BASIC_FUNC
* When the parameter type is #teec_value, if the member variable a or b is not assigned,
* you need to assign this value to it, indicates that this member variable is not used.
*/
#define TEEC_VALUE_UNDEF 0xFFFFFFFF
/*
* Function: TeekIsAgentAlive
* Description: This function check if the special agent is launched.
* Used For HDCP key.
* e.g. If sfs agent is not alive,
* you can not do HDCP key write to SRAM.
* Parameters: agentId.
* Return: 1:agent is alive
* 0:agent not exsit.
*/
int TeekIsAgentAlive(unsigned int agentId);
/*
* @ingroup TEEC_BASIC_FUNC
* @brief Initialize the TEE context
*
* @par Description
* Initialize the TEE context whose path is 'name'. The 'name' can be left empty,
* TEE initialization is the basis for opening a session and sending a command,
* after the initialization is successful, a connection is set up between the CA and the TEE.
*
* @param name [IN] Tee context path
* @param context [IN/OUT] context pointersecure world environment handle
*
* @retval #TEEC_SUCCESS TEE context is successfully initialized
* @retval #TEEC_ERROR_BAD_PARAMETERS Parameter is incorrect, 'name' is incorrect or context is empty
* @retval #TEEC_ERROR_GENERIC System resources are insufficient
*/
TeecResult TeekInitializeContext(const char *name, TeecContext *context);
/*
* @ingroup TEEC_BASIC_FUNC
* @brief Close the tee context
*
* @par Description
* Close the TEE context to which the 'context' points, and disconnect the client application from the TEE environment.
*
* @param context [IN/OUT] The TEE context that has been successfully initialized
*
*/
void TeekFinalizeContext(TeecContext *context);
/*
* @ingroup TEEC_BASIC_FUNC
* @brief Open session
*
* @par Description
* Create a session which is from CA to the 'destination' UUID TA,
* the connection method is 'connectionMethod', and the link data is 'connectionData',
* The transferred data is contained in the 'opetation'.
* After a session is opened successfully, the output parameter 'session' is a description of the link.
* If the session fails to be opened, 'returnOrigin' is the error source.
*
* @param context [IN/OUT] The TEE context that has been successfully initialized
* @param session [OUT] Pointed to the session, the value cannot be empty
* @param destination [IN] UUID of a security service, a security service has a unique UUID.
* @param connectionMethod [IN] Connection mode. The value range is #TEEC_LoginMethod.
* @param connectionData [IN] Connection data corresponding to the connection mode
* If connection mode is #TEEC_LOGIN_PUBLIC, #TEEC_LOGIN_USE,
* #TEEC_LOGIN_USER_APPLICATION, #TEEC_LOGIN_GROUP_APPLICATION, connection data must be empty.
* If connection mode is #TEEC_LOGIN_GROUP、#TEEC_LOGIN_GROUP_APPLICATION
* the connection data must point to data of type uint32_t,
* which represents the user group that the client application expects to connect to.
* @param operation [IN/OUT] Data transferred between CAs and TAs
* @param returnOrigin [IN/OUT] Error source. The value range is #TEEC_ReturnCodeOrigin.
*
* @retval #TEEC_SUCCESS Open successfully.
* @retval #TEEC_ERROR_BAD_PARAMETERS The parameter is incorrect.
* @retval #TEEC_ERROR_ACCESS_DENIED Failed to access the system call permission.
* @retval #TEEC_ERROR_OUT_OF_MEMORY Insufficient system resources.
* @retval #TEEC_ERROR_TRUSTED_APP_LOAD_ERROR Failed to load the security service.
* @retval Other return values, see. #TEEC_ReturnCode
*/
TeecResult TeekOpenSession(TeecContext *context,
TeecSession *session,
const TeecUuid *destination,
uint32_t connectionMethod,
const void *connectionData,
const TeecOperation *operation,
uint32_t *returnOrigin);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief Close session
*
* @par Description
* Close the session to which the 'session' points, and disconnect the client application from the security service.
*
* @param session [IN/OUT] Point to a session that has been opened successfully
*/
void TeekCloseSession(TeecSession *session);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief Send a command.
*
* @par Description
* In a specified 'session', the CA sends the 'commandID' command to the TA.
* The sent data is 'operation'.
* If the command fails to be sent, the 'returnOrigin' indicate the error source.
*
* @param session [IN/OUT] Pointing to a session that has been successfully opened
* @param commandID [IN] Command ID supported by the security service, which is defined by the security service.
* @param operation [IN/OUT] Contains the data sent from the CA to the TA.
* @param returnOrigin [IN/OUT] Error source. The value range is #TEEC_ReturnCodeOrigin.
*
* @retval #TEEC_SUCCESS Command sent successfully.
* @retval #TEEC_ERROR_BAD_PARAMETERS The parameter is incorrect,
* the session parameter is empty or the operation parameter is in an incorrect format.
* @retval #TEEC_ERROR_ACCESS_DENIED Failed to access the system call permission.
* @retval #TEEC_ERROR_OUT_OF_MEMORY Insufficient system resources.
* @retval other return values, see. #TEEC_ReturnCode
*/
TeecResult TeekInvokeCommand(TeecSession *session,
uint32_t commandID,
TeecOperation *operation,
uint32_t *returnOrigin);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief Register the Shared Memory
*
* @par Description
* Registers the shared memory 'sharedMem' in the specified TEE 'context'
* the operating system needs to support zero copy to obtain the shared memory through registration,
* in the current implementation, zero copy cannot be implemented in this mode.
*
* @attention If the size field of the input parameter 'sharedMem' is set to 0,
* the function returns a success message, but this field cannot be used.Shared memory,
* because this memory has no size
* @param context [IN/OUT] TEE environment that has been successfully initialized
* @param sharedMem [IN/OUT] Pointer to the shared memory, the memory cannot be null or 0.
*
* @retval #TEEC_SUCCESS Command sent successfully.
* @retval #TEEC_ERROR_BAD_PARAMETERS The parameter is incorrect. The context or sharedMem parameter is empty
* or the memory to which the shared memory points is empty.
*/
TeecResult TeekRegisterSharedMemory(TeecContext *context,
TeecSharedMemory *sharedMem);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief Apply for Shared Memory
*
* @par Description
* Apply for the shared memory 'sharedMem' in the specified TEE 'context',
* The shared memory can implement zero copy when data is transferred
* between the non-secure world and the secure world.
*
* @attention If the size field of the input parameter 'sharedMem' is set to 0,
* the function returns a success message, but this Shared memory field cannot be used,
* because this memory has neither address nor size.
* @param context [IN/OUT] TEE environment that has been successfully initialized
* @param sharedMem [IN/OUT] Pointer to the shared memory. The size of the shared memory cannot be 0.
*
* @retval #TEEC_SUCCESS Command sent successfully.
* @retval #TEEC_ERROR_BAD_PARAMETERS The parameter is incorrect. The context or sharedMem parameter is empty.
* @retval #TEEC_ERROR_OUT_OF_MEMORY Allocation failed due to insufficient system resources.
*/
TeecResult TeekAllocateSharedMemory(TeecContext *context,
TeecSharedMemory *sharedMem);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief Release the shared memory.
*
* @par Description
* Releases the shared memory that has been registered or applied for.
*
* @attention If the shared memory is obtained in #TEEK_AllocateSharedMemory mode, When the memory is released,
* the memory is reclaimed. If the #TEEK_RegisterSharedMemory method is used,
* The local memory to which the shared memory points is not reclaimed when the shared memory is released.
* @param sharedMem [IN/OUT] Point to the shared memory that has been registered or applied for successfully
*/
void TeekReleaseSharedMemory(TeecSharedMemory *sharedMem);
/**
* @ingroup TEEC_BASIC_FUNC
* @brief cancel API
*
* @par Description
* Cancel a running open session or an invoke command.
* Send a cancel signal and return immediately.
*
* @attention This operation only sends a cancel message,
* whether to perform the cancel operation is determined by the TEE or TA.
* @param operation [IN/OUT] Contains the data sent from the CA to the TA.
*/
void TeekRequestCancellation(TeecOperation *operation);
#endif
-175
View File
@@ -1,175 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include <linux/types.h>
#ifndef _TEEK_CLIENT_CONSTANTS_H_
#define _TEEK_CLIENT_CONSTANTS_H_
enum GlobalServiceCmdId {
GLOBAL_CMD_ID_INVALID = 0x0,
GLOBAL_CMD_ID_BOOT_ACK = 0x1,
GLOBAL_CMD_ID_OPEN_SESSION = 0x2,
GLOBAL_CMD_ID_CLOSE_SESSION = 0x3,
/* Global Task dynamically load secure applications */
GLOBAL_CMD_ID_LOAD_SECURE_APP = 0x4,
/* Global Task determine whether to load a secure application */
GLOBAL_CMD_ID_NEED_LOAD_APP = 0x5,
GLOBAL_CMD_ID_REGISTER_AGENT = 0x6,
GLOBAL_CMD_ID_UNREGISTER_AGENT = 0x7,
GLOBAL_CMD_ID_REGISTER_NOTIFY_MEMORY = 0x8,
GLOBAL_CMD_ID_UNREGISTER_NOTIFY_MEMORY = 0x9,
GLOBAL_CMD_ID_INIT_CONTENT_PATH = 0xa, /* Global Task init content path */
/* Global Task free content path */
GLOBAL_CMD_ID_TERMINATE_CONTENT_PATH = 0xb,
GLOBAL_CMD_ID_ALLOC_EXCEPTION_MEM = 0xc,
GLOBAL_CMD_ID_TEE_TIME = 0xd,
GLOBAL_CMD_ID_TEE_INFO = 0xe,
GLOBAL_CMD_ID_REGISTER_RDR_MEM = 0xf,
GLOBAL_CMD_ID_KILL_TASK = 0x10, /* Global Task Kill session */
GLOBAL_CMD_ID_ADJUST_TIME = 0x12, /* TIME adjust */
GLOBAL_CMD_ID_SET_CA_HASH = 0x13, /* set ca hash info */
GLOBAL_CMD_ID_SET_BUILD_VERSION = 0x14, /* set the build version */
/* get session key for encrypting dialog */
GLOBAL_CMD_ID_GET_SESSION_SECURE_PARAMS = 0x16,
GLOBAL_CMD_ID_REGISTER_MAILBOX = 0x17,
GLOBAL_CMD_ID_DUMP_MEMINFO = 0x1a,
/* this cmd will be used to service no ca handle cmd */
GLOBAL_CMD_ID_SET_SERVE_CMD = 0x1b,
GLOBAL_CMD_ID_ADD_DYNAMIC_ION = 0x1c,
GLOBAL_CMD_ID_DEL_DYNAMIC_ION = 0x1d,
GLOBAL_CMD_ID_LOAD_SECURE_APP_ION = 0x1e,
GLOBAL_CMD_ID_LATE_INIT = 0x20,
GLOBAL_CMD_ID_GET_TEE_VERSION = 0x22,
GLOBAL_CMD_ID_UNKNOWN = 0x7FFFFFFE,
GLOBAL_CMD_ID_MAX = 0x7FFFFFFF
};
// Return Codes
enum TeecResult {
TEEC_SUCCESS = 0x0,
TEEC_ERROR_INVALID_CMD = 0x1,
TEEC_ERROR_SERVICE_NOT_EXIST = 0x2,
TEEC_ERROR_SESSION_NOT_EXIST = 0x3,
TEEC_ERROR_SESSION_MAXIMUM, /* security service session is full */
TEEC_ERROR_REGISTER_EXIST_SERVICE, /* register exist service */
TEEC_ERROR_TAGET_DEAD_FATAL, /* security service Global error(Global is the basic of all services) */
TEEC_ERROR_READ_DATA, /* read file fail */
TEEC_ERROR_WRITE_DATA, /* write file fail */
TEEC_ERROR_TRUNCATE_OBJECT, /* trancate file fail */
TEEC_ERROR_SEEK_DATA, /* seek file fail */
TEEC_ERROR_RENAME_OBJECT, /* renme file fail */
TEEC_ERROR_TRUSTED_APP_LOAD_ERROR, /* load security app fail */
TEEC_ERROR_GENERIC = 0xFFFF0000,
TEEC_ERROR_ACCESS_DENIED = 0xFFFF0001,
TEEC_ERROR_CANCEL = 0xFFFF0002,
TEEC_ERROR_ACCESS_CONFLICT = 0xFFFF0003,
TEEC_ERROR_EXCESS_DATA = 0xFFFF0004,
TEEC_ERROR_BAD_FORMAT = 0xFFFF0005,
TEEC_ERROR_BAD_PARAMETERS = 0xFFFF0006,
TEEC_ERROR_BAD_STATE = 0xFFFF0007,
TEEC_ERROR_ITEM_NOT_FOUND = 0xFFFF0008,
TEEC_ERROR_NOT_IMPLEMENTED = 0xFFFF0009,
TEEC_ERROR_NOT_SUPPORTED = 0xFFFF000A,
TEEC_ERROR_NO_DATA = 0xFFFF000B,
TEEC_ERROR_OUT_OF_MEMORY = 0xFFFF000C,
TEEC_ERROR_BUSY = 0xFFFF000D,
TEEC_ERROR_COMMUNICATION = 0xFFFF000E,
TEEC_ERROR_SECURITY = 0xFFFF000F,
TEEC_ERROR_SHORT_BUFFER = 0xFFFF0010,
TEEC_PENDING = 0xFFFF2000,
TEEC_PENDING2 = 0xFFFF2001,
TEE_ERROR_TAGET_DEAD = 0xFFFF3024,
TEE_ERROR_GT_DEAD = 0xFFFF3124,
TEEC_ERROR_MAC_INVALID = 0xFFFF3071,
TEEC_CLIENT_INTR = 0xFFFF4000,
TEEC_ERROR_CA_AUTH_FAIL = 0xFFFFCFE5,
TEE_ERROR_AUDIT_FAIL = 0xFFFF9112,
};
// Return Code Origins
enum TEEC_ReturnCodeOrigin {
TEEC_ORIGIN_API = 0x1,
TEEC_ORIGIN_COMMS = 0x2,
TEEC_ORIGIN_TEE = 0x3,
TEEC_ORIGIN_TRUSTED_APP = 0x4,
TEEC_ORIGIN_TRUSTED_APP_TUI = 0x5,
};
// Shared Memory Control
enum TEEC_SharedMemCtl {
TEEC_MEM_INPUT = 0x1,
TEEC_MEM_OUTPUT = 0x2,
TEEC_MEM_INOUT = 0x3,
};
// API Parameter Types
enum TEEC_ParamType {
TEEC_NONE = 0x0,
TEEC_VALUE_INPUT = 0x01,
TEEC_VALUE_OUTPUT = 0x02,
TEEC_VALUE_INOUT = 0x03,
TEEC_MEMREF_TEMP_INPUT = 0x05,
TEEC_MEMREF_TEMP_OUTPUT = 0x06,
TEEC_MEMREF_TEMP_INOUT = 0x07,
TEEC_ION_INPUT = 0x08,
TEEC_ION_SGLIST_INPUT = 0x09,
TEEC_MEMREF_WHOLE = 0xc,
TEEC_MEMREF_PARTIAL_INPUT = 0xd,
TEEC_MEMREF_PARTIAL_OUTPUT = 0xe,
TEEC_MEMREF_PARTIAL_INOUT = 0xf
};
enum TEE_ParamType {
TEE_PARAM_TYPE_NONE = 0x0,
TEE_PARAM_TYPE_VALUE_INPUT = 0x1,
TEE_PARAM_TYPE_VALUE_OUTPUT = 0x2,
TEE_PARAM_TYPE_VALUE_INOUT = 0x3,
TEE_PARAM_TYPE_MEMREF_INPUT = 0x5,
TEE_PARAM_TYPE_MEMREF_OUTPUT = 0x6,
TEE_PARAM_TYPE_MEMREF_INOUT = 0x7,
TEE_PARAM_TYPE_ION_INPUT = 0x8,
TEE_PARAM_TYPE_ION_SGLIST_INPUT = 0x9,
};
// Session Login Methods
enum TEEC_LoginMethod {
TEEC_LOGIN_PUBLIC = 0x0,
TEEC_LOGIN_USER,
TEEC_LOGIN_GROUP,
TEEC_LOGIN_APPLICATION = 0x4,
TEEC_LOGIN_USER_APPLICATION = 0x5,
TEEC_LOGIN_GROUP_APPLICATION = 0x6,
TEEC_LOGIN_IDENTIFY = 0x7,
};
#endif
-180
View File
@@ -1,180 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include <linux/types.h>
#ifndef _TEE_CLIENT_LIST_H_
#define _TEE_CLIENT_LIST_H_
/*
* @ingroup TEEC_List
* Linked list type
*/
struct ListNode {
struct ListNode *next;
struct ListNode *prev;
};
#define TEEK_INIT_LIST_HEAD(list) do { \
(list)->next = (list); \
(list)->prev = (list); \
} while (0)
#define LIST_FOR_EACH(node, list) for ((node) = (list)->next; (node) != (list); (node) = (node)->next)
/*
* @ingroup TEEC_List
* @brief Define a linked list node.
* @par Description
* Defines a linked list node and initializes it.
* @param name [IN] linked list node name
*/
#define LIST_DECLARE(name) \
struct ListNode (name) = { \
.next = &(name), \
.prev = &(name), \
}
#ifndef NULL
#define NULL 0
#endif
/*
* @ingroup TEEC_List
* Obtains the prev node of the linked list.
*/
#define LIST_TAIL(list) ((list)->prev)
/*
* @ingroup TEEC_List
* Check whether the linked list is empty.
*/
#define LIST_EMPTY(list) ((list) == (list)->next)
/*
* @ingroup TEEC_List
* @brief Inserts a new node from the head of a linked list.
*
* @par Description
* Inserts a new node from the head of a linked list
*
* @param list [IN/OUT]Pointer to the linked list header, the value cannot be empty.
* @param entry [IN/OUT]Pointer to the new linked list node, the value cannot be empty.
*/
static inline void ListInsertHead(struct ListNode *list,
struct ListNode *entry)
{
list->next->prev = entry;
entry->next = list->next;
entry->prev = list;
list->next = entry;
}
/*
* @ingroup TEEC_List
* @brief Inserts a new node at the end of the linked list.
*
* @par Description
* Inserts a new node at the end of the linked list.
*
* @param list [IN/OUT]Pointer to the linked list header, the value cannot be empty.
* @param entry [IN/OUT]Pointer to the new linked list node, the value cannot be empty.
*/
static inline void ListInsertTail(struct ListNode *list,
struct ListNode *entry)
{
entry->next = list;
entry->prev = list->prev;
list->prev->next = entry;
list->prev = entry;
}
/*
* @ingroup TEEC_List
* @brief Delete node
*
* @par Description
* Deletes a specified node.
*
* @attention Release the memory of the node to be deleted.
* @param entry [IN]Pointer to the linked list node to be deleted. The value cannot be null.
*/
static inline void ListRemove(struct ListNode *entry)
{
entry->prev->next = entry->next;
entry->next->prev = entry->prev;
}
/*
* @ingroup TEEC_List
* @brief Delete the head node of the linked list.
*
* @par Description
* Deletes the head node of a specified linked list.
*
* @attention After return, the memory of the deleted node should be release.
* @param list [IN]Pointer to the linked list header, the value cannot be empty.
*
* @retval #NULL The linked list is empty.
* @retval not #NULL Linked list header node
*/
static inline struct ListNode *ListRemoveHead(struct ListNode *list)
{
struct ListNode *entry = NULL;
if (!LIST_EMPTY(list)) {
entry = list->next;
ListRemove(entry);
}
return entry;
}
/*
* @ingroup TEEC_List
* @brief Delete the tail node of the linked list.
*
* @par Description
* Delete the tail node of the linked list.
*
* @attention After return, the memory of the deleted node should be release.
* @param list [IN]Pointer to the linked list header, the value cannot be empty.
*
* @retval NULL The linked list is empty.
* @retval not #NULL Linked list header node
*/
static inline struct ListNode *ListRemoveTail(struct ListNode *list)
{
struct ListNode *entry = NULL;
if (!LIST_EMPTY(list)) {
entry = list->prev;
ListRemove(entry);
}
return entry;
}
#endif
-206
View File
@@ -1,206 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TEE_CLIENT_TYPE_H_
#define _TEE_CLIENT_TYPE_H_
#define SECURITY_AUTH_ENHANCE
#include "teek_client_constants.h"
#include "teek_client_list.h"
#define TOKEN_SAVE_LEN 24
#define CLOCK_NODE_LEN 8
#define TEE_PARAM_NUM 4
/*
* @ingroup teec_common_data
* define NULL
*/
#ifndef NULL
#define NULL 0
#endif
/*
* @ingroup teec_common_data
* Function return value type
*/
typedef uint32_t TeecResult;
/*
* @ingroup teec_common_data
* uuid type def
*
* uuid type follow rfc4122 [2]is used to identify the security service.
*/
typedef struct {
/* Lower 4 bytes of the timestamp */
uint32_t timeLow;
/* Middle 2 bytes of the timestamp */
uint16_t timeMid;
/* Combination of higher 2 bytes of the timestamp and version */
uint16_t timeHiAndVersion;
/* Combination of clock sequence and node identifier */
uint8_t clockseqAndNode[CLOCK_NODE_LEN];
} TeecUuid;
/*
* @ingroup teec_common_data
* teec_context struct definition
*
* Describes the connect context between client applications and the secure world.
*/
typedef struct {
void *dev;
uint8_t *ta_path;
/* session list */
struct ListNode sessionList;
/* shared memory list */
struct ListNode shrdMemList;
} TeecContext;
/*
* @ingroup teec_common_data
* teec_session
*
* Describes the sessions established between CAs and the TEE.
*/
typedef struct {
/* Session ID, which is returned by the TEE. */
uint32_t sessionId;
/* Indicates the UUID of a security service. Each TA has a unique UUID. */
TeecUuid serviceId;
/* Number of operations in a session. */
uint32_t opsCnt;
/* Session linked list header */
struct ListNode head;
/* Point to the Tee context to which the session belongs */
TeecContext *context;
#ifdef SECURITY_AUTH_ENHANCE
/* token_save_len 24byte = token 16byte + timestamp 8byte */
uint8_t teecToken[TOKEN_SAVE_LEN];
#endif
} TeecSession;
/*
* @ingroup teec_common_data
* teec_sharedmemory
*
* Describes a piece of shared memory that can be registered or allocated.
*/
typedef struct {
/* Memory pointer */
void *buffer;
/* Memory Size */
size_t size;
/* Memory flags which is used to distinguish between input and output, range is as follows:#teec_sharedmemctl */
uint32_t flags;
/* Number of memory operations */
uint32_t opsCnt;
/* Memory allocation identifier, which is used to identify whether the memory is registered or allocated. */
bool isAllocated;
/* Linked list header of the shared memory */
struct ListNode head;
/* The Tee context to which the object belongs. */
TeecContext *context;
} TeecSharedMemory;
/*
* @ingroup teec_common_data
* teec_tempmemory_reference
*
* A temporary buffer is used for #teec_parameter, corresponding to which can be
* #teec_memref_temp_input, #teec_memref_temp_outputor #teec_memref_temp_inout
*/
typedef struct {
/* temporary buffer pointer */
void *buffer;
/* temporary buffer size */
size_t size;
} TeecTempmemoryReference;
/*
* @ingroup teec_common_data
* teec_registeredmemory_reference
*
* Indicates the pointer of the shared memory, which points to the registered or allocated shared memory.
* The type that can be used for #teec_parameter, corresponding to which can be
* #teec_memref_whole #teec_memref_partial_input
* #teec_memref_partial_outputor #teec_memref_partial_inout
*/
typedef struct {
/* shared memory pointer */
TeecSharedMemory *parent;
/* shared memory size */
size_t size;
/* shared memory offset */
size_t offset;
} TeecRegisteredmemoryReference;
/*
* @ingroup teec_common_data
* teec_value
*
* Describe a small amount of data
* The type that can be used for #teec_parameter, corresponding to which can be
* #teec_value_input, #teec_value_output, or #teec_value_inout
*/
typedef struct {
uint32_t a;
uint32_t b;
} TeecValue;
/*
* @ingroup teec_common_data
* teec_parameter
*
* Parameter type corresponding to #teec_operation.
*/
typedef union {
TeecTempmemoryReference tmpref;
TeecRegisteredmemoryReference memref;
TeecValue value;
} TeecParameter;
/*
* @ingroup teec_common_data
* teec_operation
*
* Parameters used for opening a session or sending a command,
* can also be used to cancel an operation
*/
typedef struct {
/* Indicates whether the operation is canceled. 0 indicates canceled. */
uint32_t started;
uint32_t paramTypes;
TeecParameter params[TEE_PARAM_NUM];
TeecSession *session;
bool cancelFlag;
} TeecOperation;
#endif
-317
View File
@@ -1,317 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TEEK_NS_CLIENT_H_
#define _TEEK_NS_CLIENT_H_
#include <linux/list.h>
#include <linux/slab.h>
#include <securec.h>
#include "tc_ns_client.h"
#include "tc_ns_log.h"
#include "tzdriver_compat.h"
#define TC_NS_CLIENT_IOC_MAGIC 't'
#define TC_NS_CLIENT_DEV "tc_ns_client"
#define TC_NS_CLIENT_DEV_NAME "/dev/tc_ns_client"
#ifdef CONFIG_SECURE_EXTENSION
#define TC_ASYNC_NOTIFY_SUPPORT
#endif
#define EXCEPTION_MEM_SIZE (8*1024) /* mem for exception handling */
#define TSP_REQUEST 0xB2000008
#define TSP_RESPONSE 0xB2000009
#define TSP_REE_SIQ 0xB200000A
#define TSP_CRASH 0xB200000B
#define TSP_PREEMPTED 0xB2000005
#define TC_CALL_GLOBAL 0x01
#define TC_CALL_SYNC 0x02
#define TC_CALL_LOGIN 0x04
#define TEE_REQ_FROM_USER_MODE 0x0
#define TEE_REQ_FROM_KERNEL_MODE 0x1
/* Max sizes for login info buffer comming from teecd */
#define MAX_PACKAGE_NAME_LEN 255
/* The application certificate format is as follows:
* modulus_size(4 bytes) + modulus buffer(512 bytes)
* + exponent size(4 bytes) + exponent buffer(1 bytes)
*/
#define MAX_PUBKEY_LEN 1024
struct TagTcNsSharedMem;
struct TagTcNsService;
struct TcNsDevList {
mutex_t devLock; /* for devFileList */
struct list_head devFileList;
};
#define SERVICES_MAX_COUNT 32 /* service limit can opened on 1 fd */
typedef struct TagTcNsDevFile {
unsigned int devFileId;
mutex_t serviceLock; /* for serviceRef[], services[] */
uint8_t serviceRef[SERVICES_MAX_COUNT]; /* a judge if set services[i]=NULL */
struct TagTcNsService *services[SERVICES_MAX_COUNT];
mutex_t sharedMemLock; /* for sharedMemList */
struct list_head sharedMemList;
struct list_head head;
/* Device is linked to call from kernel */
uint8_t kernelApi;
/* client login info provided by teecd, can be either package name and public
* key or uid(for non services/daemons)
* login information can only be set once, dont' allow subsequent calls
*/
bool loginSetup;
mutex_t LoginSetupLock; /* for loginSetup */
uint32_t pkgNameLen;
uint8_t PkgName[MAX_PACKAGE_NAME_LEN];
uint32_t pubKeyLen;
uint8_t pubKey[MAX_PUBKEY_LEN];
int loadAppFlag;
} TcNsDevFile;
typedef union {
struct {
unsigned int buffer;
unsigned int size;
} memref;
struct {
unsigned int a;
unsigned int b;
} value;
} TcNsParameter;
typedef struct TagTcNsLogin {
unsigned int method;
unsigned int mdata;
} tc_ns_login;
typedef struct TagTcNsOperation {
unsigned int paramTypes;
TcNsParameter params[TEE_PARAM_NUM];
unsigned int bufferHaddr[TEE_PARAM_NUM];
struct TagTcNsSharedMem *sharemem[TEE_PARAM_NUM];
void *mbBuffer[TEE_PARAM_NUM];
} TcNsOperation;
typedef struct TagTcNsTempBuf {
void *tempBuffer;
unsigned int size;
} TcNsTempBuf;
typedef struct TagTcNsSmcCmd {
uint8_t uuid[sizeof(TeecUuid)];
bool globalCmd; /* mark it's a gtask cmd */
unsigned int cmdId;
unsigned int devFileId;
unsigned int contextId;
unsigned int agentId;
unsigned int operationPhys;
unsigned int operationHphys;
unsigned int loginMethod;
unsigned int loginDataPhy;
unsigned int loginDataHaddr;
unsigned int loginDataLen;
unsigned int errOrigin;
int retVal;
unsigned int eventNr;
unsigned int uid;
#ifdef CONFIG_TEE_SMP
unsigned int caPid;
#endif
#ifdef SECURITY_AUTH_ENHANCE
unsigned int tokenPhys;
unsigned int tokenHphys;
unsigned int pid;
unsigned int paramsPhys;
unsigned int paramsHphys;
unsigned int eventindex; // tee audit event index for upload
#endif
bool started;
}__attribute__((__packed__))TcNsSmcCmd;
typedef struct TagTcNsSharedMem {
void *kernelAddr;
void *userAddr;
void *userAddrCa; /* for ca alloc share mem */
unsigned int len;
struct list_head head;
atomic_t usage;
atomic_t offset;
} TcNsSharedMem;
typedef struct TagTcNsService {
unsigned char uuid[UUID_LEN];
mutex_t SessionLock; /* for sessionList */
struct list_head sessionList;
struct list_head head;
mutex_t operationLock; /* for session's open/close */
atomic_t usage;
} TcNsService;
/*
* @brief
*/
struct TcWaitData {
wait_queue_head_t sendCmdWq;
int sendWaitFlag;
};
#ifdef SECURITY_AUTH_ENHANCE
/* Using AES-CBC algorithm to encrypt communication between secure world and
* normal world.
*/
#define CIPHER_KEY_BYTESIZE 32 /* AES-256 key size */
#define IV_BYTESIZE 16 /* AES-CBC encryption initialization vector size */
#define CIPHER_BLOCK_BYTESIZE 16 /* AES-CBC cipher block size */
#define SCRAMBLING_NUMBER 3
#define CHKSUM_LENGTH (sizeof(TcNsSmcCmd) - sizeof(uint32_t))
#define HASH_PLAINTEXT_SIZE (MAX_SHA_256_SZ + sizeof(struct EncryptionHead))
#define HASH_PLAINTEXT_ALIGNED_SIZE \
ALIGN_TZ(HASH_PLAINTEXT_SIZE, CIPHER_BLOCK_BYTESIZE)
enum SCRAMBLING_ID {
SCRAMBLING_TOKEN = 0,
SCRAMBLING_OPERATION = 1,
SCRAMBLING_MAX = SCRAMBLING_NUMBER
};
struct SessionCryptoInfo {
uint8_t key[CIPHER_KEY_BYTESIZE]; /* AES-256 key */
uint8_t iv[IV_BYTESIZE]; /* AES-CBC encryption initialization vector */
};
struct SessionSecureInfo {
uint32_t challengeWord;
uint32_t scrambling[SCRAMBLING_NUMBER];
struct SessionCryptoInfo cryptoInfo;
};
#define MAGIC_SIZE 16
#define MAGIC_STRING "Trusted-magic"
/* One encrypted block, which is aligned with CIPHER_BLOCK_BYTESIZE bytes
* Head + Payload + Padding
*/
struct EncryptionHead {
int8_t magic[MAGIC_SIZE];
uint32_t payloadLen;
};
struct SessionSecureParams {
struct EncryptionHead head;
union {
struct {
uint32_t challengeWord;
} ree2tee;
struct {
uint32_t scrambling[SCRAMBLING_NUMBER];
struct SessionCryptoInfo cryptoInfo;
} tee2ree;
} payload;
};
#endif
#ifdef SECURITY_AUTH_ENHANCE
typedef struct TagTcNsToken {
/* 42byte, token_32byte + timestamp_8byte + kernal_api_1byte + sync_1byte */
uint8_t *tokenBuffer;
uint32_t tokenLen;
} TcNsToken;
#endif
#define NUM_OF_SO 1
#define KIND_OF_SO 2
typedef struct TagTcNsSession {
unsigned int sessionId;
struct list_head head;
struct TcWaitData waitData;
mutex_t taSessionLock; /* for open/close/invoke on 1 session */
TcNsDevFile *owner;
#ifdef SECURITY_AUTH_ENHANCE
/* Session secure enhanced information */
struct SessionSecureInfo secureInfo;
TcNsToken TcNsToken;
/* when SECURITY_AUTH_ENHANCE enabled, hash of the same CA and
* SO library will be encrypted by different session key,
* so put authHashBuf in TcNsSession.
* the first MAX_SHA_256_SZ size stores SO hash,
* the next HASH_PLAINTEXT_ALIGNED_SIZE stores CA hash and cryptohead,
* the last IV_BYTESIZE size stores aes iv
*/
uint8_t authHashBuf[MAX_SHA_256_SZ * NUM_OF_SO + HASH_PLAINTEXT_ALIGNED_SIZE + IV_BYTESIZE];
#else
uint8_t authHashBuf[MAX_SHA_256_SZ * NUM_OF_SO + MAX_SHA_256_SZ];
#endif
atomic_t usage;
} TcNsSession;
void GetServiceStruct(struct TagTcNsService *service);
void PutServiceStruct(struct TagTcNsService *service);
static inline void GetSessionStruct(struct TagTcNsSession *session)
{
if (session != NULL) {
atomic_inc(&session->usage);
}
}
void PutSessionStruct(struct TagTcNsSession *session);
TcNsSession *TcFindSessionWithOwner(struct list_head *sessionList,
unsigned int sessionId, TcNsDevFile *dev);
#ifdef SECURITY_AUTH_ENHANCE
int GenerateEncryptedSessionSecureParams(
const struct SessionSecureInfo *secureInfo,
uint8_t *encSecureParams, size_t encParamsSize);
#define ENCRYPT 1
#define DECRYPT 0
int CryptoSessionAescbcKey256(uint8_t *in, uint32_t inLen,
uint8_t *out, uint32_t out_len,
const uint8_t *key, uint8_t *iv,
uint32_t mode);
int CryptoAescbcCmsPadding(uint8_t *plaintext, uint32_t plaintextLen,
uint32_t payloadLen);
#endif
int TcNsClientOpen(TcNsDevFile **devFile, uint8_t kernelApi);
int TcNsClientClose(TcNsDevFile *dev);
int IsAgentAlive(unsigned int agentId);
int TcNsOpenSession(TcNsDevFile *devFile, TcNsClientContext *context);
int TcNsCloseSession(TcNsDevFile *devFile, TcNsClientContext *context);
int TcNsSendCmd(TcNsDevFile *devFile, TcNsClientContext *context);
uint32_t TcNsGetUid(void);
#endif
-39
View File
@@ -1,39 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TZ_SPI_NOTIFY_H_
#define _TZ_SPI_NOTIFY_H_
#include "teek_ns_client.h"
int TzSpiInit(void);
void TzSpiExit(void);
int TcNsTstCmd(TcNsDevFile *devId, void *argp);
#endif
-57
View File
@@ -1,57 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TZDEBUG_H_
#define _TZDEBUG_H_
#include <linux/types.h>
struct ta_mem {
char taName[16];
uint32_t pmem;
uint32_t pmemMax;
uint32_t pmemLimit;
};
#define MEMINFO_TA_MAX 100
struct TeeMem {
uint32_t totalMem;
uint32_t pmem;
uint32_t freeMem;
uint32_t freeMemMin;
uint32_t taNum;
struct ta_mem TaMemInfo[MEMINFO_TA_MAX];
};
int GetTeeMeminfo(struct TeeMem *meminfo);
void TeeDumpMem(void);
int TzdebugInit(void);
#endif
-38
View File
@@ -1,38 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef _TZDRIVER_H
#define _TZDRIVER_H
int TcInit(void);
void SetVmmRegionCodeStart(UINTPTR codeStart, UINT32 codeSize);
#endif
-385
View File
@@ -1,385 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __TZDRIVER_COMPAT_H
#define __TZDRIVER_COMPAT_H
#include <linux/interrupt.h>
#include <linux/kernel.h>
#include <linux/workqueue.h>
#include "arm.h"
#include "fs/driver.h"
#include "hisoc/random.h"
#include "los_process_pri.h"
#include "los_sched_pri.h"
#include "los_task_pri.h"
#include "los_vm_lock.h"
#include "los_vm_map.h"
#include "los_vm_phys.h"
#include "mbedtls/sha256.h"
/* TEE config */
#define DEF_ENG 1
#define CONFIG_TEE_SMP 1
#define CONFIG_TEELOG 1
#define CONFIG_CPU_AFF_NR 0
#define CONFIG_TEE_SMP 1
/* TEE config end */
#define VERIFY_READ 0
#define VERIFY_WRITE 1
#define MAX_DEV_NAME_SIZE 32
#define SHA256_DIGEST_LENGTH 32
#define ALIGN_TZ(x, boundary) (((x) + ((boundary) - 1)) & ~((boundary) - 1))
#ifndef ARRAY_SIZE
#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
#endif
typedef pthread_mutex_t mutex_t;
#ifndef IS_ERR_OR_NULL
#ifndef IS_ERR_VALUE
#define IS_ERR_VALUE(x) unlikely((unsigned long)(void *)(x) >= (unsigned long) - 4095)
#endif
#define IS_ERR_OR_NULL(x) ((!x) || IS_ERR_VALUE((UINTPTR)x))
#endif
#define TEE_DEV_PRI 0660
#define TASK_COMM_LEN OS_TCB_NAME_LEN
#define WQ_HIGHPRI (1 << 4)
#define IRQF_NO_SUSPEND 0x00004000
#define __GFP_ZERO 0x8000u
#define SZ_4K 0x1000UL
#define SZ_1M (1024 * 1024)
#define SZ_4M (4 * SZ_1M)
#define SZ_8M (8 * SZ_1M)
#define MAX_POW_TWO(n) \
( \
((n) >> 31) ? 31 : ((n) >> 30) ? 30 : \
((n) >> 29) ? 29 : ((n) >> 28) ? 28 : \
((n) >> 27) ? 27 : ((n) >> 26) ? 26 : \
((n) >> 25) ? 25 : ((n) >> 25) ? 25 : \
((n) >> 23) ? 23 : ((n) >> 22) ? 22 : \
((n) >> 21) ? 21 : ((n) >> 20) ? 20 : \
((n) >> 19) ? 19 : ((n) >> 18) ? 18 : \
((n) >> 17) ? 17 : ((n) >> 16) ? 16 : \
((n) >> 15) ? 15 : ((n) >> 14) ? 14 : \
((n) >> 13) ? 13 : ((n) >> 12) ? 12 : \
((n) >> 11) ? 11 : ((n) >> 10) ? 10 : \
((n) >> 9) ? 9: ((n) >> 8) ? 8 : \
((n) >> 7) ? 7: ((n) >> 6) ? 6 : \
((n) >> 5) ? 5: ((n) >> 4) ? 4 : \
((n) >> 3) ? 3: ((n) >> 2) ? 2 : 1)
#define GET_ORDER(n) \
( \
n <= PAGE_SIZE ? 0 : (MAX_POW_TWO(n - 1) - PAGE_SHIFT + 1) \
)
#ifndef MSEC_PER_SEC
#define MSEC_PER_SEC 1000
#endif
#ifndef NSEC_PER_MSEC
#define NSEC_PER_MSEC 1000000L
#endif
#ifndef USEC_PER_SEC
#define USEC_PER_SEC 1000000L
#endif
#ifndef NSEC_PER_USEC
#define NSEC_PER_USEC 1000
#endif
#define CRASH_RET_EXIT 0
#define CRASH_RET_TA 1
#define CRASH_RET_IP 2
#undef DIV_ROUND_UP
#define DIV_ROUND_UP(n, d) (((n) + (d)-1) / (d))
#undef BITS_PER_BYTE
#define BITS_PER_BYTE 8
#undef BITS_PER_LONG
#define BITS_PER_LONG 64
#undef BITS_TO_LONGS
#define BITS_TO_LONGS(nr) DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(uint64_t))
#undef BIT_MASK
#define BIT_MASK(nr) (1UL << ((nr) % BITS_PER_LONG))
#undef BIT_WORD
#define BIT_WORD(nr) ((nr) / BITS_PER_LONG)
#undef DECLARE_BITMAP
#define DECLARE_BITMAP(name, bits) uint64_t name[BITS_TO_LONGS(bits)]
#define INIT_WORK_ONSTACK(_work, _func) \
do { \
INIT_WORK(_work, _func); \
} while (0)
bool ScheduleWorkOn(int cpu, struct work_struct *work);
#define __WORK_INIT(n, f) { \
.data = 0, \
.entry = { &(n).entry, &(n).entry }, \
.func = f \
}
#define DECLARE_WORK(work, func) \
struct work_struct work = __WORK_INIT(work, func);
#define noinline __attribute__((noinline))
LosTaskCB *KthreadRun(int (*threadfn)(UINTPTR data, int dataLen), void *data, int len, char *name);
void KthreadStop(const LosTaskCB *k);
int KthreadShouldStop(void);
INT32 DoVmallocRemap(LosVmMapRegion *vma, void *kvaddr);
int RemapVmallocRange(LosVmMapRegion *vma, void *addr, unsigned long pgoff);
int CreateTcClientDevice(const char *devName, const struct file_operations_vfs *op);
ssize_t SimpleReadFromBuffer(void *to, size_t count, const void *from, size_t available);
LosVmPage *MailboxPoolAllocPages(unsigned int order);
void MailboxPoolFreePages(LosVmPage *pageArray, size_t order);
struct AesParam {
unsigned char *iv;
const unsigned char *key;
int size;
unsigned int encryptoType;
};
int CryptoAescbcKey256(unsigned char *output, const unsigned char *input, struct AesParam *param);
#define INT_SIZE 4
static inline struct workqueue_struct *AllocOrderedWorkqueue(const char *fmt, unsigned int flags)
{
return create_workqueue((char *)fmt);
}
static inline int AccessOk(int type, unsigned long ptr, unsigned int size)
{
if (ptr + size < ptr) {
return false;
}
return LOS_IsUserAddress(ptr + size);
}
static inline int GetTaskUid(LosTaskCB *task)
{
#ifdef LOSCFG_SECURITY_CAPABILITY
return (int)OsProcessUserIDGet(task);
#else
return 0;
#endif
}
static inline int DevmRequestIrq(unsigned int irq, irq_handler_t handler,
unsigned long irqflags, const char *devname, void *devId)
{
return request_irq(irq, handler, irqflags, devname, NULL);
}
static inline void *GetPhyPage(void)
{
LosVmPage *page = LOS_PhysPageAlloc();
if (page == NULL) {
return NULL;
}
return OsVmPageToVaddr(page);
}
static inline void FreePhyPage(void *ptr)
{
if (ptr == NULL) {
return;
}
LosVmPage *page = OsVmVaddrToPage(ptr);
if (page != NULL) {
LOS_PhysPageFree(page);
}
}
static inline void KthreadBindMask(LosTaskCB *p, UINT16 mask)
{
if (p == NULL) {
return;
}
LOS_TaskCpuAffiSet(p->taskID, mask);
}
static inline void HmSetBit(int nr, volatile uint64_t *addr)
{
if (addr == NULL) {
return;
}
uint64_t mask = BIT_MASK(nr);
uint64_t *p = ((uint64_t *)addr) + BIT_WORD(nr);
*p |= mask;
}
static inline void HmClearBit(int nr, volatile uint64_t *addr)
{
if (addr == NULL) {
return;
}
uint64_t mask = BIT_MASK(nr);
uint64_t *p = ((uint64_t *)addr) + BIT_WORD(nr);
*p &= ~mask;
}
static inline int HmTestBit(int nr, const volatile uint64_t *addr)
{
if (addr == NULL) {
return 0;
}
return 1UL & (addr[BIT_WORD(nr)] >> (nr & (BITS_PER_LONG - 1)));
}
static inline void PreemptDisable(void)
{
UINT32 intSave = LOS_IntLock();
OsSchedLock();
LOS_IntRestore(intSave);
}
static inline void PreemptEnable(void)
{
UINT32 intSave = LOS_IntLock();
OsSchedUnlock();
LOS_IntRestore(intSave);
}
static inline int CmpXchg(unsigned int *lock, int old, int new)
{
return LOS_AtomicCmpXchg32bits((Atomic *)lock, new, old);
}
static inline int RawSmpProcessorId(void)
{
return ArchCurrCpuid();
}
static inline int WakeUpProcess(LosTaskCB *p)
{
LOS_TaskYield();
return 0;
}
static inline void GetRandomBytesArch(void *data, uint32_t size)
{
HiRandomHwGetNumber((char *)data, size);
}
static inline void GetUser(unsigned int *value, const unsigned int *userPtr)
{
copy_from_user(value, userPtr, sizeof(unsigned int));
}
static inline int GetCurrentPid(void)
{
return OsCurrTaskGet()->processID;
}
/* unsupport restart syscall */
static inline int RestartSyscall(void)
{
return 0;
}
static inline LosTaskCB *GetProcessGroupLeader(LosTaskCB *task)
{
if (task == NULL) {
return NULL;
}
return OS_TCB_FROM_TID(OsProcessThreadGroupIDGet(task));
}
static inline unsigned long MsecsToJiffies(const unsigned int m)
{
if ((int)m < 0) {
return 0;
}
return (m + (MSEC_PER_SEC / HZ) - 1) / (MSEC_PER_SEC / HZ);
}
static inline struct timespec CurrentKernelTime(void)
{
struct timespec ts;
clock_gettime(CLOCK_MONOTONIC_RAW, &ts);
return ts;
}
static inline void InitDeferrableWork(struct delayed_work *w, void(* wq)(struct work_struct *))
{
INIT_DELAYED_WORK(w, wq);
}
static inline int IsKernelThread(LosTaskCB *task)
{
if (task == NULL) {
return true;
}
return !(OsProcessIsUserMode(OS_PCB_FROM_PID(task->processID)));
}
static inline int IsTeecdProcess(LosTaskCB *teecd, LosTaskCB *task)
{
if (teecd == NULL || task == NULL) {
return 0;
}
return teecd->processID == task->processID;
}
typedef mbedtls_sha256_context TeeSha256Context;
static inline void TeeSha256Init(TeeSha256Context *ctx)
{
mbedtls_sha256_init(ctx);
(void)mbedtls_sha256_starts_ret(ctx, 0);
}
static inline void TeeSha256Update(TeeSha256Context *ctx, const unsigned char *input, size_t ilen)
{
(void)mbedtls_sha256_update_ret(ctx, input, ilen);
}
static inline void TeeSha256Final(TeeSha256Context *ctx, unsigned char output[32])
{
(void)mbedtls_sha256_finish_ret(ctx, output);
}
#endif
-1256
View File
File diff suppressed because it is too large Load Diff
-337
View File
@@ -1,337 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "cmdmonitor.h"
#include <securec.h>
#include "smc.h"
#include "tc_ns_log.h"
#include "tzdriver_compat.h"
const char g_cmdMonitorWhiteTable[][TASK_COMM_LEN] = {
#ifdef DEF_ENG
{"tee_test_ut"},
#endif
};
const uint32_t g_whiteTableThreadNum = sizeof(g_cmdMonitorWhiteTable) /
TASK_COMM_LEN;
static int g_cmdNeedArchiveLog = 0;
static LINUX_LIST_HEAD(g_cmdMonitorList);
static int g_cmdMonitorListSize = 0;
/* report 2 hours */
#define MAX_CMD_MONITOR_LIST 200
#define MAX_AGENT_CALL_COUNT 250
static DEFINE_MUTEX(g_cmdMonitorLock);
struct CmdMonitor {
struct list_head list;
struct timespec sendTime;
int count;
bool returned;
bool isReported;
int pid;
int tid;
char pName[TASK_COMM_LEN];
char tName[TASK_COMM_LEN];
unsigned int lastCmdId;
long long timeTotal;
int agentCallCount;
};
static struct delayed_work g_cmdMonitorWork;
static struct delayed_work g_cmdMonitorWorkArchive;
static int g_teeDetectTaCrash = 0;
enum {
TYPE_CRASH_TA = 1,
TYPE_CRASH_TEE = 2,
};
void TzDebugArchiveLog(void)
{
schedule_delayed_work(&g_cmdMonitorWorkArchive, MsecsToJiffies(0));
}
void CmdMonitorTaCrash(int32_t type)
{
g_teeDetectTaCrash = ((type == TYPE_CRASH_TEE) ? TYPE_CRASH_TEE :
TYPE_CRASH_TA);
TzDebugArchiveLog();
}
static bool IsThreadInWhiteTable(const char *tName)
{
uint32_t i;
if (tName == NULL) {
return false;
}
for (i = 0; i < g_whiteTableThreadNum; i++) {
if (!strcmp(tName, g_cmdMonitorWhiteTable[i])) {
return true;
}
}
return false;
}
bool IsThreadReported(unsigned int tid)
{
bool ret = false;
struct CmdMonitor *monitor = NULL;
mutex_lock(&g_cmdMonitorLock);
list_for_each_entry(monitor, &g_cmdMonitorList, list) {
if (monitor->tid == tid) {
ret = (monitor->isReported ||
monitor->agentCallCount > MAX_AGENT_CALL_COUNT);
break;
}
}
mutex_unlock(&g_cmdMonitorLock);
return ret;
}
void CmdMonitorResetContext(void)
{
struct CmdMonitor *monitor = NULL;
int pid = OsCurrTaskGet()->processID;
int tid = OsCurrTaskGet()->taskID;
mutex_lock(&g_cmdMonitorLock);
list_for_each_entry(monitor, &g_cmdMonitorList, list) {
if (monitor->pid == pid && monitor->tid == tid) {
monitor->sendTime = CurrentKernelTime();
if (monitor->agentCallCount + 1 < 0) {
tloge("agent call count add overflow\n");
} else {
monitor->agentCallCount++;
}
break;
}
}
mutex_unlock(&g_cmdMonitorLock);
}
static void CmdMonitorTick(void)
{
long long timeDif;
struct CmdMonitor *monitor = NULL;
struct CmdMonitor *tmp = NULL;
struct timespec nowTime = CurrentKernelTime();
mutex_lock(&g_cmdMonitorLock);
list_for_each_entry_safe(monitor, tmp, &g_cmdMonitorList, list) {
if (monitor->returned == true) {
g_cmdMonitorListSize--;
tloge("[CmdMonitorTick] pid:%d, pName:%s, tid:%d, tName:%s, \
lastCmdId:%u, count:%d, agent call count:%d, timeTotal:%lld us returned, remained command(s):%d\n",
monitor->pid, monitor->pName, monitor->tid,
monitor->tName, monitor->lastCmdId,
monitor->count, monitor->agentCallCount,
monitor->timeTotal, g_cmdMonitorListSize);
list_del(&monitor->list);
free(monitor);
monitor = NULL;
continue;
}
/* not return, we need to check */
/*
* get time value D (timeDif=nowTime-sendTime), we do not care about overflow
* 1 year means 1000 * (60*60*24*365) = 0x757B12C00
* only 5bytes, will not overflow
*/
timeDif = MSEC_PER_SEC * (nowTime.tv_sec - monitor->sendTime.tv_sec) +
(nowTime.tv_nsec - monitor->sendTime.tv_nsec) / NSEC_PER_MSEC;
/* Temporally change timeout to 25s, we log the teeos log,and report */
if ((timeDif > TEMPORALLY_CHAGE_TIMEOUT) && (!monitor->isReported)) {
monitor->isReported = true;
/* print tee stask */
tloge("[CmdMonitorTick] pid:%d, pName:%s, tid:%d, tName:%s, \
lastCmdId:%u, agent call count:%d, timeDif:%lld ms and report\n",
monitor->pid, monitor->pName, monitor->tid,
monitor->tName, monitor->lastCmdId,
monitor->agentCallCount, timeDif);
/* threads out of white table need info dump */
if (!(IsThreadInWhiteTable(monitor->tName))) {
ShowCmdBitmapWithLock();
g_cmdNeedArchiveLog = 1;
WakeupTcSiq();
}
} else if (timeDif > 1 * MSEC_PER_SEC) {
tloge("[CmdMonitorTick] pid=%d, pName=%s, tid=%d, \
lastCmdId=%u, agent call count:%d, timeDif=%lld ms\n",
monitor->pid, monitor->pName, monitor->tid,
monitor->lastCmdId, monitor->agentCallCount,
timeDif);
}
}
if (g_cmdMonitorListSize > 0) {
/* if have cmd in monitor list, we need tick */
schedule_delayed_work(&g_cmdMonitorWork, MsecsToJiffies(MSEC_PER_SEC));
}
mutex_unlock(&g_cmdMonitorLock);
}
static void CmdMonitorTickfn(struct work_struct *work)
{
(void)(work);
CmdMonitorTick();
}
static void CmdMonitorArchivefn(struct work_struct *work)
{
(void)(work);
}
static struct CmdMonitor *InitMonitorLocked(void)
{
struct CmdMonitor *newItem = NULL;
newItem = calloc(1, sizeof(*newItem));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)newItem)) {
tloge("[CmdMonitorTick]calloc failed\n");
return NULL;
}
newItem->sendTime = CurrentKernelTime();
newItem->count = 1;
newItem->agentCallCount = 0;
newItem->returned = false;
newItem->isReported = false;
newItem->pid = OsCurrTaskGet()->processID;
newItem->tid = OsCurrTaskGet()->taskID;
LosProcessCB *runProcess = OS_PCB_FROM_PID(newItem->pid);
if (strncpy_s(newItem->pName, TASK_COMM_LEN, runProcess->processName, OS_PCB_NAME_LEN) != EOK) {
free(newItem);
newItem = NULL;
return NULL;
}
if (strncpy_s(newItem->tName, TASK_COMM_LEN, OsCurrTaskGet()->taskName, OS_TCB_NAME_LEN) != EOK) {
free(newItem);
newItem = NULL;
return NULL;
}
INIT_LIST_HEAD(&newItem->list);
list_add_tail(&newItem->list, &g_cmdMonitorList);
g_cmdMonitorListSize++;
return newItem;
}
void CmdMonitorLog(const TcNsSmcCmd *cmd)
{
int foundFlag = 0;
int pid;
int tid;
struct CmdMonitor *monitor = NULL;
struct CmdMonitor *newItem = NULL;
if (cmd == NULL) {
return;
}
pid = OsCurrTaskGet()->processID;
tid = OsCurrTaskGet()->taskID;
mutex_lock(&g_cmdMonitorLock);
do {
list_for_each_entry(monitor, &g_cmdMonitorList, list) {
if (monitor->pid == pid && monitor->tid == tid) {
foundFlag = 1;
/* restart */
monitor->sendTime = CurrentKernelTime();
monitor->count++;
monitor->returned = false;
monitor->isReported = false;
monitor->lastCmdId = cmd->cmdId;
monitor->agentCallCount = 0;
break;
}
}
if (foundFlag == 0) {
if (g_cmdMonitorListSize > MAX_CMD_MONITOR_LIST - 1) {
tloge("[CmdMonitorTick]MAX_CMD_MONITOR_LIST\n");
break;
}
newItem = InitMonitorLocked();
if (newItem == NULL) {
tloge("[CmdMonitorTick]init_monitor failed\n");
break;
}
newItem->lastCmdId = cmd->cmdId;
/* the first cmd will cause timer */
if (g_cmdMonitorListSize == 1) {
schedule_delayed_work(&g_cmdMonitorWork,
MsecsToJiffies(MSEC_PER_SEC));
}
}
} while (0);
mutex_unlock(&g_cmdMonitorLock);
}
void CmdMonitorLogend(void)
{
int pid;
int tid;
struct CmdMonitor *monitor = NULL;
pid = OsCurrTaskGet()->processID;
tid = OsCurrTaskGet()->taskID;
mutex_lock(&g_cmdMonitorLock);
list_for_each_entry(monitor, &g_cmdMonitorList, list) {
if (monitor->pid == pid && monitor->tid == tid &&
monitor->returned == false) {
struct timespec nowTime = CurrentKernelTime();
/*
* get time value D (timeDif=nowTime-sendTime), we do not care about overflow
* 1 year means 1000000 * (60*60*24*365) = 0x1CAE8C13E000
* only 6bytes, will not overflow
*/
long long timeDif = USEC_PER_SEC *
(nowTime.tv_sec - monitor->sendTime.tv_sec) +
(nowTime.tv_nsec - monitor->sendTime.tv_nsec) / NSEC_PER_USEC;
monitor->timeTotal += timeDif;
monitor->returned = true;
break;
}
}
mutex_unlock(&g_cmdMonitorLock);
}
void DoCmdNeedArchivelog(void)
{
if (g_cmdNeedArchiveLog == 1) {
g_cmdNeedArchiveLog = 0;
schedule_delayed_work(&g_cmdMonitorWorkArchive,
MsecsToJiffies(MSEC_PER_SEC));
}
}
void InitCmdMonitor(void)
{
InitDeferrableWork((struct delayed_work *)(uintptr_t)&g_cmdMonitorWork, CmdMonitorTickfn);
InitDeferrableWork((struct delayed_work *)(uintptr_t)&g_cmdMonitorWorkArchive, CmdMonitorArchivefn);
}
File diff suppressed because it is too large Load Diff
-568
View File
@@ -1,568 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "mailbox_mempool.h"
#include <securec.h>
#include "smc.h"
#include "tc_ns_log.h"
#include "teek_client_constants.h"
#include "tzdriver_compat.h"
#define MAILBOX_PAGE_MAX (MAILBOX_POOL_SIZE >> PAGE_SHIFT)
#define MAILBOX_ORDER_MAX GET_ORDER(MAILBOX_POOL_SIZE)
static unsigned int g_mailboxMaxOrder = MAILBOX_ORDER_MAX;
struct MbPageT {
struct list_head node;
LosVmPage *page;
int order; // block size
unsigned int count; // whether be used
};
struct MbFreeAreaT {
struct list_head pageList;
int order;
};
struct MbZoneT {
LosVmPage *allPages;
struct MbPageT pages[MAILBOX_PAGE_MAX];
struct MbFreeAreaT freeAreas[MAILBOX_ORDER_MAX + 1];
};
static struct MbZoneT g_mZone;
static mutex_t g_mbLock;
#ifdef DEF_ENG
static void MailboxShowStatus(void)
{
unsigned int i;
struct MbPageT *pos = NULL;
struct list_head *head = NULL;
unsigned int used = 0;
pr_info("########################################\n");
mutex_lock(&g_mbLock);
for (i = 0; i < MAILBOX_PAGE_MAX; i++) {
if (g_mZone.pages[i].count) {
pr_info("page[%02d], order=%02d, count=%d\n", i, g_mZone.pages[i].order, g_mZone.pages[i].count);
used += (1UL << (uint32_t)g_mZone.pages[i].order);
}
}
pr_info("total usage:%u/%u\n", used, MAILBOX_PAGE_MAX);
pr_info("----------------------------------------\n");
for (i = 0; i < g_mailboxMaxOrder; i++) {
head = &g_mZone.freeAreas[i].pageList;
if (list_empty(head)) {
pr_info("order[%02d] is empty\n", i);
} else {
list_for_each_entry(pos, head, node)
pr_info("order[%02d]\n", i);
}
}
mutex_unlock(&g_mbLock);
pr_info("########################################\n");
}
#define MB_SHOW_LINE 64
#define BITS_OF_BYTE 8
static void MailboxShowDetails(void)
{
unsigned int i;
unsigned int used = 0;
unsigned int left = 0;
unsigned int order = 0;
pr_info("----- show mailbox details -----");
mutex_lock(&g_mbLock);
for (i = 0; i < MAILBOX_PAGE_MAX; i++) {
if ((i % MB_SHOW_LINE) == 0) {
PRINTK("\n");
PRINTK("%04d-%04d:", i, i + MB_SHOW_LINE);
}
if (g_mZone.pages[i].count) {
left = 1 << (uint32_t)g_mZone.pages[i].order;
order = g_mZone.pages[i].order;
used += (1UL << (uint32_t)g_mZone.pages[i].order);
}
if (left) {
left--;
PRINTK("%01d", order);
} else {
PRINTK("X");
}
if (i > 1 && (i + 1) % (MB_SHOW_LINE / BITS_OF_BYTE) == 0) {
PRINTK(" ");
}
}
pr_info("\ntotal usage:%u/%u\n", used, MAILBOX_PAGE_MAX);
mutex_unlock(&g_mbLock);
}
#endif
void *MailboxAlloc(size_t size, unsigned int flag)
{
unsigned int i;
struct MbPageT *pos = (struct MbPageT *)NULL;
struct list_head *head = NULL;
unsigned int order = GET_ORDER(ALIGN(size, SZ_4K));
void *addr = NULL;
if (size == 0) {
tlogw("alloc 0 size mailbox\n");
return NULL;
}
if (order > g_mailboxMaxOrder) {
tloge("invalid order %d\n", order);
return NULL;
}
mutex_lock(&g_mbLock);
for (i = order; i <= g_mailboxMaxOrder; i++) {
unsigned int j;
head = &g_mZone.freeAreas[i].pageList;
if (list_empty(head)) {
continue;
}
pos = list_first_entry(head, struct MbPageT, node);
pos->count = 1;
pos->order = order;
/* split and add free list */
for (j = order; j < i; j++) {
struct MbPageT *newPage = NULL;
newPage = pos + (1UL << j);
newPage->count = 0;
newPage->order = j;
list_add_tail(&newPage->node, &g_mZone.freeAreas[j].pageList);
}
list_del(&pos->node);
addr = OsVmPageToVaddr(pos->page);
break;
}
mutex_unlock(&g_mbLock);
if (addr != NULL && (flag & MB_FLAG_ZERO)) {
if (memset_s(addr, ALIGN(size, SZ_4K), 0,
ALIGN(size, SZ_4K)) != EOK) {
tloge("clean mailbox failed\n");
MailboxFree(addr);
return NULL;
}
}
return addr;
}
void MailboxFree(const void *ptr)
{
unsigned int i;
LosVmPage *page = NULL;
struct MbPageT *self = NULL;
struct MbPageT *buddy = NULL;
unsigned int selfIdx;
unsigned int buddyIdx;
if (ptr == NULL) {
tloge("invalid ptr\n");
return;
}
page = OsVmVaddrToPage((void *)ptr);
if (page < g_mZone.allPages ||
page >= (g_mZone.allPages + MAILBOX_PAGE_MAX)) {
tloge("invalid ptr to free in mailbox\n");
return;
}
mutex_lock(&g_mbLock);
selfIdx = page - g_mZone.allPages;
self = &g_mZone.pages[selfIdx];
if (!self->count) {
tloge("already freed in mailbox\n");
mutex_unlock(&g_mbLock);
return;
}
for (i = (unsigned int)self->order; i <=
g_mailboxMaxOrder; i++) {
selfIdx = page - g_mZone.allPages;
buddyIdx = selfIdx ^ (1UL << i);
self = &g_mZone.pages[selfIdx];
buddy = &g_mZone.pages[buddyIdx];
self->count = 0;
/* is buddy free */
if ((unsigned int)buddy->order == i && buddy->count == 0) {
/* release buddy */
list_del(&buddy->node);
/* combine self and buddy */
if (selfIdx > buddyIdx) {
page = buddy->page;
buddy->order = (int)i + 1;
self->order = -1;
} else {
self->order = (int)i + 1;
buddy->order = -1;
}
} else {
/* release self */
list_add_tail(&self->node, &g_mZone.freeAreas[i].pageList);
mutex_unlock(&g_mbLock);
return;
}
}
mutex_unlock(&g_mbLock);
}
struct MbCmdPack *MailboxAllocCmdPack(void)
{
void *pack = MailboxAlloc(SZ_4K, MB_FLAG_ZERO);
if (pack == NULL) {
tloge("alloc mb cmd pack failed\n");
}
return (struct MbCmdPack *)pack;
}
void *MailboxCopyAlloc(const void *src, size_t size)
{
void *mbPtr = NULL;
if ((src == NULL) || (size == 0)) {
tloge("invali src to alloc mailbox copy\n");
return NULL;
}
mbPtr = MailboxAlloc(size, 0);
if (mbPtr == NULL) {
tloge("alloc size(%zu) mailbox failed\n", size);
return NULL;
}
if (memcpy_s(mbPtr, size, src, size)) {
tloge("memcpy to mailbox failed\n");
MailboxFree(mbPtr);
return NULL;
}
return mbPtr;
}
#ifdef DEF_ENG
struct MbDbgEntry {
struct list_head node;
unsigned int idx;
void *ptr;
};
static LINUX_LIST_HEAD(g_mbDbgList);
static DEFINE_MUTEX(g_mbDbgLock);
static unsigned int g_mbDbgEntryCount = 1;
static unsigned int g_mbDbgLastRes; /* only cache 1 opt result */
static unsigned int MbDbgAddEntry(void *ptr)
{
struct MbDbgEntry *newEntry = NULL;
newEntry = malloc(sizeof(*newEntry));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)newEntry)) {
tloge("alloc entry failed\n");
return 0;
}
INIT_LIST_HEAD(&newEntry->node);
newEntry->ptr = ptr;
mutex_lock(&g_mbDbgLock);
newEntry->idx = g_mbDbgEntryCount;
/* to make sure g_mbDbgEntryCount==0 is invalid */
if ((g_mbDbgEntryCount++) == 0) {
g_mbDbgEntryCount++;
}
list_add_tail(&newEntry->node, &g_mbDbgList);
mutex_unlock(&g_mbDbgLock);
return newEntry->idx;
}
static void MbDbgRemoveEntry(unsigned int idx)
{
struct MbDbgEntry *pos = NULL;
mutex_lock(&g_mbDbgLock);
list_for_each_entry(pos, &g_mbDbgList, node) {
if (pos->idx == idx) {
MailboxFree(pos->ptr);
list_del(&pos->node);
free(pos);
mutex_unlock(&g_mbDbgLock);
return;
}
}
mutex_unlock(&g_mbDbgLock);
tloge("entry %u invalid\n", idx);
}
static void MbDbgReset(void)
{
struct MbDbgEntry *pos = NULL;
struct MbDbgEntry *tmp = NULL;
mutex_lock(&g_mbDbgLock);
list_for_each_entry_safe(pos, tmp, &g_mbDbgList, node) {
MailboxFree(pos->ptr);
list_del(&pos->node);
free(pos);
}
g_mbDbgEntryCount = 0;
mutex_unlock(&g_mbDbgLock);
}
#define MB_WRITE_SIZE 64
static int CheckDbgOptWrite(struct file *filp, const char __user *ubuf, char *obuf, size_t cnt)
{
bool checkValue = (filp == NULL);
if (checkValue || ubuf == NULL) {
return -EINVAL;
}
if (cnt >= MB_WRITE_SIZE || cnt == 0) {
return -EINVAL;
}
if (copy_from_user(obuf, ubuf, cnt)) {
return -EFAULT;
}
return 0;
}
static ssize_t MbDbgOptWrite(struct file *filp, const char __user *ubuf, size_t cnt)
{
char buf[MB_WRITE_SIZE] = {0};
char *cmd = NULL;
char *value = NULL;
char *endPtr = NULL;
int ret = CheckDbgOptWrite(filp, ubuf, buf, cnt);
if (ret) {
return ret;
}
buf[cnt] = 0;
value = buf;
if (!strncmp(value, "reset", strlen("reset"))) {
tlogi("mb dbg reset\n");
MbDbgReset();
return cnt;
}
cmd = strsep(&value, ":");
if (cmd == NULL || value == NULL) {
tloge("no valid cmd or value for mb dbg\n");
return -EFAULT;
}
if (!strncmp(cmd, "alloc", strlen("alloc"))) {
unsigned int allocSize = strtoul(value, &endPtr, 0);
if ((endPtr == NULL) || (*endPtr != 0)) {
tloge("invalid value format for mb dbg\n");
return cnt;
}
unsigned int idx;
void *ptr = MailboxAlloc(allocSize, 0);
if (ptr != NULL) {
idx = MbDbgAddEntry(ptr);
if (idx == 0) {
MailboxFree(ptr);
}
g_mbDbgLastRes = idx;
} else {
tloge("alloc order=%u in mailbox failed\n", allocSize);
}
} else if (!strncmp(cmd, "free", strlen("free"))) {
unsigned int freeIdx = strtoul(value, &endPtr, 0);
if ((endPtr == NULL) || (*endPtr != 0)) {
tloge("invalid value format for mb dbg\n");
return cnt;
}
MbDbgRemoveEntry(freeIdx);
} else {
tloge("invalid format for mb dbg\n");
}
return cnt;
}
#define DBG_READ_BUFSIZE 16
static ssize_t MbDbgOptRead(struct file *filp, char __user *ubuf,
size_t cnt)
{
char buf[DBG_READ_BUFSIZE] = {0};
ssize_t ret;
(void)(filp);
ret = snprintf_s(buf, sizeof(buf), sizeof(buf) - 1, "%u\n", g_mbDbgLastRes);
if (ret < 0) {
tloge("snprintf idx failed\n");
return -EINVAL;
}
return SimpleReadFromBuffer(ubuf, cnt, buf, ret);
}
static const struct file_operations_vfs g_mbDbgOptFops = {
.read = MbDbgOptRead,
.write = MbDbgOptWrite,
};
static ssize_t MbDbgStateRead(struct file *filp, char __user *ubuf,
size_t cnt)
{
(void)(filp);
(void)(ubuf);
MailboxShowStatus();
MailboxShowDetails();
return 0;
}
static const struct file_operations_vfs mb_dbg_state_fops = {
.read = MbDbgStateRead,
};
#endif
static int MailboxRegister(const void *mbPool, unsigned int size)
{
TcNsOperation *operation = NULL;
TcNsSmcCmd *smcCmd = NULL;
int ret = 0;
smcCmd = calloc(1, sizeof(*smcCmd));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)smcCmd)) {
tloge("alloc smcCmd failed\n");
return -EIO;
}
operation = calloc(1, sizeof(*operation));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)operation)) {
tloge("alloc operation failed\n");
ret = -EIO;
goto FREE_SMC_CMD;
}
operation->paramTypes = TEE_PARAM_TYPE_VALUE_INPUT |
(TEE_PARAM_TYPE_VALUE_INPUT << TEE_PARAM_NUM);
operation->params[TEE_PARAM_ONE].value.a = LOS_PaddrQuery((void *)mbPool);
operation->params[TEE_PARAM_ONE].value.b = 0;
operation->params[TEE_PARAM_TWO].value.a = size;
smcCmd->globalCmd = true;
smcCmd->cmdId = GLOBAL_CMD_ID_REGISTER_MAILBOX;
smcCmd->operationPhys = LOS_PaddrQuery(operation);
smcCmd->operationHphys = 0;
ret = TcNsSmc(smcCmd);
if (ret != TEEC_SUCCESS) {
tloge("resigter mailbox failed\n");
ret = -EIO;
}
free(operation);
operation = NULL;
FREE_SMC_CMD:
free(smcCmd);
smcCmd = NULL;
return ret;
}
#define TC_NS_CLIENT_MEILBOX_OPT_NAME "/dev/tz_mailbox_opt"
#define TC_NS_CLIENT_MEILBOX_STATE_NAME "/dev/tz_mailbox_state"
int MailboxMempoolInit(void)
{
int i;
struct MbPageT *mbPage = NULL;
struct MbFreeAreaT *area = NULL;
LosVmPage *allPages = NULL;
allPages = MailboxPoolAllocPages(g_mailboxMaxOrder);
if (allPages == NULL) {
tloge("fail to alloc mailbox mempool\n");
return -ENOMEM;
}
if (MailboxRegister(OsVmPageToVaddr(allPages), MAILBOX_POOL_SIZE)) {
tloge("register mailbox failed\n");
MailboxPoolFreePages(allPages, g_mailboxMaxOrder);
return -EIO;
}
for (i = 0; i < MAILBOX_PAGE_MAX; i++) {
g_mZone.pages[i].order = -1;
g_mZone.pages[i].count = 0;
g_mZone.pages[i].page = &allPages[i];
}
g_mZone.pages[0].order = g_mailboxMaxOrder;
for (i = 0; i <= g_mailboxMaxOrder; i++) {
area = &g_mZone.freeAreas[i];
INIT_LIST_HEAD(&area->pageList);
area->order = i;
}
mbPage = &g_mZone.pages[0];
list_add_tail(&mbPage->node, &area->pageList);
g_mZone.allPages = allPages;
mutex_init(&g_mbLock);
#ifdef DEF_ENG
int ret = CreateTcClientDevice(TC_NS_CLIENT_MEILBOX_OPT_NAME, &g_mbDbgOptFops);
if (ret != EOK) {
return ret;
}
ret = CreateTcClientDevice(TC_NS_CLIENT_MEILBOX_STATE_NAME, &mb_dbg_state_fops);
if (ret != EOK) {
return ret;
}
#endif
return 0;
}
void MailboxMempoolDestroy(void)
{
MailboxPoolFreePages(g_mZone.allPages, g_mailboxMaxOrder);
g_mZone.allPages = NULL;
}
-106
View File
@@ -1,106 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "mem.h"
#include <securec.h>
#include "agent.h"
#include "mailbox_mempool.h"
#include "tc_ns_client.h"
#include "tc_ns_log.h"
#include "teek_ns_client.h"
#include "tzdriver_compat.h"
void TcMemFree(TcNsSharedMem *sharedMem)
{
if (sharedMem == NULL) {
return;
}
if (sharedMem->kernelAddr != NULL) {
LOS_VFree(sharedMem->kernelAddr);
sharedMem->kernelAddr = NULL;
}
free(sharedMem);
}
TcNsSharedMem *TcMemAllocate(size_t len)
{
TcNsSharedMem *sharedMem = NULL;
void *addr = NULL;
sharedMem = calloc(1, sizeof(*sharedMem));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)sharedMem)) {
tloge("sharedMem malloc failed\n");
return ERR_PTR(-ENOMEM);
}
len = ALIGN(len, SZ_4K);
if (len > MAILBOX_POOL_SIZE) {
tloge("alloc sharemem size(%zu) is too large\n", len);
free(sharedMem);
return ERR_PTR(-EINVAL);
}
addr = LOS_VMalloc(len);
if (addr == NULL) {
tloge("alloc mailbox failed\n");
free(sharedMem);
return ERR_PTR(-ENOMEM);
}
sharedMem->kernelAddr = addr;
sharedMem->len = len;
sharedMem->userAddr = NULL;
sharedMem->userAddrCa = NULL;
atomic_set(&sharedMem->usage, 0);
return sharedMem;
}
int TcMemInit(void)
{
int ret;
tlogi("TcMemInit\n");
ret = MailboxMempoolInit();
if (ret) {
tloge("tz mailbox init failed\n");
return -ENOMEM;
}
return 0;
}
void TcMemDestroy(void)
{
tlogi("tc_client exit\n");
MailboxMempoolDestroy();
}
-323
View File
@@ -1,323 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "security_auth_enhance.h"
#include <securec.h>
#include "securectype.h"
#include "tc_client_sub_driver.h"
#include "tc_ns_client.h"
#include "tc_ns_log.h"
#include "teek_client_constants.h"
#include "teek_client_type.h"
#include "tzdriver_compat.h"
#if !defined(UINT64_MAX)
#define UINT64_MAX ((uint64_t)0xFFFFFFFFFFFFFFFFULL)
#endif
#ifdef SECURITY_AUTH_ENHANCE
#define GLOBAL_CMD_ID_SSA 0x2DCB /* SSA cmdId 11723 */
#define GLOBAL_CMD_ID_MT 0x2DCC /* MT cmdId 11724 */
#define GLOBAL_CMD_ID_MT_UPDATE 0x2DCD /* MT_IPDATE cmdId 11725 */
#define TEEC_PENDING2_AGENT 0xFFFF2001
static bool IsTokenEmpty(const uint8_t *token, uint32_t tokenLen)
{
uint32_t i;
if (token == NULL) {
tloge("bad parameters, token is null\n");
return true;
}
for (i = 0; i < tokenLen; i++) {
if (*(token + i)) {
return false;
}
}
return true;
}
static TeecResult ScramblingTimestamp(const void *in, void *out,
uint32_t dataLen, const void *key, uint32_t keyLen)
{
uint32_t i;
bool checkValue = false;
if (in == NULL || out == NULL || key == NULL) {
tloge("bad parameters, input_data is null\n");
return TEEC_ERROR_BAD_PARAMETERS;
}
checkValue = (dataLen == 0 || dataLen > SECUREC_MEM_MAX_LEN ||
keyLen > SECUREC_MEM_MAX_LEN || keyLen == 0);
if (checkValue) {
tloge("bad parameters, dataLen is %u, scrambling_len is %u\n",
dataLen, keyLen);
return TEEC_ERROR_BAD_PARAMETERS;
}
for (i = 0; i < dataLen; i++) {
*((uint8_t *)out + i) =
*((uint8_t *)in + i) ^ *((uint8_t *)key + i % keyLen);
}
return TEEC_SUCCESS;
}
static int32_t ChangeTimeStamp(uint8_t flag, uint64_t *timeStamp)
{
if (flag == INC) {
if (*timeStamp < UINT64_MAX) {
(*timeStamp)++;
} else {
tloge("val overflow\n");
return -EFAULT;
}
} else if (flag == DEC) {
if (*timeStamp > 0) {
(*timeStamp)--;
} else {
tloge("val down overflow\n");
return -EFAULT;
}
} else {
tloge("flag error , 0x%x\n", flag);
return -EFAULT;
}
return EOK;
}
static int32_t DescramblingTimestamp(uint8_t *inTokenBuf,
const struct SessionSecureInfo *secureInfo, uint8_t flag)
{
uint64_t timeStamp = 0;
int32_t ret;
if (inTokenBuf == NULL || secureInfo == NULL) {
tloge("invalid params!\n");
return -EINVAL;
}
if (ScramblingTimestamp(&inTokenBuf[TIMESTAMP_BUFFER_INDEX],
&timeStamp, TIMESTAMP_LEN_DEFAULT, secureInfo->scrambling, SCRAMBLING_KEY_LEN)) {
tloge("DescramblingTimestamp failed\n");
return -EFAULT;
}
ret = ChangeTimeStamp(flag, &timeStamp);
if (ret != EOK) {
return ret;
}
tlogd("timestamp is %llu\n", timeStamp);
if (ScramblingTimestamp(&timeStamp, &inTokenBuf[TIMESTAMP_BUFFER_INDEX],
TIMESTAMP_LEN_DEFAULT, secureInfo->scrambling, SCRAMBLING_KEY_LEN)) {
tloge("DescramblingTimestamp failed\n");
return -EFAULT;
}
return EOK;
}
TeecResult UpdateTimestamp(const TcNsSmcCmd *cmd)
{
TcNsSession *session = NULL;
struct SessionSecureInfo *secureInfo = NULL;
uint8_t *tokenBuffer = NULL;
bool filterFlag = false;
bool needCheckFlag = false;
if (cmd == NULL) {
tloge("cmd is NULL, error!");
return TEEC_ERROR_BAD_PARAMETERS;
}
/* if cmd is agent, not check uuid. and sometime uuid canot access it */
filterFlag = (cmd->agentId != 0) ||
(cmd->retVal == TEEC_PENDING2_AGENT);
if (filterFlag) {
return TEEC_SUCCESS;
}
needCheckFlag = (cmd->globalCmd == false) && (cmd->agentId == 0) &&
(cmd->retVal != TEEC_PENDING2_AGENT);
if (needCheckFlag) {
tokenBuffer = (void *)LOS_PaddrToKVaddr((paddr_t)(cmd->tokenPhys));
if (tokenBuffer == NULL ||
IsTokenEmpty(tokenBuffer, TOKEN_BUFFER_LEN)) {
tloge("token is NULL or token is empyt, error!\n");
return TEEC_ERROR_GENERIC;
}
session = TcFindSession2(cmd->devFileId, cmd);
if (session == NULL) {
tlogd("tc_find_session_key find session FAILURE\n");
return TEEC_ERROR_GENERIC;
}
secureInfo = &session->secureInfo;
if (DescramblingTimestamp(tokenBuffer, secureInfo, INC) != EOK) {
PutSessionStruct(session);
tloge("update tokenBuffer error\n");
return TEEC_ERROR_GENERIC;
}
PutSessionStruct(session);
tokenBuffer[SYNC_INDEX] = UN_SYNCED;
} else {
tlogd("global cmd or agent, do not update timestamp\n");
}
return TEEC_SUCCESS;
}
TeecResult SyncTimestamp(const TcNsSmcCmd *cmd, uint8_t *token,
uint32_t tokenLen, bool global)
{
TcNsSession *session = NULL;
bool checkVal = false;
checkVal = (cmd == NULL || token == NULL || tokenLen <= SYNC_INDEX);
if (checkVal) {
tloge("parameters is NULL, error!\n");
return TEEC_ERROR_BAD_PARAMETERS;
}
if (cmd->cmdId == GLOBAL_CMD_ID_OPEN_SESSION && global) {
tlogd("OpenSession would not need sync timestamp\n");
return TEEC_SUCCESS;
}
if (token[SYNC_INDEX] == UN_SYNCED) {
tlogd("flag is UN_SYNC, to sync timestamp!\n");
session = TcFindSession2(cmd->devFileId, cmd);
if (session == NULL) {
tloge("SyncTimestamp find session FAILURE\n");
return TEEC_ERROR_GENERIC;
}
if (DescramblingTimestamp(token, &session->secureInfo, DEC) != EOK) {
PutSessionStruct(session);
tloge("sync tokenBuffer error\n");
return TEEC_ERROR_GENERIC;
}
PutSessionStruct(session);
return TEEC_SUCCESS;
} else if (token[SYNC_INDEX] == IS_SYNCED) {
return TEEC_SUCCESS;
} else {
tloge("sync flag error! 0x%x\n", token[SYNC_INDEX]);
}
return TEEC_ERROR_GENERIC;
}
/* scrambling operation and pid */
static void ScramblingOperation(TcNsSmcCmd *cmd, uint32_t scrambler)
{
if (cmd == NULL) {
return;
}
if (cmd->operationPhys != 0 || cmd->operationHphys != 0) {
cmd->operationPhys = cmd->operationPhys ^ scrambler;
cmd->operationHphys = cmd->operationHphys ^ scrambler;
}
cmd->pid = cmd->pid ^ scrambler;
}
static bool AgentMsg(uint32_t cmdId)
{
bool agent = cmdId == GLOBAL_CMD_ID_SSA ||
cmdId == GLOBAL_CMD_ID_MT ||
cmdId == GLOBAL_CMD_ID_MT_UPDATE;
return agent;
}
/* calculate cmd checksum and scrambling operation */
TeecResult UpdateChksum(TcNsSmcCmd *cmd)
{
TcNsSession *session = NULL;
struct SessionSecureInfo *secureInfo = NULL;
uint32_t ScramblerOper;
bool checkValue = false;
if (cmd == NULL) {
tloge("cmd is NULL, error\n");
return TEEC_ERROR_BAD_PARAMETERS;
}
/*
* if cmd is agent, do not check uuid.
* and sometimes uuid cannot access it
*/
checkValue = (cmd->agentId != 0 || cmd->retVal == TEEC_PENDING2_AGENT);
if (checkValue == true) {
return TEEC_SUCCESS;
}
if (AgentMsg(cmd->cmdId)) {
tlogd("SSA cmd, no need to UpdateChksum\n");
return TEEC_SUCCESS;
}
/* cmd is invoke command */
checkValue = (cmd->globalCmd == false) && (cmd->agentId == 0) &&
(cmd->retVal != TEEC_PENDING2_AGENT);
if (checkValue) {
session = TcFindSession2(cmd->devFileId, cmd);
if (session != NULL) {
secureInfo = &session->secureInfo;
ScramblerOper =
secureInfo->scrambling[SCRAMBLING_OPERATION];
ScramblingOperation(cmd, ScramblerOper);
PutSessionStruct(session);
}
}
return TEEC_SUCCESS;
}
TeecResult VerifyChksum(const TcNsSmcCmd *cmd)
{
TcNsSession *session = NULL;
bool checkFlag = false;
if (cmd == NULL) {
tloge("cmd is NULL, error\n");
return TEEC_ERROR_BAD_PARAMETERS;
}
if (AgentMsg(cmd->cmdId)) {
tlogd("SSA cmd, no need to UpdateChksum\n");
return TEEC_SUCCESS;
}
/* cmd is invoke command */
checkFlag = cmd->globalCmd == false &&
cmd->cmdId != GLOBAL_CMD_ID_CLOSE_SESSION &&
cmd->cmdId != GLOBAL_CMD_ID_KILL_TASK &&
cmd->agentId == 0;
if (checkFlag) {
session = TcFindSession2(cmd->devFileId, cmd);
if (session) {
PutSessionStruct(session);
}
}
return TEEC_SUCCESS;
}
#endif
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
-765
View File
@@ -1,765 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "teek_client_api.h"
#include <securec.h>
#include "tc_ns_log.h"
#include "tzdriver_compat.h"
static void EncdeForPartMem(TcNsClientContext *cliContext,
const TeecOperation *operation, uint32_t paramCnt, uint32_t *paramType)
{
uint32_t diff = (uint32_t)TEEC_MEMREF_PARTIAL_INPUT -
(uint32_t)TEEC_MEMREF_TEMP_INPUT;
if (paramCnt < TEE_PARAM_NUM) {
/* buffer offset len */
if (paramType[paramCnt] == TEEC_MEMREF_WHOLE) {
cliContext->params[paramCnt].memref.offset = 0;
cliContext->params[paramCnt].memref.sizeAddr =
(uint64_t)(uintptr_t)&operation->params[paramCnt].memref.parent->size;
} else {
cliContext->params[paramCnt].memref.offset =
operation->params[paramCnt].memref.offset;
cliContext->params[paramCnt].memref.sizeAddr =
(uint64_t)(uintptr_t)&operation->params[paramCnt].memref.size;
}
if (operation->params[paramCnt].memref.parent->isAllocated) {
cliContext->params[paramCnt].memref.buffer =
(uint64_t)(uintptr_t)
operation->params[paramCnt].memref.parent->buffer;
} else {
cliContext->params[paramCnt].memref.buffer =
(uint64_t)(uintptr_t)
operation->params[paramCnt].memref.parent->buffer +
operation->params[paramCnt].memref.offset;
cliContext->params[paramCnt].memref.offset = 0;
}
/* translate the paramType to know the driver */
if (paramType[paramCnt] == TEEC_MEMREF_WHOLE) {
switch (operation->params[paramCnt].memref.parent->flags) {
case TEEC_MEM_INPUT:
paramType[paramCnt] = TEEC_MEMREF_PARTIAL_INPUT;
break;
case TEEC_MEM_OUTPUT:
paramType[paramCnt] = TEEC_MEMREF_PARTIAL_OUTPUT;
break;
case TEEC_MEM_INOUT:
paramType[paramCnt] = TEEC_MEMREF_PARTIAL_INOUT;
break;
default:
paramType[paramCnt] = TEEC_MEMREF_PARTIAL_INOUT;
break;
}
}
/* if is not allocated, translate TEEC_MEMREF_PARTIAL_XXX to TEEC_MEMREF_TEMP_XXX */
if (!operation->params[paramCnt].memref.parent->isAllocated) {
paramType[paramCnt] = paramType[paramCnt] - diff;
}
}
return;
}
static TeecResult ProcTeekEncode(TcNsClientContext *cliContext,
const TeecOperation *operation)
{
bool checkValue = false;
bool checkTempMem = false;
bool checkPartMem = false;
uint32_t paramType[TEE_PARAM_NUM];
uint32_t paramCnt;
paramType[TEE_PARAM_ONE] =
TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_ONE);
paramType[TEE_PARAM_TWO] =
TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_TWO);
paramType[TEE_PARAM_THREE] =
TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_THREE);
paramType[TEE_PARAM_FOUR] =
TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_FOUR);
for (paramCnt = 0; paramCnt < TEE_PARAM_NUM; paramCnt++) {
checkTempMem = paramType[paramCnt] == TEEC_MEMREF_TEMP_INPUT ||
paramType[paramCnt] == TEEC_MEMREF_TEMP_OUTPUT ||
paramType[paramCnt] == TEEC_MEMREF_TEMP_INOUT;
checkPartMem = paramType[paramCnt] == TEEC_MEMREF_WHOLE ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_INPUT ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_OUTPUT ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_INOUT;
checkValue = paramType[paramCnt] == TEEC_VALUE_INPUT ||
paramType[paramCnt] == TEEC_VALUE_OUTPUT ||
paramType[paramCnt] == TEEC_VALUE_INOUT;
if (checkTempMem == true) {
cliContext->params[paramCnt].memref.buffer =
(uint64_t)(uintptr_t)(operation->params[paramCnt].tmpref.buffer);
cliContext->params[paramCnt].memref.sizeAddr =
(uint64_t)(uintptr_t)(&operation->params[paramCnt].tmpref.size);
} else if (checkPartMem == true) {
EncdeForPartMem(cliContext, operation,
paramCnt, paramType);
} else if (checkValue == true) {
cliContext->params[paramCnt].value.aAddr =
(uint64_t)(uintptr_t)(&operation->params[paramCnt].value.a);
cliContext->params[paramCnt].value.bAddr =
(uint64_t)(uintptr_t)(&operation->params[paramCnt].value.b);
} else if (paramType[paramCnt] == TEEC_NONE) {
/* do nothing */
} else {
tloge("paramType[%u]=%u not correct\n", paramCnt,
paramType[paramCnt]);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
}
cliContext->paramTypes = TEEC_PARAM_TYPES(paramType[TEE_PARAM_ONE],
paramType[TEE_PARAM_TWO], paramType[TEE_PARAM_THREE],
paramType[TEE_PARAM_FOUR]);
return TEEC_SUCCESS;
}
struct TeekEncodeMeg {
TeecUuid serviceId;
uint32_t sessionId;
uint32_t cmdId;
};
static TeecResult TeekEncode(TcNsClientContext *cliContext,
struct TeekEncodeMeg *msg,
const TcNsClientLogin *cliLogin, const TeecOperation *operation)
{
TeecResult ret;
errno_t sret;
if (cliContext == NULL || cliLogin == NULL) {
tloge("cliContext or cliLogin is null.\n");
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
sret = memset_s(cliContext, sizeof(*cliContext),
0x00, sizeof(*cliContext));
if (sret != EOK) {
tloge("memset error sret is %d.\n", sret);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
sret = memcpy_s(cliContext->uuid, sizeof(cliContext->uuid),
(uint8_t *)&msg->serviceId, sizeof(msg->serviceId));
if (sret != EOK) {
tloge("memcpy error sret is %d.\n", sret);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
cliContext->sessionId = msg->sessionId;
cliContext->cmdId = msg->cmdId;
cliContext->returns.code = 0;
cliContext->returns.origin = 0;
cliContext->login.method = cliLogin->method;
cliContext->login.mdata = cliLogin->mdata;
/* support when operation is null */
if (operation == NULL) {
return TEEC_SUCCESS;
}
cliContext->started = operation->cancelFlag;
ret = ProcTeekEncode(cliContext, operation);
tlogv("cli param type %u\n", cliContext->paramTypes);
return ret;
}
static TeecResult TeekCheckTmpRef(TeecTempmemoryReference tmpref)
{
TeecResult ret;
bool checkValue = (tmpref.buffer == NULL) || (tmpref.size == 0);
if (checkValue == true) {
tloge("tmpref buffer is null, or size is zero\n");
ret = (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
} else {
ret = (TeecResult) TEEC_SUCCESS;
}
return ret;
}
static TeecResult TeekCheckMemRef(TeecRegisteredmemoryReference memref,
uint32_t paramType)
{
bool checkValue = (memref.parent == NULL) || (memref.parent->buffer == NULL);
bool checkOffset = false;
if (checkValue == true) {
tloge("parent of memref is null, or the buffer is zero\n");
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
if (paramType == TEEC_MEMREF_PARTIAL_INPUT) {
if (!(memref.parent->flags & TEEC_MEM_INPUT)) {
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
} else if (paramType == TEEC_MEMREF_PARTIAL_OUTPUT) {
if (!(memref.parent->flags & TEEC_MEM_OUTPUT)) {
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
} else if (paramType == TEEC_MEMREF_PARTIAL_INOUT) {
if (!(memref.parent->flags & TEEC_MEM_INPUT)) {
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
if (!(memref.parent->flags & TEEC_MEM_OUTPUT)) {
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
} else if (paramType == TEEC_MEMREF_WHOLE) {
/* if type is TEEC_MEMREF_WHOLE, ignore it */
} else {
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
checkValue = (paramType == TEEC_MEMREF_PARTIAL_INPUT) ||
(paramType == TEEC_MEMREF_PARTIAL_OUTPUT) ||
(paramType == TEEC_MEMREF_PARTIAL_INOUT);
if (checkValue == true) {
checkOffset = (memref.offset + memref.size) > memref.parent->size ||
(memref.offset + memref.size) < memref.offset ||
(memref.offset + memref.size) < memref.size;
if (checkOffset == true) {
tloge("offset + size exceed the parent size\n");
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
}
return (TeecResult) TEEC_SUCCESS;
}
/*
* This function checks an operation is valid or not.
*/
TeecResult TeekCheckOperation(const TeecOperation *operation)
{
uint32_t paramType[TEE_PARAM_NUM] = {0};
uint32_t paramCnt;
TeecResult ret = TEEC_SUCCESS;
bool checkValue = false;
bool checkTempMem = false;
bool checkPartMem = false;
/* GP Support operation is NULL
* operation: a pointer to a Client Application initialized TeecOperation structure,
* or NULL if there is no payload to send or if the Command does not need to support
* cancellation.
*/
if (operation == NULL) {
return (TeecResult)TEEC_SUCCESS;
}
if (!operation->started) {
tloge("sorry, cancellation not support\n");
return (TeecResult) TEEC_ERROR_NOT_IMPLEMENTED;
}
paramType[TEE_PARAM_ONE] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_ONE);
paramType[TEE_PARAM_TWO] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_TWO);
paramType[TEE_PARAM_THREE] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_THREE);
paramType[TEE_PARAM_FOUR] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_FOUR);
for (paramCnt = 0; paramCnt < TEE_PARAM_NUM; paramCnt++) {
checkTempMem = paramType[paramCnt] == TEEC_MEMREF_TEMP_INPUT ||
paramType[paramCnt] == TEEC_MEMREF_TEMP_OUTPUT || paramType[paramCnt] == TEEC_MEMREF_TEMP_INOUT;
checkPartMem = paramType[paramCnt] == TEEC_MEMREF_WHOLE ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_INPUT ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_OUTPUT ||
paramType[paramCnt] == TEEC_MEMREF_PARTIAL_INOUT;
checkValue = paramType[paramCnt] == TEEC_VALUE_INPUT ||
paramType[paramCnt] == TEEC_VALUE_OUTPUT || paramType[paramCnt] == TEEC_VALUE_INOUT;
if (checkTempMem == true) {
ret = TeekCheckTmpRef(operation->params[paramCnt].tmpref);
if (ret != TEEC_SUCCESS) {
break;
}
} else if (checkPartMem == true) {
ret = TeekCheckMemRef(operation->params[paramCnt].memref, paramType[paramCnt]);
if (ret != TEEC_SUCCESS) {
break;
}
} else if (checkValue == true) {
/* if type is value, ignore it */
} else if (paramType[paramCnt] == TEEC_NONE) {
/* if type is none, ignore it */
} else {
tloge("paramType[%u]=%x is not support\n", paramCnt, paramType[paramCnt]);
ret = (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
break;
}
}
return ret;
}
/*
* This function check if the special agent is launched.Used For HDCP key.
* e.g. If sfs agent is not alive, you can not do HDCP key write to SRAM.
*/
int TeekIsAgentAlive(unsigned int agentId)
{
return IsAgentAlive(agentId);
}
/*
* This function initializes a new TEE Context, forming a connection between this Client Application
* and the TEE identified by the string identifier name.
*/
TeecResult TeekInitializeContext(const char *name, TeecContext *context)
{
int32_t ret;
/* name current not used */
(void)(name);
tlogd("TeekInitializeContext Started:\n");
/* First, check parameters is valid or not */
if (context == NULL) {
tloge("context is null, not correct\n");
return (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
}
context->dev = NULL;
/* Paramters right, start execution */
ret = TcNsClientOpen((TcNsDevFile **)&context->dev,
TEE_REQ_FROM_KERNEL_MODE);
if (ret != TEEC_SUCCESS) {
tloge("open device failed\n");
return (TeecResult) TEEC_ERROR_GENERIC;
}
tlogd("open device success\n");
TEEK_INIT_LIST_HEAD(&context->sessionList);
TEEK_INIT_LIST_HEAD(&context->shrdMemList);
return TEEC_SUCCESS;
}
/*
* This function finalizes an initialized TEE Context.
*/
void TeekFinalizeContext(TeecContext *context)
{
struct ListNode *ptr = NULL;
TeecSession *session = NULL;
/* TeecSharedMemory* shrdmem */
tlogd("TeekFinalizeContext started\n");
/* First, check parameters is valid or not */
if (context == NULL || context->dev == NULL) {
tloge("context or dev is null, not correct\n");
return;
}
/* Paramters right, start execution */
if (!LIST_EMPTY(&context->sessionList)) {
tlogi("context still has sessions opened, close it\n");
LIST_FOR_EACH(ptr, &context->sessionList) {
session = list_entry(ptr, TeecSession, head);
TeekCloseSession(session);
}
}
tlogd("close device\n");
TcNsClientClose(context->dev);
context->dev = NULL;
}
static TeecResult CheckParamsForOpenSession(TeecContext *context,
const TeecOperation *operation, TcNsClientLogin *cliLogin)
{
bool checkValue = false;
TcNsDevFile *devFile = NULL;
TeecResult teecRet;
errno_t sret;
uint32_t paramType[TEE_PARAM_NUM] = {0};
paramType[TEE_PARAM_FOUR] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_FOUR);
paramType[TEE_PARAM_THREE] = TEEC_PARAM_TYPE_GET(operation->paramTypes, TEE_PARAM_THREE);
checkValue = paramType[TEE_PARAM_FOUR] != TEEC_MEMREF_TEMP_INPUT ||
paramType[TEE_PARAM_THREE] != TEEC_MEMREF_TEMP_INPUT;
if (checkValue == true) {
tloge("invalid param type 0x%x\n", operation->paramTypes);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
checkValue = operation->params[TEE_PARAM_FOUR].tmpref.buffer == NULL ||
operation->params[TEE_PARAM_THREE].tmpref.buffer == NULL ||
operation->params[TEE_PARAM_FOUR].tmpref.size == 0 || operation->params[TEE_PARAM_THREE].tmpref.size == 0;
if (checkValue == true) {
tloge("invalid operation params(NULL)\n");
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
cliLogin->method = TEEC_LOGIN_IDENTIFY;
devFile = (TcNsDevFile *)(context->dev);
if (devFile == NULL) {
tloge("invalid context->dev (NULL)\n");
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
devFile->pkgNameLen = operation->params[TEE_PARAM_FOUR].tmpref.size;
if (operation->params[TEE_PARAM_FOUR].tmpref.size > (MAX_PACKAGE_NAME_LEN - 1)) {
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
} else {
sret = memset_s(devFile->PkgName, sizeof(devFile->PkgName), 0, MAX_PACKAGE_NAME_LEN);
if (sret != EOK) {
tloge("memset error sret is %d.\n", sret);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
sret = memcpy_s(devFile->PkgName, sizeof(devFile->PkgName), operation->params[TEE_PARAM_FOUR].tmpref.buffer,
operation->params[TEE_PARAM_FOUR].tmpref.size);
if (sret != EOK) {
tloge("memcpy error sret is %d.\n", sret);
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
}
devFile->pubKeyLen = 0;
devFile->loginSetup = 1;
teecRet = TeekCheckOperation(operation);
if (teecRet != TEEC_SUCCESS) {
tloge("operation is invalid\n");
return (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
}
return teecRet;
}
static TeecResult OpenSessionAndSwitchRet(TeecSession *session,
TeecContext *context, const TeecUuid *destination,
TcNsClientContext *cliContext, uint32_t *origin)
{
int32_t ret;
TeecResult teecRet;
ret = TcNsOpenSession(context->dev, cliContext);
if (ret == 0) {
tlogd("open session success\n");
session->sessionId = cliContext->sessionId;
session->serviceId = *destination;
session->opsCnt = 0;
TEEK_INIT_LIST_HEAD(&session->head);
ListInsertTail(&context->sessionList, &session->head);
session->context = context;
return TEEC_SUCCESS;
} else if (ret < 0) {
tloge("open session failed, ioctl errno = %u\n", ret);
if (ret == -EFAULT) {
teecRet = (TeecResult) TEEC_ERROR_ACCESS_DENIED;
} else if (ret == -ENOMEM) {
teecRet = (TeecResult) TEEC_ERROR_OUT_OF_MEMORY;
} else if (ret == -EINVAL) {
teecRet = (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
} else if (ret == -ERESTARTSYS) {
teecRet = (TeecResult) TEEC_CLIENT_INTR;
} else {
teecRet = (TeecResult) TEEC_ERROR_GENERIC;
}
*origin = TEEC_ORIGIN_COMMS;
return teecRet;
} else {
tloge("open session failed, code=0x%x, origin=%u\n", cliContext->returns.code,
cliContext->returns.origin);
teecRet = (TeecResult)cliContext->returns.code;
*origin = cliContext->returns.origin;
}
return teecRet;
}
/*
* Function: TEEC_OpenSession
* Description: This function opens a new Session
* Parameters: context: a pointer to an initialized TEE Context.
* session: a pointer to a Session structure to open.
* destination: a pointer to a UUID structure.
* connectionMethod: the method of connection to use.
* connectionData: any necessary data required to support the connection method chosen.
* operation: a pointer to an Operation containing a set of Parameters.
* returnOrigin: a pointer to a variable which will contain the return origin.
* Return: TEEC_SUCCESS: success other: failure
*/
static TeecResult ProcTeekOpenSession(TeecContext *context,
TeecSession *session, const TeecUuid *destination,
uint32_t connectionMethod, const void *connectionData,
const TeecOperation *operation, uint32_t *returnOrigin)
{
TeecResult teecRet;
uint32_t origin = TEEC_ORIGIN_API;
TcNsClientContext cliContext;
TcNsClientLogin cliLogin = { 0, 0 };
bool checkValue = false;
tlogd("TeekOpenSession Started:\n");
/* connectionData current not used */
(void)(connectionData);
/* returnOrigin maybe null, so only when it is valid, we set
* origin(error come from which module)
*/
if (returnOrigin != NULL) {
*returnOrigin = origin;
}
/* First, check parameters is valid or not */
checkValue = (context == NULL || operation == NULL ||
connectionMethod != TEEC_LOGIN_IDENTIFY);
if (checkValue == true || destination == NULL || session == NULL) {
tloge("invalid input params\n");
return TEEC_ERROR_BAD_PARAMETERS;
}
teecRet = CheckParamsForOpenSession(context, operation, &cliLogin);
if (teecRet != TEEC_SUCCESS) {
goto RET_FAIL;
}
/* Paramters right, start execution
* note:before open session success,
* we should send session=0 as initial state.
*/
struct TeekEncodeMeg msg = {
*destination, 0, GLOBAL_CMD_ID_OPEN_SESSION
};
teecRet = TeekEncode(&cliContext, &msg, &cliLogin, operation);
if (teecRet != TEEC_SUCCESS) {
tloge("encode failed\n");
goto RET_FAIL;
}
#ifdef SECURITY_AUTH_ENHANCE
cliContext.teecToken = session->teecToken;
cliContext.tokenLen = sizeof(session->teecToken);
#endif
teecRet = OpenSessionAndSwitchRet(session, context,
destination, &cliContext, &origin);
/* ONLY when ioctl returnCode!=0 and returnOrigin not NULL, set returnOrigin */
if (teecRet != TEEC_SUCCESS && returnOrigin != NULL) {
*returnOrigin = origin;
}
RET_FAIL:
return teecRet;
}
#define RETRY_TIMES 5
TeecResult TeekOpenSession(TeecContext *context,
TeecSession *session, const TeecUuid *destination,
uint32_t connectionMethod, const void *connectionData,
const TeecOperation *operation, uint32_t *returnOrigin)
{
int i;
TeecResult ret;
for (i = 0; i < RETRY_TIMES; i++) {
ret = ProcTeekOpenSession(context, session,
destination, connectionMethod, connectionData,
operation, returnOrigin);
if (ret != (TeecResult)TEEC_CLIENT_INTR) {
return ret;
}
}
return ret;
}
static int CheckCloseSessionParam(TeecSession *session)
{
bool checkValue = false;
bool found = false;
TeecSession *tempSess = NULL;
struct ListNode *ptr = NULL;
/* First, check parameters is valid or not */
checkValue = session == NULL || session->context == NULL;
if (checkValue || session->context->dev == NULL) {
tloge("input invalid session or session->context is null\n");
return -1;
}
LIST_FOR_EACH(ptr, &session->context->sessionList) {
tempSess = list_entry(ptr, TeecSession, head);
if (tempSess == session) {
found = true;
break;
}
}
if (!found) {
tloge("session is not in the context list\n");
return -1;
}
return 0;
}
/*
* This function closes an opened Session.
*/
void TeekCloseSession(TeecSession *session)
{
int32_t ret;
TcNsClientContext cliContext;
TcNsClientLogin cliLogin = { 0, 0 };
errno_t sret;
tlogd("TeekCloseSession started\n");
ret = CheckCloseSessionParam(session);
if (ret) {
return;
}
/* Paramters all right, start execution */
if (session->opsCnt) {
tloge("session still has commands running\n");
}
struct TeekEncodeMeg msg = {
session->serviceId, session->sessionId, GLOBAL_CMD_ID_CLOSE_SESSION
};
if (TeekEncode(&cliContext, &msg, &cliLogin, NULL) != TEEC_SUCCESS) {
tloge("encode failed, just return\n");
return;
}
#ifdef SECURITY_AUTH_ENHANCE
cliContext.teecToken = session->teecToken;
cliContext.tokenLen = sizeof(session->teecToken);
#endif
ret = TcNsCloseSession(session->context->dev, &cliContext);
if (ret == 0) {
tlogd("close session success\n");
session->sessionId = 0;
sret = memset_s((uint8_t *)(&session->serviceId), sizeof(session->serviceId), 0x00, UUID_LEN);
/* TeekCloseSession is void so go on execute */
if (sret != EOK) {
tloge("memset error sret is %d.\n", sret);
}
#ifdef SECURITY_AUTH_ENHANCE
sret = memset_s(session->teecToken, TOKEN_SAVE_LEN, 0x00, TOKEN_SAVE_LEN);
if (sret != EOK) {
tloge("memset session's member error ret value is %d.\n", sret);
}
#endif
session->opsCnt = 0;
ListRemove(&session->head);
session->context = NULL;
} else {
tloge("close session failed\n");
}
}
static TeecResult InvokeCmdAndSwitchRet(TeecSession *session,
TcNsClientContext *cliContext, uint32_t *origin)
{
int32_t ret;
TeecResult teecRet;
ret = TcNsSendCmd(session->context->dev, cliContext);
if (ret == 0) {
tlogd("invoke cmd success\n");
teecRet = TEEC_SUCCESS;
} else if (ret < 0) {
tloge("invoke cmd failed, ioctl errno = %d\n", ret);
if (ret == -EFAULT) {
teecRet = (TeecResult)TEEC_ERROR_ACCESS_DENIED;
} else if (ret == -ENOMEM) {
teecRet = (TeecResult)TEEC_ERROR_OUT_OF_MEMORY;
} else if (ret == -EINVAL) {
teecRet = (TeecResult)TEEC_ERROR_BAD_PARAMETERS;
} else {
teecRet = (TeecResult)TEEC_ERROR_GENERIC;
}
*origin = TEEC_ORIGIN_COMMS;
} else {
tloge("invoke cmd failed, code=0x%x, origin=%d\n",
cliContext->returns.code, cliContext->returns.origin);
teecRet = (TeecResult)cliContext->returns.code;
*origin = cliContext->returns.origin;
}
return teecRet;
}
/* This function invokes a Command within the specified Session. */
TeecResult TeekInvokeCommand(TeecSession *session, uint32_t commandID,
TeecOperation *operation, uint32_t *returnOrigin)
{
TeecResult teecRet = (TeecResult) TEEC_ERROR_BAD_PARAMETERS;
uint32_t origin = TEEC_ORIGIN_API;
TcNsClientContext cliContext;
TcNsClientLogin cliLogin = { 0, 0 };
tlogd("TeekInvokeCommand Started:\n");
/* First, check parameters is valid or not */
if (session == NULL || session->context == NULL) {
tloge("input invalid session or session->context is null\n");
if (returnOrigin != NULL) {
*returnOrigin = origin;
}
return teecRet;
}
teecRet = TeekCheckOperation(operation);
if (teecRet != TEEC_SUCCESS) {
tloge("operation is invalid\n");
if (returnOrigin != NULL) {
*returnOrigin = origin;
}
return teecRet;
}
/* Paramters all right, start execution */
session->opsCnt++;
struct TeekEncodeMeg msg = {
session->serviceId, session->sessionId, commandID
};
teecRet = TeekEncode(&cliContext, &msg, &cliLogin, operation);
if (teecRet != TEEC_SUCCESS) {
tloge("encode failed\n");
session->opsCnt--;
if (returnOrigin != NULL) {
*returnOrigin = origin;
}
return teecRet;
}
#ifdef SECURITY_AUTH_ENHANCE
cliContext.teecToken = session->teecToken;
cliContext.tokenLen = sizeof(session->teecToken);
#endif
teecRet = InvokeCmdAndSwitchRet(session, &cliContext, &origin);
session->opsCnt--;
/* ONLY when ioctl returnCode!=0 and returnOrigin not NULL, set *returnOrigin */
if ((teecRet != TEEC_SUCCESS) && (returnOrigin != NULL)) {
*returnOrigin = origin;
}
return teecRet;
}
/*
* This function registers a block of existing Client Application memory
* as a block of Shared Memory within the scope of the specified TEE Context.
*/
TeecResult TeekRegisterSharedMemory(TeecContext *context,
TeecSharedMemory *sharedMem)
{
tloge("TeekRegisterSharedMemory not supported\n");
return (TeecResult)TEEC_ERROR_NOT_SUPPORTED;
}
/*
* This function allocates a new block of memory as a block of
* Shared Memory within the scope of the specified TEE Context.
*/
TeecResult TeekAllocateSharedMemory(TeecContext *context,
TeecSharedMemory *sharedMem)
{
tloge("TeekAllocateSharedMemory not supported\n");
return (TeecResult)TEEC_ERROR_NOT_SUPPORTED;
}
/*
* This function deregisters or deallocates
* a previously initialized block of Shared Memory..
*/
void TeekReleaseSharedMemory(TeecSharedMemory *sharedMem)
{
tloge("TeekReleaseSharedMemory not supported\n");
}
/*
* This function requests the cancellation of a pending open Session operation or
* a Command invocation operation.
*/
void TeekRequestCancellation(TeecOperation *operation)
{
tloge("TeekRequestCancellation not supported\n");
}
-718
View File
@@ -1,718 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "tz_spi_notify.h"
#include <securec.h>
#include "gp_ops.h"
#include "mailbox_mempool.h"
#include "smc.h"
#include "tc_client_driver.h"
#include "tc_client_sub_driver.h"
#include "tc_ns_client.h"
#include "tc_ns_log.h"
#include "teek_client_constants.h"
#define MAX_CALLBACK_COUNT 100
#define UUID_SIZE 16
struct TeecTimerProperty;
#ifdef DEF_ENG
static int g_timerType;
#endif
enum TimerClassType {
/* timer event using timer10 */
TIMER_GENERIC,
/* timer event using RTC */
TIMER_RTC
};
struct TeecTimerProperty {
unsigned int type;
unsigned int timerId;
unsigned int timerClass;
unsigned int reserved2;
};
struct NotifyContextTimer {
unsigned int devFileId;
unsigned char uuid[UUID_SIZE];
unsigned int sessionId;
struct TeecTimerProperty property;
uint32_t expireTime;
};
#ifdef CONFIG_TEE_SMP
struct NotifyContextWakeup {
pid_t caThreadId;
};
struct NotifyContextShadow {
uint64_t targetTcb;
};
struct NotifyContextStats {
uint32_t sends;
uint32_t recvs;
uint32_t sendw;
uint32_t recvw;
uint32_t missed;
};
#endif
union NotifyContext {
struct NotifyContextTimer timer;
#ifdef CONFIG_TEE_SMP
struct NotifyContextWakeup wakeup;
struct NotifyContextShadow shadow;
struct NotifyContextStats meta;
#endif
};
struct NotifyDataEntry {
uint32_t entryType : 31;
uint32_t filled : 1;
union NotifyContext context;
};
#define NOTIFY_DATA_ENTRY_COUNT \
((PAGE_SIZE / sizeof(struct NotifyDataEntry)) - 1)
struct NotifyDataStruct {
struct NotifyDataEntry entry[NOTIFY_DATA_ENTRY_COUNT];
struct NotifyDataEntry meta;
};
static struct NotifyDataStruct *g_notifyData = NULL;
static struct NotifyDataEntry *g_notifyDataEntryTimer = NULL;
static struct NotifyDataEntry *g_notifyDataEntryRtc = NULL;
#ifdef CONFIG_TEE_SMP
static struct NotifyDataEntry *g_notifyDataEntryShadow = NULL;
#endif
enum NotifyDataType {
NOTIFY_DATA_ENTRY_UNUSED,
NOTIFY_DATA_ENTRY_TIMER,
NOTIFY_DATA_ENTRY_RTC,
#ifdef CONFIG_TEE_SMP
NOTIFY_DATA_ENTRY_WAKEUP,
NOTIFY_DATA_ENTRY_SHADOW,
NOTIFY_DATA_ENTRY_FIQSHD,
NOTIFY_DATA_ENTRY_SHADOW_EXIT,
#endif
NOTIFY_DATA_ENTRY_MAX,
};
struct TcNsCallback {
unsigned char uuid[UUID_SIZE];
mutex_t callbackLock;
void (*callbackFunc)(void *);
struct list_head head;
};
struct TcNsCallbackList {
unsigned int callbackCount;
mutex_t callbackListLock;
struct list_head callbackList;
};
static void TcNotifyFn(struct work_struct *dummy);
static struct TcNsCallbackList g_taCallbackFuncList;
static DECLARE_WORK(tc_notify_work, TcNotifyFn);
#ifdef CONFIG_TEE_SMP
static struct workqueue_struct *g_tzSpiWq = NULL;
#endif
static void WalkCallback(struct NotifyContextTimer *tcNotifyDataTimer, struct TcNsCallback *callbackFuncT)
{
if (tcNotifyDataTimer->property.timerClass == TIMER_RTC) {
tlogd("start to call callback func\n");
callbackFuncT->callbackFunc((void *)(&(tcNotifyDataTimer->property)));
tlogd("end to call callback func\n");
} else if (tcNotifyDataTimer->property.timerClass == TIMER_GENERIC) {
tlogd("timer60 no callback func\n");
}
}
static void WalkCallbackList(struct NotifyContextTimer *tcNotifyDataTimer)
{
struct TcNsCallback *callbackFuncT = NULL;
mutex_lock(&g_taCallbackFuncList.callbackListLock);
list_for_each_entry(callbackFuncT, &g_taCallbackFuncList.callbackList, head) {
if (memcmp(callbackFuncT->uuid, tcNotifyDataTimer->uuid, UUID_SIZE) == 0) {
WalkCallback(tcNotifyDataTimer, callbackFuncT);
}
}
mutex_unlock(&g_taCallbackFuncList.callbackListLock);
}
static void TcNotifyTimerFn(struct NotifyDataEntry *notifyDataEntry)
{
TcNsDevFile *tempDevFile = NULL;
TcNsService *tempSvc = NULL;
TcNsSession *tempSes = NULL;
int encFound = 0;
struct NotifyContextTimer *tcNotifyDataTimer = NULL;
tcNotifyDataTimer = &(notifyDataEntry->context.timer);
notifyDataEntry->filled = 0;
tlogd("notify_data timer type is 0x%x, timer ID is 0x%x\n",
tcNotifyDataTimer->property.type,
tcNotifyDataTimer->property.timerId);
WalkCallbackList(tcNotifyDataTimer);
mutex_lock(&GetTcNsDevList()->devLock);
list_for_each_entry(tempDevFile, &GetTcNsDevList()->devFileList, head) {
tlogd("dev file id1 = %u, id2 = %u\n", tempDevFile->devFileId, tcNotifyDataTimer->devFileId);
if (tempDevFile->devFileId == tcNotifyDataTimer->devFileId) {
mutex_lock(&tempDevFile->serviceLock);
tempSvc = TcFindServiceInDev(tempDevFile, tcNotifyDataTimer->uuid, UUID_LEN);
GetServiceStruct(tempSvc);
mutex_unlock(&tempDevFile->serviceLock);
if (tempSvc == NULL) {
break;
}
mutex_lock(&tempSvc->SessionLock);
tempSes = TcFindSessionWithOwner(&tempSvc->sessionList, tcNotifyDataTimer->sessionId, tempDevFile);
GetSessionStruct(tempSes);
mutex_unlock(&tempSvc->SessionLock);
PutServiceStruct(tempSvc);
tempSvc = NULL;
if (tempSes != NULL) {
tlogd("send cmd ses id %u\n", tempSes->sessionId);
encFound = 1;
break;
}
break;
}
}
mutex_unlock(&GetTcNsDevList()->devLock);
if (tcNotifyDataTimer->property.timerClass == TIMER_GENERIC) {
tlogd("timer60 wake up event\n");
if (encFound && tempSes != NULL) {
tempSes->waitData.sendWaitFlag = 1;
wake_up(&tempSes->waitData.sendCmdWq);
PutSessionStruct(tempSes);
tempSes = NULL;
}
} else {
tlogd("RTC do not need to wakeup\n");
}
}
#ifdef CONFIG_TEE_SMP
static noinline int GetNotifyDataEntry(struct NotifyDataEntry *copy)
{
uint32_t i;
int filled;
int ret = -1;
if (copy == NULL) {
tloge("Bad parameters! ");
return ret;
}
/* TIMER and RTC use fix entry, skip them. */
for (i = NOTIFY_DATA_ENTRY_WAKEUP - 1; i < NOTIFY_DATA_ENTRY_COUNT; i++) {
struct NotifyDataEntry *e = NULL;
e = &g_notifyData->entry[i];
filled = e->filled;
DMB;
if (!filled) {
continue;
}
switch (e->entryType) {
case NOTIFY_DATA_ENTRY_SHADOW: // fall through
case NOTIFY_DATA_ENTRY_SHADOW_EXIT: // fall through
case NOTIFY_DATA_ENTRY_FIQSHD: // fall through
g_notifyData->meta.context.meta.recvs++;
break;
case NOTIFY_DATA_ENTRY_WAKEUP:
g_notifyData->meta.context.meta.recvw++;
break;
default:
tloge("invalid notify type=%u\n", e->entryType);
goto exit;
}
if (memcpy_s(copy, sizeof(*copy), e, sizeof(*e)) != EOK) {
tloge("memcpy entry failed\n");
break;
}
DMB;
e->filled = 0;
ret = 0;
break;
}
exit:
return ret;
}
static void TcNotifyWakeupFn(struct NotifyDataEntry *entry)
{
struct NotifyContextWakeup *tcNotifyWakeup = NULL;
tcNotifyWakeup = &(entry->context.wakeup);
SmcWakeupCa(tcNotifyWakeup->caThreadId);
tlogd("notify_data_entry_wakeup ca: %d\n", tcNotifyWakeup->caThreadId);
}
static void TcNotifyShadowFn(struct NotifyDataEntry *entry)
{
struct NotifyContextShadow *tcNotifyShadow = NULL;
tcNotifyShadow = &(entry->context.shadow);
SmcQueueShadowWorker(tcNotifyShadow->targetTcb);
}
static void TcNotifyFiqshdFn(struct NotifyDataEntry *entry)
{
struct NotifyContextShadow *tcNotifyShadow = NULL;
if (entry == NULL) {
/* for NOTIFY_DATA_ENTRY_FIQSHD missed */
FiqShadowWorkFunc(0);
return;
}
tcNotifyShadow = &(entry->context.shadow);
FiqShadowWorkFunc(tcNotifyShadow->targetTcb);
}
static void TcNotifyShadowExitFn(struct NotifyDataEntry *entry)
{
struct NotifyContextWakeup *tcNotifyWakeup = NULL;
tcNotifyWakeup = &(entry->context.wakeup);
if (SmcShadowExit(tcNotifyWakeup->caThreadId) != 0) {
tloge("shadow ca exit failed: %d\n",
(int)tcNotifyWakeup->caThreadId);
}
}
static void SpiBroadcastNotifications(void)
{
uint32_t missed;
DMB;
missed = LOS_AtomicXchg32bits((Atomic *)&g_notifyData->meta.context.meta.missed, 0);
if (!missed) {
return;
}
if (missed & (1U << NOTIFY_DATA_ENTRY_WAKEUP)) {
SmcWakeupBroadcast();
missed &= ~(1U << NOTIFY_DATA_ENTRY_WAKEUP);
}
if (missed & (1U << NOTIFY_DATA_ENTRY_FIQSHD)) {
TcNotifyFiqshdFn(NULL);
missed &= ~(1U << NOTIFY_DATA_ENTRY_FIQSHD);
}
if (missed) {
tloge("missed spi notification mask %x\n", missed);
}
}
static void TcNotifyOtherFun(void)
{
struct NotifyDataEntry copy = {0};
while (GetNotifyDataEntry(&copy) == 0) {
switch (copy.entryType) {
case NOTIFY_DATA_ENTRY_WAKEUP:
TcNotifyWakeupFn(&copy);
break;
case NOTIFY_DATA_ENTRY_SHADOW:
TcNotifyShadowFn(&copy);
break;
case NOTIFY_DATA_ENTRY_FIQSHD:
TcNotifyFiqshdFn(&copy);
break;
case NOTIFY_DATA_ENTRY_SHADOW_EXIT:
TcNotifyShadowExitFn(&copy);
break;
default:
tloge("invalid entry type = %u\n", copy.entryType);
break;
}
if (memset_s(&copy, sizeof(copy), 0, sizeof(copy))) {
tloge("memset copy failed\n");
}
}
SpiBroadcastNotifications();
}
#else
static void TcNotifyOtherFun(void) {}
#endif
int g_spiInited = 0;
static void TcNotifyFn(struct work_struct *dummy)
{
if (!g_spiInited) {
return;
}
if (g_notifyDataEntryTimer->filled) {
TcNotifyTimerFn(g_notifyDataEntryTimer);
}
if (g_notifyDataEntryRtc->filled) {
TcNotifyTimerFn(g_notifyDataEntryRtc);
}
TcNotifyOtherFun();
}
static irqreturn_t TcSecureNotify(int irq, void *devId)
{
#ifdef CONFIG_TEE_SMP
#define N_WORK 8
int i;
static struct work_struct tcNotifyWorks[N_WORK];
static int init = 0;
if (!init) {
for (i = 0; i < N_WORK; i++) {
INIT_WORK(&tcNotifyWorks[i], TcNotifyFn);
}
init = 1;
}
for (i = 0; i < N_WORK; i++) {
if (queue_work(g_tzSpiWq, &tcNotifyWorks[i])) {
break;
}
}
#undef N_WORK
#else
schedule_work(&tc_notify_work);
ISB;
DSB;
TcSmcWakeup();
#endif
return IRQ_HANDLED;
}
int TcNsRegisterServiceCallBackFunc(const char *uuid, void *func)
{
struct TcNsCallback *callbackFunc = NULL;
struct TcNsCallback *newCallback = NULL;
int ret = 0;
errno_t sret;
bool checkStat = (uuid == NULL || func == NULL);
if (checkStat) {
return -EINVAL;
}
mutex_lock(&g_taCallbackFuncList.callbackListLock);
if (g_taCallbackFuncList.callbackCount > MAX_CALLBACK_COUNT) {
mutex_unlock(&g_taCallbackFuncList.callbackListLock);
tloge("callbackCount is out\n");
return -ENOMEM;
}
list_for_each_entry(callbackFunc,
&g_taCallbackFuncList.callbackList, head) {
if (memcmp(callbackFunc->uuid, uuid, UUID_SIZE) == 0) {
callbackFunc->callbackFunc = (void (*)(void *))func;
tlogd("succeed to find uuid ta_callback_func_list\n");
goto FIND_CALLBACK;
}
}
/* create a new callback struct if we couldn't find it in list */
newCallback = calloc(1, sizeof(*newCallback));
if (ZERO_OR_NULL_PTR((unsigned long)(uintptr_t)newCallback)) {
tloge("calloc failed\n");
ret = -ENOMEM;
goto FIND_CALLBACK;
}
sret = memcpy_s(newCallback->uuid, UUID_SIZE, uuid, UUID_SIZE);
if (sret != EOK) {
free(newCallback);
newCallback = NULL;
ret = -ENOMEM;
goto FIND_CALLBACK;
}
g_taCallbackFuncList.callbackCount++;
tlogd("ta_callback_func_list.callbackCount is %u\n",
g_taCallbackFuncList.callbackCount);
INIT_LIST_HEAD(&newCallback->head);
newCallback->callbackFunc = (void (*)(void *))func;
mutex_init(&newCallback->callbackLock);
list_add_tail(&newCallback->head, &g_taCallbackFuncList.callbackList);
FIND_CALLBACK:
mutex_unlock(&g_taCallbackFuncList.callbackListLock);
return ret;
}
#ifdef DEF_ENG
static void TimerCallbackFunc(void *param)
{
struct TeecTimerProperty *timerProperty =
(struct TeecTimerProperty *)param;
tlogd("timerProperty->type = %x, timerProperty->timerId = %x\n",
timerProperty->type, timerProperty->timerId);
g_timerType = (int)timerProperty->type;
}
static void TstGetTimerType(int *type)
{
*type = g_timerType;
}
static void CallbackDemoMain(const char *uuid)
{
int ret;
tlogd("step into CallbackDemoMain\n");
ret = TcNsRegisterServiceCallBackFunc(uuid,
(void *)&TimerCallbackFunc);
if (ret != 0) {
tloge("failed to TcNsRegisterServiceCallBackFunc\n");
}
}
#define PARAM1 1
#define DUMP_UUID_INDEX0 0
#define DUMP_UUID_INDEX1 1
#define DUMP_UUID_INDEX2 2
#define DUMP_UUID_INDEX3 3
static int HandleTstCmdId(int cmdId, TcNsClientContext *clientContext)
{
int timerType;
int ret;
switch (cmdId) {
case TST_CMD_01:
CallbackDemoMain((char *)clientContext->uuid);
break;
case TST_CMD_02:
TstGetTimerType(&timerType);
if (TcUserParamValid(clientContext, (unsigned int)PARAM1)) {
tloge("param 1 is invalid\n");
ret = -EFAULT;
return ret;
}
if (copy_to_user(
(void *)(uintptr_t)clientContext->params[PARAM1].value.aAddr,
&timerType, sizeof(timerType))) {
tloge("copy to user failed:timerType\n");
ret = -ENOMEM;
return ret;
}
break;
default:
ret = -EINVAL;
return ret;
}
return 0;
}
int TcNsTstCmd(TcNsDevFile *devId, void *argp)
{
TcNsClientContext clientContext;
int ret;
int cmdId;
TeecUuid secureTimerUuid = {
0x19b39980, 0x2487, 0x7b84,
{0xf4, 0x1a, 0xbc, 0x89, 0x22, 0x62, 0xbb, 0x3d}
};
if (argp == NULL) {
tloge("argp is NULL input buffer\n");
ret = -EINVAL;
return ret;
}
if (copy_from_user(&clientContext, argp, sizeof(clientContext))) {
tloge("copy from user failed\n");
ret = -ENOMEM;
return ret;
}
if (TcUserParamValid(&clientContext, (unsigned int)0)) {
tloge("param 0 is invalid\n");
ret = -EFAULT;
return ret;
}
/* aAddr contain the command id */
if (copy_from_user(&cmdId, (void *)(uintptr_t)clientContext.params[0].value.aAddr, sizeof(cmdId))) {
tloge("copy from user failed:cmdId\n");
ret = -ENOMEM;
return ret;
}
if (memcmp((char *)clientContext.uuid, (char *)&secureTimerUuid, sizeof(TeecUuid))) {
tloge("request not from secure_timer\n");
tloge("request uuid: %x %x %x %x\n", clientContext.uuid[DUMP_UUID_INDEX0],
clientContext.uuid[DUMP_UUID_INDEX1], clientContext.uuid[DUMP_UUID_INDEX2],
clientContext.uuid[DUMP_UUID_INDEX3]); // just wanna print the first four characters of uuid
ret = -EACCES;
return ret;
}
ret = HandleTstCmdId(cmdId, &clientContext);
if (ret) {
return ret;
}
if (copy_to_user(argp, (void *)&clientContext, sizeof(clientContext))) {
tloge("copy to user failed:client context\n");
ret = -ENOMEM;
return ret;
}
return ret;
}
#endif
static int TcNsRegisterNotifyDataMemory(void)
{
TcNsSmcCmd smcCmd = { {0}, 0 };
int ret;
struct MbCmdPack *mbPack = NULL;
mbPack = MailboxAllocCmdPack();
if (mbPack == NULL) {
return TEEC_ERROR_GENERIC;
}
mbPack->operation.paramTypes =
TEE_PARAM_TYPE_VALUE_INPUT | TEE_PARAM_TYPE_VALUE_INPUT << TEE_PARAM_NUM;
mbPack->operation.params[TEE_PARAM_ONE].value.a = LOS_PaddrQuery(g_notifyData);
mbPack->operation.params[TEE_PARAM_ONE].value.b = 0;
mbPack->operation.params[TEE_PARAM_TWO].value.a = SZ_4K;
smcCmd.globalCmd = true;
smcCmd.cmdId = GLOBAL_CMD_ID_REGISTER_NOTIFY_MEMORY;
smcCmd.operationPhys = LOS_PaddrQuery(&mbPack->operation);
smcCmd.operationHphys = 0;
tlogd("cmd. context_phys:%x\n", smcCmd.contextId);
ret = TcNsSmc(&smcCmd);
MailboxFree(mbPack);
mbPack = NULL;
return ret;
}
static int TcNsUnregisterNotifyDataMemory(void)
{
TcNsSmcCmd smcCmd = { {0}, 0 };
int ret;
struct MbCmdPack *mbPack = NULL;
mbPack = MailboxAllocCmdPack();
if (mbPack == NULL) {
return TEEC_ERROR_GENERIC;
}
mbPack->operation.paramTypes =
TEE_PARAM_TYPE_VALUE_INPUT | TEE_PARAM_TYPE_VALUE_INPUT << TEE_PARAM_NUM;
mbPack->operation.params[TEE_PARAM_ONE].value.a = LOS_PaddrQuery(g_notifyData);
mbPack->operation.params[TEE_PARAM_ONE].value.b = 0;
mbPack->operation.params[TEE_PARAM_TWO].value.a = SZ_4K;
smcCmd.globalCmd = true;
smcCmd.cmdId = GLOBAL_CMD_ID_UNREGISTER_NOTIFY_MEMORY;
smcCmd.operationPhys = LOS_PaddrQuery(&mbPack->operation);
smcCmd.operationHphys = 0;
tlogd("cmd. context_phys:%x\n", smcCmd.contextId);
ret = TcNsSmc(&smcCmd);
MailboxFree(mbPack);
mbPack = NULL;
return ret;
}
static int InitNotifyData(void)
{
if (g_notifyData != NULL) {
return 0;
}
g_notifyData = (struct NotifyDataStruct *)GetPhyPage();
if (g_notifyData == NULL) {
tloge("GetFreePage failed for notification data\n");
return -ENOMEM;
}
int ret = memset_s(g_notifyData, PAGESIZE, 0, sizeof(struct NotifyDataStruct));
if (ret != EOK) {
return -EFAULT;
}
ret = TcNsRegisterNotifyDataMemory();
if (ret != TEEC_SUCCESS) {
tloge("Shared memory failed ret is 0x%x\n", ret);
FreePhyPage(g_notifyData);
g_notifyData = NULL;
return -EFAULT;
}
g_notifyDataEntryTimer = &g_notifyData->entry[NOTIFY_DATA_ENTRY_TIMER - 1];
g_notifyDataEntryRtc = &g_notifyData->entry[NOTIFY_DATA_ENTRY_RTC - 1];
#ifdef CONFIG_TEE_SMP
g_notifyDataEntryShadow = &g_notifyData->entry[NOTIFY_DATA_ENTRY_SHADOW - 1];
tlogi("test target is: %llx\n", g_notifyDataEntryShadow->context.shadow.targetTcb);
#endif
return 0;
}
int TzSpiInit()
{
unsigned int irq;
#ifdef CONFIG_TEE_SMP
g_tzSpiWq = AllocOrderedWorkqueue("g_tzSpiWq", WQ_HIGHPRI);
if (g_tzSpiWq == NULL) {
tloge("it failed to create workqueue g_tzSpiWq\n");
return -ENOMEM;
}
#endif
/* Map IRQ 0 from the OF interrupts list */
irq = NUM_HAL_INTERRUPT_TEE_SPI_NOTIFY;
int ret = DevmRequestIrq(irq, TcSecureNotify, IRQF_NO_SUSPEND, TC_NS_CLIENT_DEV, NULL);
if (ret < 0) {
tloge("device irq %u request failed %u", irq, ret);
goto clean;
}
ret = memset_s(&g_taCallbackFuncList, sizeof(g_taCallbackFuncList), 0, sizeof(g_taCallbackFuncList));
if (ret != EOK) {
ret = -EFAULT;
goto clean;
}
g_taCallbackFuncList.callbackCount = 0;
INIT_LIST_HEAD(&g_taCallbackFuncList.callbackList);
mutex_init(&g_taCallbackFuncList.callbackListLock);
ret = InitNotifyData();
if (ret < 0) {
goto clean;
}
g_spiInited = 1;
return 0;
clean:
TzSpiExit();
return ret;
}
void TzSpiExit(void)
{
g_spiInited = 0;
if (g_notifyData != NULL) {
if (TcNsUnregisterNotifyDataMemory() != TEEC_SUCCESS) {
tloge("unregister notify data mem failed\n");
}
FreePhyPage(g_notifyData);
g_notifyData = NULL;
}
#ifdef CONFIG_TEE_SMP
if (g_tzSpiWq != NULL) {
destroy_workqueue(g_tzSpiWq);
g_tzSpiWq = NULL;
}
#endif
}
-279
View File
@@ -1,279 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "tzdebug.h"
#include <securec.h>
#include <stdarg.h>
#include "cmdmonitor.h"
#include "mailbox_mempool.h"
#include "smc.h"
#include "tc_client_sub_driver.h"
#include "tc_ns_log.h"
#include "teek_client_api.h"
#include "teek_client_constants.h"
#include "teek_ns_client.h"
#include "tzdriver_compat.h"
typedef void (*TzdebugOptFunc)(const char *param);
struct OptOps {
char *name;
TzdebugOptFunc func;
};
static DEFINE_MUTEX(g_meminfoLock);
static struct TeeMem g_teeMeminfo = {0};
static int SendDumpMem(int flag, const struct TeeMem *statmem);
static void TzMemDump(const char *param);
void TeeDumpMem(void)
{
TzMemDump(NULL);
}
/* get meminfo (TeeMem + N * ta_mem < 4Kbyte) from tee */
static int GetTeeMemInfoCmd(void)
{
int ret;
int sret;
struct TeeMem *mem = (struct TeeMem *)MailboxAlloc(sizeof(*mem), MB_FLAG_ZERO);
if (mem == NULL) {
return -1;
}
ret = SendDumpMem(0, mem);
mutex_lock(&g_meminfoLock);
sret = memcpy_s((void *)&g_teeMeminfo, sizeof(g_teeMeminfo), mem, sizeof(*mem));
if (sret != EOK) {
tloge("sret=%d\n", sret);
}
mutex_unlock(&g_meminfoLock);
MailboxFree(mem);
return ret;
}
static atomic_t g_cmdSend = ATOMIC_INIT(1);
void SetCmdSendState(void)
{
atomic_set(&g_cmdSend, 1);
}
int GetTeeMeminfo(struct TeeMem *meminfo)
{
errno_t ret;
if (meminfo == NULL) {
return -1;
}
if (atomic_read(&g_cmdSend)) {
if (GetTeeMemInfoCmd() != 0) {
return -1;
}
} else {
atomic_set(&g_cmdSend, 0);
}
mutex_lock(&g_meminfoLock);
ret = memcpy_s((void *)meminfo, sizeof(*meminfo),
(void *)&g_teeMeminfo, sizeof(g_teeMeminfo));
mutex_unlock(&g_meminfoLock);
if (ret != EOK) {
return -1;
}
return 0;
}
EXPORT_SYMBOL(GetTeeMeminfo);
static int SendDumpMem(int flag, const struct TeeMem *statmem)
{
TcNsSmcCmd smcCmd = { {0}, 0 };
struct MbCmdPack *mbPack = NULL;
int ret;
if (statmem == NULL) {
tloge("statmem is NULL\n");
return -1;
}
mbPack = MailboxAllocCmdPack();
if (mbPack == NULL) {
return -ENOMEM;
}
smcCmd.cmdId = GLOBAL_CMD_ID_DUMP_MEMINFO;
smcCmd.globalCmd = true;
mbPack->operation.paramTypes = TEEC_PARAM_TYPES(
TEE_PARAM_TYPE_MEMREF_INOUT, TEE_PARAM_TYPE_VALUE_INPUT,
TEE_PARAM_TYPE_NONE, TEE_PARAM_TYPE_NONE);
mbPack->operation.params[TEE_PARAM_ONE].memref.buffer = LOS_PaddrQuery((void *)statmem);
mbPack->operation.params[TEE_PARAM_ONE].memref.size = sizeof(*statmem);
mbPack->operation.bufferHaddr[TEE_PARAM_ONE] = 0;
mbPack->operation.params[TEE_PARAM_TWO].value.a = flag;
smcCmd.operationPhys =
(unsigned int)LOS_PaddrQuery(&mbPack->operation);
smcCmd.operationHphys = 0;
ret = TcNsSmc(&smcCmd);
if (ret) {
tloge("SendDumpMem failed.\n");
}
MailboxFree(mbPack);
return ret;
}
static void ArchiveLog(const char *param)
{
(void)param;
TzDebugArchiveLog();
}
static void TzDump(const char *param)
{
(void)param;
ShowCmdBitmap();
WakeupTcSiq();
}
static void TzMemDump(const char *param)
{
struct TeeMem *mem = NULL;
(void)param;
mem = (struct TeeMem *)MailboxAlloc(sizeof(*mem), MB_FLAG_ZERO);
if (mem == NULL) {
tloge("mailbox alloc failed\n");
return;
}
if (SendDumpMem(1, mem) != 0) {
tloge("send dump mem failed\n");
}
MailboxFree(mem);
}
static int MemstatThread(UINTPTR arg, int len)
{
(void)len;
(void)arg;
return 0;
}
static void TzMemStat(const char *param)
{
LosTaskCB *stat_tsk = NULL;
(void)param;
stat_tsk = KthreadRun(MemstatThread, NULL, 0, "tzmemstat");
if (IS_ERR(stat_tsk)) {
tloge("memstat failed\n");
}
}
static void TzLogWriteDbg(const char *param)
{
(void)param;
}
static void TzHelp(const char *param);
static struct OptOps g_optArr[] = {
{"help", TzHelp},
{"archivelog", ArchiveLog},
{"dump", TzDump},
{"memdump", TzMemDump},
{"logwrite", TzLogWriteDbg},
{"dump_service", DumpServicesStatus},
{"memstat", TzMemStat},
};
static void TzHelp(const char *param)
{
uint32_t i;
(void)param;
for (i = 0; i < sizeof(g_optArr) / sizeof(struct OptOps); i++) {
tloge("cmd:%s\n", g_optArr[i].name);
}
}
static ssize_t TzDbgOptWrite(struct file *filp,
const char __user *ubuf, size_t cnt)
{
char buf[128] = {0}; /* 128, size of copy from ubuf */
char *value = NULL;
char *p = NULL;
uint32_t i = 0;
if ((ubuf == NULL) || (filp == NULL)) {
return -EINVAL;
}
if (cnt >= sizeof(buf)) {
return -EINVAL;
}
if (cnt == 0) {
return -EINVAL;
}
if (copy_from_user(buf, ubuf, cnt)) {
return -EFAULT;
}
buf[cnt] = 0;
if (cnt > 0 && buf[cnt - 1] == '\n') {
buf[cnt - 1] = 0;
}
value = buf;
p = strsep(&value, ":");
if (p == NULL) {
return -EINVAL;
}
for (i = 0; i < sizeof(g_optArr) / sizeof(struct OptOps); i++) {
if (!strncmp(p, g_optArr[i].name, strlen(g_optArr[i].name)) &&
strlen(p) == strlen(g_optArr[i].name)) {
g_optArr[i].func(value);
return cnt;
}
}
return -EFAULT;
}
static const struct file_operations_vfs g_tzDbgOptFops = {
.write = TzDbgOptWrite,
};
#define TC_NS_CLIENT_TZDEBUG "/dev/tzdebug"
int TzdebugInit(void)
{
int ret = CreateTcClientDevice(TC_NS_CLIENT_TZDEBUG, &g_tzDbgOptFops);
if (ret != EOK) {
return ret;
}
return 0;
}
-262
View File
@@ -1,262 +0,0 @@
/*
* Copyright (c) 2013-2019 Huawei Technologies Co., Ltd. All rights reserved.
* Copyright (c) 2020-2021 Huawei Device Co., Ltd. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification,
* are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* 3. Neither the name of the copyright holder nor the names of its contributors may be used
* to endorse or promote products derived from this software without specific prior written
* permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
* THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include "tzdriver_compat.h"
#include "mbedtls/aes.h"
LosTaskCB *KthreadRun(int (*threadfn)(UINTPTR data, int dataLen), void *data, int dataLen, char *name)
{
LosTaskCB *ktask = NULL;
UINT32 taskId = 0;
UINT32 ret;
TSK_INIT_PARAM_S taskInitParam;
if (threadfn == NULL) {
return NULL;
}
if (memset_s(&taskInitParam, sizeof(TSK_INIT_PARAM_S), 0, sizeof(TSK_INIT_PARAM_S)) != EOK) {
return NULL;
}
taskInitParam.pfnTaskEntry = (TSK_ENTRY_FUNC)threadfn;
taskInitParam.uwStackSize = LOSCFG_BASE_CORE_TSK_DEFAULT_STACK_SIZE;
taskInitParam.pcName = name;
taskInitParam.usTaskPrio = 1;
taskInitParam.auwArgs[0] = (UINTPTR)data;
taskInitParam.auwArgs[1] = dataLen;
taskInitParam.uwResved = LOS_TASK_STATUS_DETACHED;
ret = LOS_TaskCreate(&taskId, &taskInitParam);
if (ret != LOS_OK) {
return NULL;
}
ktask = (LosTaskCB *)OS_TCB_FROM_TID(taskId);
(VOID)LOS_TaskYield();
return ktask;
}
void KthreadStop(const LosTaskCB *k)
{
if (k != NULL) {
LOS_TaskDelete(k->taskID);
}
}
int KthreadShouldStop(void)
{
return (OsCurrTaskGet()->signal == SIGNAL_KILL);
}
ssize_t SimpleReadFromBuffer(void __user *to, size_t count,
const void *from, size_t available)
{
size_t ret;
if (count == 0 || available == 0) {
return 0;
}
if (count > available) {
count = available;
}
ret = copy_to_user(to, from, count);
if (ret == count) {
return -EFAULT;
}
count -= ret;
return count;
}
#define MAX_ORDER 31
LosVmPage *MailboxPoolAllocPages(unsigned int order)
{
if (order > MAX_ORDER) {
return NULL;
}
void *ptr = LOS_PhysPagesAllocContiguous(1UL << order);
if (ptr == NULL) {
PRINTK("mailbox pool contiguous ptr null size %x\n", 1 << order);
return NULL;
}
for (int i = 0; i < (1UL << order); i++) {
// mempool is used to mmap, add ref to prevent pmm free page to free list.
LosVmPage *page = OsVmVaddrToPage((void *)((intptr_t)ptr + PAGE_SIZE * i));
if (page != NULL) {
LOS_AtomicInc(&page->refCounts);
}
}
return OsVmVaddrToPage(ptr);
}
void MailboxPoolFreePages(LosVmPage *pageArray, size_t order)
{
if (pageArray == NULL || order > MAX_ORDER) {
return;
}
for (int i = 0; i < (1UL << order); i++) {
LOS_AtomicDec(&(pageArray[i].refCounts));
}
LOS_PhysPagesFreeContiguous(pageArray, (1UL << order));
}
INT32 DoVmallocRemap(LosVmMapRegion *vma, void *kvaddr)
{
int i;
int ret = 0;
paddr_t pa;
UINT32 uflags = VM_MAP_REGION_FLAG_PERM_READ | VM_MAP_REGION_FLAG_PERM_WRITE | VM_MAP_REGION_FLAG_PERM_USER;
LosVmPage *vmPage = NULL;
if (vma == NULL || kvaddr == NULL) {
return -EINVAL;
}
LosVmSpace *vSpace = LOS_SpaceGet(vma->range.base);
if (vSpace == NULL) {
return -EINVAL;
}
vaddr_t kva = (vaddr_t)(uintptr_t)kvaddr;
vaddr_t uva = vma->range.base;
unsigned int page;
(VOID)LOS_MuxAcquire(&vSpace->regionMux);
for (i = 0; i < (vma->range.size >> PAGE_SHIFT); i++) {
page = (unsigned int)i;
pa = LOS_PaddrQuery((void *)(uintptr_t)(kva + (page << PAGE_SHIFT)));
if (pa == 0) {
PRINT_ERR("%s, %d\n", __FUNCTION__, __LINE__);
ret = -EINVAL;
break;
}
vmPage = LOS_VmPageGet(pa);
if (vmPage == NULL) {
PRINT_ERR("%s, %d\n", __FUNCTION__, __LINE__);
ret = -EINVAL;
break;
}
status_t err = LOS_ArchMmuMap(&vSpace->archMmu, uva + (page << PAGE_SHIFT), pa, 1, uflags);
if (err < 0) {
ret = err;
PRINT_ERR("%s, %d\n", __FUNCTION__, __LINE__);
break;
}
LOS_AtomicInc(&vmPage->refCounts);
}
/* if any failure happened, rollback */
if (i < (vma->range.size >> PAGE_SHIFT)) {
for (i = i - 1; i >= 0; i--) {
page = (unsigned int)i;
pa = LOS_PaddrQuery((void *)(uintptr_t)(kva + (page << PAGE_SHIFT)));
vmPage = LOS_VmPageGet(pa);
(VOID)LOS_ArchMmuUnmap(&vSpace->archMmu, uva + (page << PAGE_SHIFT), 1);
(VOID)LOS_PhysPageFree(vmPage);
}
}
(VOID)LOS_MuxRelease(&vSpace->regionMux);
return ret;
}
int RemapVmallocRange(LosVmMapRegion *vma, void *addr,
unsigned long pgoff)
{
if (pgoff != 0) {
return -1;
}
return DoVmallocRemap(vma, addr);
}
int CreateTcClientDevice(const char *devName, const struct file_operations_vfs *op)
{
int ret = register_driver(devName, op, TEE_DEV_PRI, NULL);
if (unlikely(ret)) {
return -1;
}
return EOK;
}
#define IV_LEN 16
#define KEY_BITS 256
#define MAX_AES_CRYPT_SIZE SZ_4M
int CryptoAescbcKey256(unsigned char *output, const unsigned char *input, struct AesParam *param)
{
mbedtls_aes_context ctx;
int ret;
if (!output || !input) {
return -1;
}
if (!param || !param->iv || !param->key ||
param->size < 0 || param->size > MAX_AES_CRYPT_SIZE) {
return -1;
}
int mode = param->encryptoType ? MBEDTLS_AES_ENCRYPT : MBEDTLS_AES_DECRYPT;
unsigned char ivTmp[IV_LEN] = {0};
ret = memcpy_s(ivTmp, IV_LEN, param->iv, IV_LEN);
if (ret != EOK) {
return -1;
}
mbedtls_aes_init(&ctx);
if (mode == MBEDTLS_AES_ENCRYPT) {
ret = mbedtls_aes_setkey_enc(&ctx, param->key, KEY_BITS);
} else {
ret = mbedtls_aes_setkey_dec(&ctx, param->key, KEY_BITS);
}
if (ret) {
return -1;
}
return mbedtls_aes_crypt_cbc(&ctx, mode, param->size, ivTmp, input, output);
}
void SetVmmRegionCodeStart(UINTPTR codeStart, UINT32 codeSize)
{
LosVmSpace *space = NULL;
space = OsCurrProcessGet()->vmSpace;
if (space->codeStart != 0) {
return;
}
if (codeSize == 0 || codeStart + codeSize < codeStart) {
return;
}
space->codeStart = codeStart;
space->codeEnd = codeStart + codeSize;
}