1 /* +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 Copyright (c) 2008-2017, Petr Kobalicek 3 4 This software is provided 'as-is', without any express or implied 5 warranty. In no event will the authors be held liable for any damages 6 arising from the use of this software. 7 8 Permission is granted to anyone to use this software for any purpose, 9 including commercial applications, and to alter it and redistribute it 10 freely, subject to the following restrictions: 11 12 1. The origin of this software must not be misrepresented; you must not 13 claim that you wrote the original software. If you use this software 14 in a product, an acknowledgment in the product documentation would be 15 appreciated but is not required. 16 2. Altered source versions must be plainly marked as such, and must not be 17 misrepresented as being the original software. 18 3. This notice may not be removed or altered from any source distribution. 19 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */ 20 #ifndef __PLUMED_asmjit_osutils_h 21 #define __PLUMED_asmjit_osutils_h 22 #ifdef __PLUMED_HAS_ASMJIT 23 #pragma GCC diagnostic push 24 #pragma GCC diagnostic ignored "-Wpedantic" 25 // [AsmJit] 26 // Complete x86/x64 JIT and Remote Assembler for C++. 27 // 28 // [License] 29 // Zlib - See LICENSE.md file in the package. 30 31 // [Guard] 32 #ifndef _ASMJIT_BASE_OSUTILS_H 33 #define _ASMJIT_BASE_OSUTILS_H 34 35 // [Dependencies] 36 #include "./globals.h" 37 38 // [Api-Begin] 39 #include "./asmjit_apibegin.h" 40 41 namespace PLMD { 42 namespace asmjit { 43 44 //! \addtogroup asmjit_base 45 //! \{ 46 47 // ============================================================================ 48 // [asmjit::VMemInfo] 49 // ============================================================================ 50 51 //! Information about OS virtual memory. 52 struct VMemInfo { 53 #if ASMJIT_OS_WINDOWS 54 HANDLE hCurrentProcess; //!< Handle of the current process (Windows). 55 #endif // ASMJIT_OS_WINDOWS 56 size_t pageSize; //!< Virtual memory page size. 57 size_t pageGranularity; //!< Virtual memory page granularity. 58 }; 59 60 // ============================================================================ 61 // [asmjit::OSUtils] 62 // ============================================================================ 63 64 //! OS utilities. 65 //! 66 //! Virtual Memory 67 //! -------------- 68 //! 69 //! Provides functions to allocate and release virtual memory that is required 70 //! to execute dynamically generated code. If both processor and host OS support 71 //! data-execution-prevention (DEP) then the only way to run machine code is to 72 //! allocate virtual memory that has `OSUtils::kVMExecutable` flag enabled. All 73 //! functions provides by OSUtils use internally platform specific API. 74 //! 75 //! Benchmarking 76 //! ------------ 77 //! 78 //! OSUtils also provide a function `getTickCount()` that can be used for 79 //! benchmarking purposes. It's similar to Windows-only `GetTickCount()`, but 80 //! it's cross-platform and tries to be the most reliable platform specific 81 //! calls to make the result usable. 82 struct OSUtils { 83 // -------------------------------------------------------------------------- 84 // [Virtual Memory] 85 // -------------------------------------------------------------------------- 86 87 //! Virtual memory flags. ASMJIT_ENUMOSUtils88 ASMJIT_ENUM(VMFlags) { 89 kVMWritable = 0x00000001U, //!< Virtual memory is writable. 90 kVMExecutable = 0x00000002U //!< Virtual memory is executable. 91 }; 92 93 ASMJIT_API static VMemInfo getVirtualMemoryInfo() noexcept; 94 95 //! Allocate virtual memory. 96 ASMJIT_API static void* allocVirtualMemory(size_t size, size_t* allocated, uint32_t flags) noexcept; 97 //! Release virtual memory previously allocated by \ref allocVirtualMemory(). 98 ASMJIT_API static Error releaseVirtualMemory(void* p, size_t size) noexcept; 99 100 #if ASMJIT_OS_WINDOWS 101 //! Allocate virtual memory of `hProcess` (Windows). 102 ASMJIT_API static void* allocProcessMemory(HANDLE hProcess, size_t size, size_t* allocated, uint32_t flags) noexcept; 103 104 //! Release virtual memory of `hProcess` (Windows). 105 ASMJIT_API static Error releaseProcessMemory(HANDLE hProcess, void* p, size_t size) noexcept; 106 #endif // ASMJIT_OS_WINDOWS 107 108 // -------------------------------------------------------------------------- 109 // [GetTickCount] 110 // -------------------------------------------------------------------------- 111 112 //! Get the current CPU tick count, used for benchmarking (1ms resolution). 113 ASMJIT_API static uint32_t getTickCount() noexcept; 114 }; 115 116 // ============================================================================ 117 // [asmjit::Lock] 118 // ============================================================================ 119 120 //! \internal 121 //! 122 //! Lock. 123 struct Lock { 124 ASMJIT_NONCOPYABLE(Lock) 125 126 // -------------------------------------------------------------------------- 127 // [Windows] 128 // -------------------------------------------------------------------------- 129 130 #if ASMJIT_OS_WINDOWS 131 typedef CRITICAL_SECTION Handle; 132 133 //! Create a new `Lock` instance. LockLock134 ASMJIT_INLINE Lock() noexcept { InitializeCriticalSection(&_handle); } 135 //! Destroy the `Lock` instance. ~LockLock136 ASMJIT_INLINE ~Lock() noexcept { DeleteCriticalSection(&_handle); } 137 138 //! Lock. lockLock139 ASMJIT_INLINE void lock() noexcept { EnterCriticalSection(&_handle); } 140 //! Unlock. unlockLock141 ASMJIT_INLINE void unlock() noexcept { LeaveCriticalSection(&_handle); } 142 #endif // ASMJIT_OS_WINDOWS 143 144 // -------------------------------------------------------------------------- 145 // [Posix] 146 // -------------------------------------------------------------------------- 147 148 #if ASMJIT_OS_POSIX 149 typedef pthread_mutex_t Handle; 150 151 //! Create a new `Lock` instance. LockLock152 ASMJIT_INLINE Lock() noexcept { pthread_mutex_init(&_handle, nullptr); } 153 //! Destroy the `Lock` instance. ~LockLock154 ASMJIT_INLINE ~Lock() noexcept { pthread_mutex_destroy(&_handle); } 155 156 //! Lock. lockLock157 ASMJIT_INLINE void lock() noexcept { pthread_mutex_lock(&_handle); } 158 //! Unlock. unlockLock159 ASMJIT_INLINE void unlock() noexcept { pthread_mutex_unlock(&_handle); } 160 #endif // ASMJIT_OS_POSIX 161 162 // -------------------------------------------------------------------------- 163 // [Members] 164 // -------------------------------------------------------------------------- 165 166 //! Native handle. 167 Handle _handle; 168 }; 169 170 // ============================================================================ 171 // [asmjit::AutoLock] 172 // ============================================================================ 173 174 //! \internal 175 //! 176 //! Scoped lock. 177 struct AutoLock { ASMJIT_NONCOPYABLEAutoLock178 ASMJIT_NONCOPYABLE(AutoLock) 179 180 // -------------------------------------------------------------------------- 181 // [Construction / Destruction] 182 // -------------------------------------------------------------------------- 183 184 ASMJIT_INLINE AutoLock(Lock& target) noexcept : _target(target) { _target.lock(); } ~AutoLockAutoLock185 ASMJIT_INLINE ~AutoLock() noexcept { _target.unlock(); } 186 187 // -------------------------------------------------------------------------- 188 // [Members] 189 // -------------------------------------------------------------------------- 190 191 //! Reference to the `Lock`. 192 Lock& _target; 193 }; 194 195 //! \} 196 197 } // asmjit namespace 198 } // namespace PLMD 199 200 // [Api-End] 201 #include "./asmjit_apiend.h" 202 203 // [Guard] 204 #endif // _ASMJIT_BASE_OSUTILS_H 205 #pragma GCC diagnostic pop 206 #endif // __PLUMED_HAS_ASMJIT 207 #endif 208