Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Fork of mbed-os by
box_init.c
00001 /* 00002 * Copyright (c) 2016, ARM Limited, All Rights Reserved 00003 * SPDX-License-Identifier: Apache-2.0 00004 * 00005 * Licensed under the Apache License, Version 2.0 (the "License"); you may 00006 * not use this file except in compliance with the License. 00007 * You may obtain a copy of the License at 00008 * 00009 * http://www.apache.org/licenses/LICENSE-2.0 00010 * 00011 * Unless required by applicable law or agreed to in writing, software 00012 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 00013 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00014 * See the License for the specific language governing permissions and 00015 * limitations under the License. 00016 */ 00017 #include "uvisor-lib/uvisor-lib.h" 00018 #include "api/inc/pool_queue_exports.h" 00019 #include "api/inc/rpc_exports.h" 00020 #include "api/inc/uvisor_semaphore.h" 00021 #include "mbed_interface.h" 00022 #include "cmsis_os.h" 00023 #include <stdint.h> 00024 #include <string.h> 00025 00026 /* Register the OS with uVisor */ 00027 extern void SVC_Handler(void); 00028 extern void PendSV_Handler(void); 00029 extern void SysTick_Handler(void); 00030 extern uint32_t rt_suspend(void); 00031 00032 UVISOR_SET_PRIV_SYS_HOOKS(SVC_Handler, PendSV_Handler, SysTick_Handler, rt_suspend, __uvisor_semaphore_post); 00033 00034 extern RtxBoxIndex * const __uvisor_ps; 00035 00036 void __uvisor_initialize_rpc_queues(void) 00037 { 00038 UvisorBoxIndex * const index = &__uvisor_ps->index; 00039 00040 uvisor_pool_slot_t i; 00041 00042 uvisor_rpc_outgoing_message_queue_t * rpc_outgoing_msg_queue = index->rpc_outgoing_message_queue; 00043 uvisor_rpc_incoming_message_queue_t * rpc_incoming_msg_queue = index->rpc_incoming_message_queue; 00044 uvisor_rpc_fn_group_queue_t * rpc_fn_group_queue = index->rpc_fn_group_queue; 00045 00046 /* Initialize the outgoing RPC message queue. */ 00047 if (uvisor_pool_queue_init(&rpc_outgoing_msg_queue->queue, 00048 &rpc_outgoing_msg_queue->pool, 00049 rpc_outgoing_msg_queue->messages, 00050 sizeof(*rpc_outgoing_msg_queue->messages), 00051 UVISOR_RPC_OUTGOING_MESSAGE_SLOTS, 00052 UVISOR_POOL_QUEUE_BLOCKING)) { 00053 uvisor_error(USER_NOT_ALLOWED); 00054 } 00055 00056 /* Initialize all the result semaphores. */ 00057 for (i = 0; i < UVISOR_RPC_OUTGOING_MESSAGE_SLOTS; i++) { 00058 UvisorSemaphore * semaphore = &rpc_outgoing_msg_queue->messages[i].semaphore; 00059 if (__uvisor_semaphore_init(semaphore, 1)) { 00060 uvisor_error(USER_NOT_ALLOWED); 00061 } 00062 00063 /* Semaphores are created with their value initialized to count. We 00064 * want the semaphore to start at zero. Decrement the semaphore, so it 00065 * starts with a value of zero. This will allow the first pend to 00066 * block. */ 00067 if (__uvisor_semaphore_pend(semaphore, 0)) { 00068 uvisor_error(USER_NOT_ALLOWED); 00069 } 00070 } 00071 00072 /* Initialize the incoming RPC message queues. */ 00073 if (uvisor_pool_queue_init(&rpc_incoming_msg_queue->todo_queue, 00074 &rpc_incoming_msg_queue->pool, 00075 rpc_incoming_msg_queue->messages, 00076 sizeof(*rpc_incoming_msg_queue->messages), 00077 UVISOR_RPC_INCOMING_MESSAGE_SLOTS, 00078 UVISOR_POOL_QUEUE_NON_BLOCKING)) { 00079 uvisor_error(USER_NOT_ALLOWED); 00080 } 00081 /* This is a double init of the pool. We need a function that just inits 00082 * the queue, not the pool, and init everybody separately. */ 00083 if (uvisor_pool_queue_init(&rpc_incoming_msg_queue->done_queue, 00084 &rpc_incoming_msg_queue->pool, 00085 rpc_incoming_msg_queue->messages, 00086 sizeof(*rpc_incoming_msg_queue->messages), 00087 UVISOR_RPC_INCOMING_MESSAGE_SLOTS, 00088 UVISOR_POOL_QUEUE_NON_BLOCKING)) { 00089 uvisor_error(USER_NOT_ALLOWED); 00090 } 00091 00092 /* Initialize the function group pool. */ 00093 if (uvisor_pool_queue_init(&rpc_fn_group_queue->queue, 00094 &rpc_fn_group_queue->pool, 00095 rpc_fn_group_queue->fn_groups, 00096 sizeof(*rpc_fn_group_queue->fn_groups), 00097 UVISOR_RPC_FN_GROUP_SLOTS, 00098 UVISOR_POOL_QUEUE_BLOCKING)) { 00099 uvisor_error(USER_NOT_ALLOWED); 00100 } 00101 00102 /* Initialize all the function group semaphores. */ 00103 for (i = 0; i < UVISOR_RPC_FN_GROUP_SLOTS; i++) { 00104 UvisorSemaphore * semaphore = &rpc_fn_group_queue->fn_groups[i].semaphore; 00105 if (__uvisor_semaphore_init(semaphore, 1)) { 00106 uvisor_error(USER_NOT_ALLOWED); 00107 } 00108 00109 /* Semaphores are created with their value initialized to count. We 00110 * want the semaphore to start at zero. Decrement the semaphore, so it 00111 * starts with a value of zero. This will allow the first pend to 00112 * block. */ 00113 if (__uvisor_semaphore_pend(semaphore, 0)) { 00114 uvisor_error(USER_NOT_ALLOWED); 00115 } 00116 } 00117 } 00118 00119 /* This function is called by uVisor in unprivileged mode. On this OS, we 00120 * create box main threads for the box. */ 00121 void __uvisor_lib_box_init(void * lib_config) 00122 { 00123 osThreadId thread_id; 00124 osThreadDef_t * flash_thread_def = lib_config; 00125 osThreadDef_t thread_def; 00126 00127 __uvisor_initialize_rpc_queues(); 00128 00129 /* Copy thread definition from flash to RAM. The thread definition is most 00130 * likely in flash, so we need to copy it to box-local RAM before we can 00131 * modify it. */ 00132 memcpy(&thread_def, flash_thread_def, sizeof(thread_def)); 00133 00134 /* Note that the box main thread stack is separate from the box stack. This 00135 * is because the thread must be created to use a different stack than the 00136 * stack osCreateThread() is called from, as context information is saved 00137 * to the thread stack by the call to osCreateThread(). */ 00138 /* Allocate memory for the main thread from the process heap (which is 00139 * private to the process). This memory is never freed, even if the box's 00140 * main thread exits. */ 00141 thread_def.stack_pointer = malloc_p(thread_def.stacksize); 00142 00143 if (thread_def.stack_pointer == NULL) { 00144 /* No process heap memory available */ 00145 mbed_die(); 00146 } 00147 00148 thread_id = osThreadCreate(&thread_def, NULL); 00149 00150 if (thread_id == NULL) { 00151 /* Failed to create thread */ 00152 mbed_die(); 00153 } 00154 }
Generated on Tue Jul 12 2022 13:15:32 by
