summaryrefslogtreecommitdiff
path: root/lib/libutee/tee_socket_pta.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libutee/tee_socket_pta.c')
-rw-r--r--lib/libutee/tee_socket_pta.c182
1 files changed, 182 insertions, 0 deletions
diff --git a/lib/libutee/tee_socket_pta.c b/lib/libutee/tee_socket_pta.c
new file mode 100644
index 0000000..ddb4fb7
--- /dev/null
+++ b/lib/libutee/tee_socket_pta.c
@@ -0,0 +1,182 @@
+/*
+ * Copyright (c) 2016-2017, Linaro Limited
+ * 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.
+ *
+ * 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 <pta_socket.h>
+#include <string.h>
+#include <tee_internal_api.h>
+#include <__tee_tcpsocket_defines.h>
+#include <__tee_udpsocket_defines.h>
+
+#include "tee_socket_private.h"
+
+static TEE_Result invoke_socket_pta(uint32_t cmd_id, uint32_t param_types,
+ TEE_Param params[TEE_NUM_PARAMS])
+{
+ static TEE_TASessionHandle sess = TEE_HANDLE_NULL;
+ static const TEE_UUID socket_uuid = PTA_SOCKET_UUID;
+
+ if (sess == TEE_HANDLE_NULL) {
+ TEE_Result res = TEE_OpenTASession(&socket_uuid, 0, 0, NULL,
+ &sess, NULL);
+
+ if (res != TEE_SUCCESS)
+ return res;
+ }
+
+ return TEE_InvokeTACommand(sess, 0, cmd_id, param_types, params, NULL);
+}
+
+TEE_Result __tee_socket_pta_open(TEE_ipSocket_ipVersion ip_vers,
+ const char *addr, uint16_t port,
+ uint32_t protocol, uint32_t *handle)
+{
+ TEE_Result res;
+ uint32_t param_types;
+ TEE_Param params[TEE_NUM_PARAMS];
+
+ param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_MEMREF_INPUT,
+ TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_VALUE_OUTPUT);
+ memset(params, 0, sizeof(params));
+
+ switch (ip_vers) {
+ case TEE_IP_VERSION_DC:
+ case TEE_IP_VERSION_4:
+ case TEE_IP_VERSION_6:
+ params[0].value.a = ip_vers;
+ break;
+ default:
+ return TEE_ERROR_BAD_PARAMETERS;
+ }
+
+ params[0].value.b = port;
+
+ if (!addr)
+ return TEE_ERROR_BAD_PARAMETERS;
+ params[1].memref.buffer = (void *)addr;
+ params[1].memref.size = strlen(addr) + 1;
+
+ switch (protocol) {
+ case TEE_ISOCKET_PROTOCOLID_TCP:
+ case TEE_ISOCKET_PROTOCOLID_UDP:
+ params[2].value.a = protocol;
+ break;
+ default:
+ return TEE_ERROR_BAD_PARAMETERS;
+ }
+
+ res = invoke_socket_pta(PTA_SOCKET_OPEN, param_types, params);
+ if (res == TEE_SUCCESS)
+ *handle = params[3].value.a;
+ return res;
+}
+
+TEE_Result __tee_socket_pta_close(uint32_t handle)
+{
+ uint32_t param_types;
+ TEE_Param params[TEE_NUM_PARAMS];
+
+ param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_NONE, TEE_PARAM_TYPE_NONE,
+ TEE_PARAM_TYPE_NONE);
+ memset(params, 0, sizeof(params));
+
+ params[0].value.a = handle;
+ return invoke_socket_pta(PTA_SOCKET_CLOSE, param_types, params);
+}
+
+TEE_Result __tee_socket_pta_send(uint32_t handle, const void *buf,
+ uint32_t *len, uint32_t timeout)
+{
+ TEE_Result res;
+ uint32_t param_types;
+ TEE_Param params[TEE_NUM_PARAMS];
+
+ param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_MEMREF_INPUT,
+ TEE_PARAM_TYPE_VALUE_OUTPUT,
+ TEE_PARAM_TYPE_NONE);
+ memset(params, 0, sizeof(params));
+
+ params[0].value.a = handle;
+ params[0].value.b = timeout;
+
+ params[1].memref.buffer = (void *)buf;
+ params[1].memref.size = *len;
+
+ res = invoke_socket_pta(PTA_SOCKET_SEND, param_types, params);
+ *len = params[2].value.a;
+ return res;
+}
+
+TEE_Result __tee_socket_pta_recv(uint32_t handle, void *buf, uint32_t *len,
+ uint32_t timeout)
+
+{
+ TEE_Result res;
+ uint32_t param_types;
+ TEE_Param params[TEE_NUM_PARAMS];
+
+ param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_MEMREF_OUTPUT,
+ TEE_PARAM_TYPE_NONE, TEE_PARAM_TYPE_NONE);
+ memset(params, 0, sizeof(params));
+
+ params[0].value.a = handle;
+ params[0].value.b = timeout;
+
+ params[1].memref.buffer = buf;
+ params[1].memref.size = *len;
+
+ res = invoke_socket_pta(PTA_SOCKET_RECV, param_types, params);
+ *len = params[1].memref.size;
+ return res;
+}
+
+TEE_Result __tee_socket_pta_ioctl(uint32_t handle, uint32_t command, void *buf,
+ uint32_t *len)
+{
+ TEE_Result res;
+ uint32_t param_types;
+ TEE_Param params[TEE_NUM_PARAMS];
+
+ param_types = TEE_PARAM_TYPES(TEE_PARAM_TYPE_VALUE_INPUT,
+ TEE_PARAM_TYPE_MEMREF_INOUT,
+ TEE_PARAM_TYPE_NONE, TEE_PARAM_TYPE_NONE);
+ memset(params, 0, sizeof(params));
+
+ params[0].value.a = handle;
+ params[0].value.b = command;
+
+ params[1].memref.buffer = buf;
+ params[1].memref.size = *len;
+
+ res = invoke_socket_pta(PTA_SOCKET_IOCTL, param_types, params);
+ *len = params[1].memref.size;
+ return res;
+}