LCOV - code coverage report
Current view: top level - asmjit - runtime.cpp (source / functions) Hit Total Coverage
Test: plumed test coverage (other modules) Lines: 28 38 73.7 %
Date: 2024-10-11 08:09:49 Functions: 9 12 75.0 %

          Line data    Source code
       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             : #ifdef __PLUMED_HAS_ASMJIT
      21             : #pragma GCC diagnostic push
      22             : #pragma GCC diagnostic ignored "-Wpedantic"
      23             : // [AsmJit]
      24             : // Complete x86/x64 JIT and Remote Assembler for C++.
      25             : //
      26             : // [License]
      27             : // Zlib - See LICENSE.md file in the package.
      28             : 
      29             : // [Export]
      30             : #define ASMJIT_EXPORTS
      31             : 
      32             : // [Dependencies]
      33             : #include "./assembler.h"
      34             : #include "./cpuinfo.h"
      35             : #include "./runtime.h"
      36             : 
      37             : // [Api-Begin]
      38             : #include "./asmjit_apibegin.h"
      39             : 
      40             : namespace PLMD {
      41             : namespace asmjit {
      42             : 
      43             : static ASMJIT_INLINE void hostFlushInstructionCache(const void* p, size_t size) noexcept {
      44             :   // Only useful on non-x86 architectures.
      45             : #if !ASMJIT_ARCH_X86 && !ASMJIT_ARCH_X64
      46             : # if ASMJIT_OS_WINDOWS
      47             :   // Windows has a built-in support in kernel32.dll.
      48             :   ::FlushInstructionCache(_memMgr.getProcessHandle(), p, size);
      49             : # endif // ASMJIT_OS_WINDOWS
      50             : #else
      51             :   ASMJIT_UNUSED(p);
      52             :   ASMJIT_UNUSED(size);
      53             : #endif // !ASMJIT_ARCH_X86 && !ASMJIT_ARCH_X64
      54             : }
      55             : 
      56             : static ASMJIT_INLINE uint32_t hostDetectNaturalStackAlignment() noexcept {
      57             :   // Alignment is assumed to match the pointer-size by default.
      58             :   uint32_t alignment = sizeof(intptr_t);
      59             : 
      60             :   // X86 & X64
      61             :   // ---------
      62             :   //
      63             :   //   - 32-bit X86 requires stack to be aligned to 4 bytes. Modern Linux, Mac
      64             :   //     and UNIX guarantees 16-byte stack alignment even on 32-bit. I'm not
      65             :   //     sure about all other UNIX operating systems, because 16-byte alignment
      66             :   //!    is addition to an older specification.
      67             :   //   - 64-bit X86 requires stack to be aligned to at least 16 bytes.
      68             : #if ASMJIT_ARCH_X86 || ASMJIT_ARCH_X64
      69             :   int kIsModernOS = ASMJIT_OS_LINUX  || // Linux & ANDROID.
      70             :                     ASMJIT_OS_MAC    || // OSX and iOS.
      71             :                     ASMJIT_OS_BSD    ;  // BSD variants.
      72             :   alignment = ASMJIT_ARCH_X64 || kIsModernOS ? 16 : 4;
      73             : #endif
      74             : 
      75             :   // ARM32 & ARM64
      76             :   // -------------
      77             :   //
      78             :   //   - 32-bit ARM requires stack to be aligned to 8 bytes.
      79             :   //   - 64-bit ARM requires stack to be aligned to 16 bytes.
      80             : #if ASMJIT_ARCH_ARM32 || ASMJIT_ARCH_ARM64
      81             :   alignment = ASMJIT_ARCH_ARM32 ? 8 : 16;
      82             : #endif
      83             : 
      84             :   return alignment;
      85             : }
      86             : 
      87             : 
      88             : // ============================================================================
      89             : // [asmjit::Runtime - Construction / Destruction]
      90             : // ============================================================================
      91             : 
      92        1972 : Runtime::Runtime() noexcept
      93             :   : _codeInfo(),
      94        1972 :     _runtimeType(kRuntimeNone),
      95        1972 :     _allocType(VMemMgr::kAllocFreeable) {}
      96        1972 : Runtime::~Runtime() noexcept {}
      97             : 
      98             : // ============================================================================
      99             : // [asmjit::HostRuntime - Construction / Destruction]
     100             : // ============================================================================
     101             : 
     102        1972 : HostRuntime::HostRuntime() noexcept {
     103        1972 :   _runtimeType = kRuntimeJit;
     104             : 
     105             :   // Setup the CodeInfo of this Runtime.
     106        1972 :   _codeInfo._archInfo       = CpuInfo::getHost().getArchInfo();
     107        1972 :   _codeInfo._stackAlignment = static_cast<uint8_t>(hostDetectNaturalStackAlignment());
     108        1972 :   _codeInfo._cdeclCallConv  = CallConv::kIdHostCDecl;
     109        1972 :   _codeInfo._stdCallConv    = CallConv::kIdHostStdCall;
     110        1972 :   _codeInfo._fastCallConv   = CallConv::kIdHostFastCall;
     111        1972 : }
     112        1972 : HostRuntime::~HostRuntime() noexcept {}
     113             : 
     114             : // ============================================================================
     115             : // [asmjit::HostRuntime - Interface]
     116             : // ============================================================================
     117             : 
     118        1944 : void HostRuntime::flush(const void* p, size_t size) noexcept {
     119             :   hostFlushInstructionCache(p, size);
     120        1944 : }
     121             : 
     122             : // ============================================================================
     123             : // [asmjit::JitRuntime - Construction / Destruction]
     124             : // ============================================================================
     125             : 
     126        1972 : JitRuntime::JitRuntime() noexcept {}
     127        3944 : JitRuntime::~JitRuntime() noexcept {}
     128             : 
     129             : // ============================================================================
     130             : // [asmjit::JitRuntime - Interface]
     131             : // ============================================================================
     132             : 
     133        1944 : Error JitRuntime::_add(void** dst, CodeHolder* code) noexcept {
     134        1944 :   size_t codeSize = code->getCodeSize();
     135        1944 :   if (ASMJIT_UNLIKELY(codeSize == 0)) {
     136           0 :     *dst = nullptr;
     137           0 :     return DebugUtils::errored(kErrorNoCodeGenerated);
     138             :   }
     139             : 
     140        1944 :   void* p = _memMgr.alloc(codeSize, getAllocType());
     141        1944 :   if (ASMJIT_UNLIKELY(!p)) {
     142           0 :     *dst = nullptr;
     143           0 :     return DebugUtils::errored(kErrorNoVirtualMemory);
     144             :   }
     145             : 
     146             :   // Relocate the code and release the unused memory back to `VMemMgr`.
     147        1944 :   size_t relocSize = code->relocate(p);
     148        1944 :   if (ASMJIT_UNLIKELY(relocSize == 0)) {
     149           0 :     *dst = nullptr;
     150           0 :     _memMgr.release(p);
     151           0 :     return DebugUtils::errored(kErrorInvalidState);
     152             :   }
     153             : 
     154        1944 :   if (relocSize < codeSize)
     155           0 :     _memMgr.shrink(p, relocSize);
     156             : 
     157        1944 :   flush(p, relocSize);
     158        1944 :   *dst = p;
     159             : 
     160        1944 :   return kErrorOk;
     161             : }
     162             : 
     163           0 : Error JitRuntime::_release(void* p) noexcept {
     164           0 :   return _memMgr.release(p);
     165             : }
     166             : 
     167             : } // asmjit namespace
     168             : } // namespace PLMD
     169             : 
     170             : // [Api-End]
     171             : #include "./asmjit_apiend.h"
     172             : #pragma GCC diagnostic pop
     173             : #endif // __PLUMED_HAS_ASMJIT

Generated by: LCOV version 1.15