Lines Matching +full:op +full:- +full:tee

1 // SPDX-License-Identifier: GPL-2.0-only
3 * Copyright (c) 2015-2021, 2023 Linaro Limited
34 * (optee->rpc_param_count).
44 mutex_init(&cq->mutex); in optee_cq_init()
45 INIT_LIST_HEAD(&cq->waiters); in optee_cq_init()
48 * If cq->total_thread_count is 0 then we're not trying to keep in optee_cq_init()
53 cq->total_thread_count = thread_count; in optee_cq_init()
54 cq->free_thread_count = thread_count; in optee_cq_init()
73 mutex_lock(&cq->mutex); in optee_cq_wait_init()
81 init_completion(&w->c); in optee_cq_wait_init()
82 list_add_tail(&w->list_node, &cq->waiters); in optee_cq_wait_init()
83 w->sys_thread = sys_thread; in optee_cq_wait_init()
85 if (cq->total_thread_count) { in optee_cq_wait_init()
86 if (sys_thread || !cq->sys_thread_req_count) in optee_cq_wait_init()
91 if (cq->free_thread_count > free_thread_threshold) in optee_cq_wait_init()
92 cq->free_thread_count--; in optee_cq_wait_init()
97 mutex_unlock(&cq->mutex); in optee_cq_wait_init()
101 mutex_lock(&cq->mutex); in optee_cq_wait_init()
103 if (sys_thread || !cq->sys_thread_req_count) in optee_cq_wait_init()
108 if (cq->free_thread_count > free_thread_threshold) { in optee_cq_wait_init()
109 cq->free_thread_count--; in optee_cq_wait_init()
113 mutex_unlock(&cq->mutex); in optee_cq_wait_init()
120 wait_for_completion(&w->c); in optee_cq_wait_for_completion()
122 mutex_lock(&cq->mutex); in optee_cq_wait_for_completion()
125 list_del(&w->list_node); in optee_cq_wait_for_completion()
126 reinit_completion(&w->c); in optee_cq_wait_for_completion()
127 list_add_tail(&w->list_node, &cq->waiters); in optee_cq_wait_for_completion()
129 mutex_unlock(&cq->mutex); in optee_cq_wait_for_completion()
137 list_for_each_entry(w, &cq->waiters, list_node) { in optee_cq_complete_one()
138 if (w->sys_thread && !completion_done(&w->c)) { in optee_cq_complete_one()
139 complete(&w->c); in optee_cq_complete_one()
144 list_for_each_entry(w, &cq->waiters, list_node) { in optee_cq_complete_one()
145 if (!completion_done(&w->c)) { in optee_cq_complete_one()
146 complete(&w->c); in optee_cq_complete_one()
160 mutex_lock(&cq->mutex); in optee_cq_wait_final()
163 list_del(&w->list_node); in optee_cq_wait_final()
165 cq->free_thread_count++; in optee_cq_wait_final()
176 if (completion_done(&w->c)) in optee_cq_wait_final()
179 mutex_unlock(&cq->mutex); in optee_cq_wait_final()
185 if (cq->total_thread_count <= 1) in optee_cq_incr_sys_thread_count()
188 mutex_lock(&cq->mutex); in optee_cq_incr_sys_thread_count()
189 cq->sys_thread_req_count++; in optee_cq_incr_sys_thread_count()
190 mutex_unlock(&cq->mutex); in optee_cq_incr_sys_thread_count()
197 mutex_lock(&cq->mutex); in optee_cq_decr_sys_thread_count()
198 cq->sys_thread_req_count--; in optee_cq_decr_sys_thread_count()
201 mutex_unlock(&cq->mutex); in optee_cq_decr_sys_thread_count()
210 list_for_each_entry(sess, &ctxdata->sess_list, list_node) in find_session()
211 if (sess->session_id == session_id) in find_session()
219 INIT_LIST_HEAD(&optee->shm_arg_cache.shm_args); in optee_shm_arg_cache_init()
220 mutex_init(&optee->shm_arg_cache.mutex); in optee_shm_arg_cache_init()
221 optee->shm_arg_cache.flags = flags; in optee_shm_arg_cache_init()
226 struct list_head *head = &optee->shm_arg_cache.shm_args; in optee_shm_arg_cache_uninit()
229 mutex_destroy(&optee->shm_arg_cache.mutex); in optee_shm_arg_cache_uninit()
233 list_del(&entry->list_node); in optee_shm_arg_cache_uninit()
234 if (find_first_bit(entry->map, MAX_ARG_COUNT_PER_ENTRY) != in optee_shm_arg_cache_uninit()
236 pr_err("Freeing non-free entry\n"); in optee_shm_arg_cache_uninit()
238 tee_shm_free(entry->shm); in optee_shm_arg_cache_uninit()
254 * optee_get_msg_arg() - Provide shared memory for argument struct
255 * @ctx: Caller TEE context
269 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_get_msg_arg()
270 size_t sz = optee_msg_arg_size(optee->rpc_param_count); in optee_get_msg_arg()
279 return ERR_PTR(-EINVAL); in optee_get_msg_arg()
281 if (optee->shm_arg_cache.flags & OPTEE_SHM_ARG_SHARED) in optee_get_msg_arg()
286 mutex_lock(&optee->shm_arg_cache.mutex); in optee_get_msg_arg()
287 list_for_each_entry(entry, &optee->shm_arg_cache.shm_args, list_node) { in optee_get_msg_arg()
288 bit = find_first_zero_bit(entry->map, MAX_ARG_COUNT_PER_ENTRY); in optee_get_msg_arg()
298 res = ERR_PTR(-ENOMEM); in optee_get_msg_arg()
302 if (optee->shm_arg_cache.flags & OPTEE_SHM_ARG_ALLOC_PRIV) in optee_get_msg_arg()
311 entry->shm = res; in optee_get_msg_arg()
312 list_add(&entry->list_node, &optee->shm_arg_cache.shm_args); in optee_get_msg_arg()
317 res = tee_shm_get_va(entry->shm, offs); in optee_get_msg_arg()
321 set_bit(bit, entry->map); in optee_get_msg_arg()
323 ma->num_params = num_params; in optee_get_msg_arg()
325 *shm_ret = entry->shm; in optee_get_msg_arg()
328 mutex_unlock(&optee->shm_arg_cache.mutex); in optee_get_msg_arg()
333 * optee_free_msg_arg() - Free previsouly obtained shared memory
334 * @ctx: Caller TEE context
343 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_free_msg_arg()
344 size_t sz = optee_msg_arg_size(optee->rpc_param_count); in optee_free_msg_arg()
353 mutex_lock(&optee->shm_arg_cache.mutex); in optee_free_msg_arg()
355 if (!test_bit(bit, entry->map)) in optee_free_msg_arg()
357 clear_bit(bit, entry->map); in optee_free_msg_arg()
359 mutex_unlock(&optee->shm_arg_cache.mutex); in optee_free_msg_arg()
366 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_open_session()
367 struct optee_context_data *ctxdata = ctx->data; in optee_open_session()
377 msg_arg = optee_get_msg_arg(ctx, arg->num_params + 2, in optee_open_session()
382 msg_arg->cmd = OPTEE_MSG_CMD_OPEN_SESSION; in optee_open_session()
383 msg_arg->cancel_id = arg->cancel_id; in optee_open_session()
389 msg_arg->params[0].attr = OPTEE_MSG_ATTR_TYPE_VALUE_INPUT | in optee_open_session()
391 msg_arg->params[1].attr = OPTEE_MSG_ATTR_TYPE_VALUE_INPUT | in optee_open_session()
393 memcpy(&msg_arg->params[0].u.value, arg->uuid, sizeof(arg->uuid)); in optee_open_session()
394 msg_arg->params[1].u.value.c = arg->clnt_login; in optee_open_session()
396 rc = tee_session_calc_client_uuid(&client_uuid, arg->clnt_login, in optee_open_session()
397 arg->clnt_uuid); in optee_open_session()
400 export_uuid(msg_arg->params[1].u.octets, &client_uuid); in optee_open_session()
402 rc = optee->ops->to_msg_param(optee, msg_arg->params + 2, in optee_open_session()
403 arg->num_params, param); in optee_open_session()
409 rc = -ENOMEM; in optee_open_session()
413 if (optee->ops->do_call_with_arg(ctx, shm, offs, in optee_open_session()
414 sess->use_sys_thread)) { in optee_open_session()
415 msg_arg->ret = TEEC_ERROR_COMMUNICATION; in optee_open_session()
416 msg_arg->ret_origin = TEEC_ORIGIN_COMMS; in optee_open_session()
419 if (msg_arg->ret == TEEC_SUCCESS) { in optee_open_session()
421 sess->session_id = msg_arg->session; in optee_open_session()
422 mutex_lock(&ctxdata->mutex); in optee_open_session()
423 list_add(&sess->list_node, &ctxdata->sess_list); in optee_open_session()
424 mutex_unlock(&ctxdata->mutex); in optee_open_session()
429 if (optee->ops->from_msg_param(optee, param, arg->num_params, in optee_open_session()
430 msg_arg->params + 2)) { in optee_open_session()
431 arg->ret = TEEC_ERROR_COMMUNICATION; in optee_open_session()
432 arg->ret_origin = TEEC_ORIGIN_COMMS; in optee_open_session()
434 optee_close_session(ctx, msg_arg->session); in optee_open_session()
436 arg->session = msg_arg->session; in optee_open_session()
437 arg->ret = msg_arg->ret; in optee_open_session()
438 arg->ret_origin = msg_arg->ret_origin; in optee_open_session()
448 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_system_session()
449 struct optee_context_data *ctxdata = ctx->data; in optee_system_session()
451 int rc = -EINVAL; in optee_system_session()
453 mutex_lock(&ctxdata->mutex); in optee_system_session()
456 if (sess && (sess->use_sys_thread || in optee_system_session()
457 optee_cq_incr_sys_thread_count(&optee->call_queue))) { in optee_system_session()
458 sess->use_sys_thread = true; in optee_system_session()
462 mutex_unlock(&ctxdata->mutex); in optee_system_session()
470 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_close_session_helper()
480 msg_arg->cmd = OPTEE_MSG_CMD_CLOSE_SESSION; in optee_close_session_helper()
481 msg_arg->session = session; in optee_close_session_helper()
482 optee->ops->do_call_with_arg(ctx, shm, offs, system_thread); in optee_close_session_helper()
487 optee_cq_decr_sys_thread_count(&optee->call_queue); in optee_close_session_helper()
494 struct optee_context_data *ctxdata = ctx->data; in optee_close_session()
499 mutex_lock(&ctxdata->mutex); in optee_close_session()
502 list_del(&sess->list_node); in optee_close_session()
503 mutex_unlock(&ctxdata->mutex); in optee_close_session()
505 return -EINVAL; in optee_close_session()
506 system_thread = sess->use_sys_thread; in optee_close_session()
515 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_invoke_func()
516 struct optee_context_data *ctxdata = ctx->data; in optee_invoke_func()
526 mutex_lock(&ctxdata->mutex); in optee_invoke_func()
527 sess = find_session(ctxdata, arg->session); in optee_invoke_func()
529 system_thread = sess->use_sys_thread; in optee_invoke_func()
530 mutex_unlock(&ctxdata->mutex); in optee_invoke_func()
532 return -EINVAL; in optee_invoke_func()
534 msg_arg = optee_get_msg_arg(ctx, arg->num_params, in optee_invoke_func()
538 msg_arg->cmd = OPTEE_MSG_CMD_INVOKE_COMMAND; in optee_invoke_func()
539 msg_arg->func = arg->func; in optee_invoke_func()
540 msg_arg->session = arg->session; in optee_invoke_func()
541 msg_arg->cancel_id = arg->cancel_id; in optee_invoke_func()
543 rc = optee->ops->to_msg_param(optee, msg_arg->params, arg->num_params, in optee_invoke_func()
548 if (optee->ops->do_call_with_arg(ctx, shm, offs, system_thread)) { in optee_invoke_func()
549 msg_arg->ret = TEEC_ERROR_COMMUNICATION; in optee_invoke_func()
550 msg_arg->ret_origin = TEEC_ORIGIN_COMMS; in optee_invoke_func()
553 if (optee->ops->from_msg_param(optee, param, arg->num_params, in optee_invoke_func()
554 msg_arg->params)) { in optee_invoke_func()
555 msg_arg->ret = TEEC_ERROR_COMMUNICATION; in optee_invoke_func()
556 msg_arg->ret_origin = TEEC_ORIGIN_COMMS; in optee_invoke_func()
559 arg->ret = msg_arg->ret; in optee_invoke_func()
560 arg->ret_origin = msg_arg->ret_origin; in optee_invoke_func()
568 struct optee *optee = tee_get_drvdata(ctx->teedev); in optee_cancel_req()
569 struct optee_context_data *ctxdata = ctx->data; in optee_cancel_req()
578 mutex_lock(&ctxdata->mutex); in optee_cancel_req()
581 system_thread = sess->use_sys_thread; in optee_cancel_req()
582 mutex_unlock(&ctxdata->mutex); in optee_cancel_req()
584 return -EINVAL; in optee_cancel_req()
590 msg_arg->cmd = OPTEE_MSG_CMD_CANCEL; in optee_cancel_req()
591 msg_arg->session = session; in optee_cancel_req()
592 msg_arg->cancel_id = cancel_id; in optee_cancel_req()
593 optee->ops->do_call_with_arg(ctx, shm, offs, system_thread); in optee_cancel_req()
618 if (!is_normal_memory(vma->vm_page_prot)) in __check_mem_type()
619 return -EINVAL; in __check_mem_type()
627 struct mm_struct *mm = current->mm; in optee_check_mem_type()
631 * Allow kernel address to register with OP-TEE as kernel in optee_check_mem_type()
646 struct optee *optee = tee_get_drvdata(ctx->teedev); in simple_call_with_arg()
656 msg_arg->cmd = cmd; in simple_call_with_arg()
657 optee->ops->do_call_with_arg(ctx, shm, offs, false); in simple_call_with_arg()