mbed library sources. Supersedes mbed-src.
Fork of mbed-dev by
Embed:
(wiki syntax)
Show/hide line numbers
SingletonPtr.h
00001 00002 /** \addtogroup platform */ 00003 /** @{*/ 00004 /* mbed Microcontroller Library 00005 * Copyright (c) 2006-2013 ARM Limited 00006 * 00007 * Licensed under the Apache License, Version 2.0 (the "License"); 00008 * you may not use this file except in compliance with the License. 00009 * You may obtain a copy of the License at 00010 * 00011 * http://www.apache.org/licenses/LICENSE-2.0 00012 * 00013 * Unless required by applicable law or agreed to in writing, software 00014 * distributed under the License is distributed on an "AS IS" BASIS, 00015 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00016 * See the License for the specific language governing permissions and 00017 * limitations under the License. 00018 */ 00019 #ifndef SINGLETONPTR_H 00020 #define SINGLETONPTR_H 00021 00022 #include <stdint.h> 00023 #include <new> 00024 #include "platform/mbed_assert.h" 00025 #ifdef MBED_CONF_RTOS_PRESENT 00026 #include "cmsis_os.h" 00027 #endif 00028 00029 #ifdef MBED_CONF_RTOS_PRESENT 00030 extern osMutexId singleton_mutex_id; 00031 #endif 00032 00033 /** Lock the singleton mutex 00034 * 00035 * This function is typically used to provide 00036 * exclusive access when initializing a 00037 * global object. 00038 */ 00039 inline static void singleton_lock(void) 00040 { 00041 #ifdef MBED_CONF_RTOS_PRESENT 00042 osMutexWait(singleton_mutex_id, osWaitForever); 00043 #endif 00044 } 00045 00046 /** Unlock the singleton mutex 00047 * 00048 * This function is typically used to provide 00049 * exclusive access when initializing a 00050 * global object. 00051 */ 00052 inline static void singleton_unlock(void) 00053 { 00054 #ifdef MBED_CONF_RTOS_PRESENT 00055 osMutexRelease (singleton_mutex_id); 00056 #endif 00057 } 00058 00059 /** Utility class for creating an using a singleton 00060 * 00061 * @Note Synchronization level: Thread safe 00062 * 00063 * @Note: This class must only be used in a static context - 00064 * this class must never be allocated or created on the 00065 * stack. 00066 * 00067 * @Note: This class is lazily initialized on first use. 00068 * This class is a POD type so if it is not used it will 00069 * be garbage collected. 00070 */ 00071 template <class T> 00072 struct SingletonPtr { 00073 00074 /** Get a pointer to the underlying singleton 00075 * 00076 * @returns 00077 * A pointer to the singleton 00078 */ 00079 T* get() { 00080 if (NULL == _ptr) { 00081 singleton_lock(); 00082 if (NULL == _ptr) { 00083 _ptr = new (_data) T(); 00084 } 00085 singleton_unlock(); 00086 } 00087 // _ptr was not zero initialized or was 00088 // corrupted if this assert is hit 00089 MBED_ASSERT(_ptr == (T *)&_data); 00090 return _ptr; 00091 } 00092 00093 /** Get a pointer to the underlying singleton 00094 * 00095 * @returns 00096 * A pointer to the singleton 00097 */ 00098 T* operator->() { 00099 return get(); 00100 } 00101 00102 // This is zero initialized when in global scope 00103 T *_ptr; 00104 // Force data to be 4 byte aligned 00105 uint32_t _data[(sizeof(T) + sizeof(uint32_t) - 1) / sizeof(uint32_t)]; 00106 }; 00107 00108 #endif 00109 00110 /** @}*/
Generated on Wed Jul 13 2022 02:23:48 by 1.7.2