SeqAn3 3.1.0
The Modern C++ library for sequence analysis.
spin_delay.hpp
Go to the documentation of this file.
1// -----------------------------------------------------------------------------------------------------
2// Copyright (c) 2006-2021, Knut Reinert & Freie Universität Berlin
3// Copyright (c) 2016-2021, Knut Reinert & MPI für molekulare Genetik
4// This file may be used, modified and/or redistributed under the terms of the 3-clause BSD-License
5// shipped with this file and also available at: https://github.com/seqan/seqan3/blob/master/LICENSE.md
6// -----------------------------------------------------------------------------------------------------
7
13#pragma once
14
15#include <thread>
16
17#if defined(__SSE2__) // AMD and Intel
18#include <xmmintrin.h> // _mm_pause()
19#endif
20
22
23namespace seqan3::detail
24{
36class spin_delay
37{
38public:
42 constexpr spin_delay() noexcept = default;
43 constexpr spin_delay(spin_delay const &) noexcept = default;
44 constexpr spin_delay(spin_delay &&) noexcept = default;
45 constexpr spin_delay & operator=(spin_delay const &) noexcept = default;
46 constexpr spin_delay & operator=(spin_delay &&) noexcept = default;
47 ~spin_delay() noexcept = default;
48
50
58 void wait()
59 {
60 if (current <= max_repetitions) // Start active spinning phase
61 {
62 for (int_fast32_t i = 0; i < current; ++i)
63 pause_processor();
64 current <<= 1; // double the amount of active CPU waiting cycles.
65 }
66 else // Start passive spinning phase
67 {
69 }
70 }
71
72private:
73
75 void pause_processor()
76 {
77 #if defined(__SSE2__) // AMD and Intel
78 _mm_pause();
79 #elif defined(__armel__) || defined(__ARMEL__) // arm, but broken? ; repeat of default case as armel also defines __arm__
80 asm volatile ("nop" ::: "memory"); // default operation - does nothing => Might lead to passive spinning.
81 #elif defined(__arm__) || defined(__aarch64__) // arm big endian / arm64
82 __asm__ __volatile__ ("yield" ::: "memory");
83 #elif defined(__ia64__) // IA64
84 __asm__ __volatile__ ("hint @pause");
85 #elif defined(__powerpc__) || defined(__ppc__) || defined(__PPC__) // PowerPC
86 __asm__ __volatile__ ("or 27,27,27" ::: "memory");
87 #else // everything else.
88 asm volatile ("nop" ::: "memory"); // default operation - does nothing => Might lead to passive spinning.
89 #endif
90 }
91
93 static constexpr int_fast32_t max_repetitions{16};
95 int_fast32_t current{1};
96};
97
98} // namespace seqan3::detail
Provides platform and dependency checks.
T yield(T... args)