thread/primitive: add platform wrappers for pause/yield instructions

This commit is contained in:
Danny Robson 2019-02-02 14:55:13 +11:00
parent 8c934fbd2c
commit 1f6caaa242
5 changed files with 40 additions and 13 deletions

View File

@ -157,8 +157,9 @@ endif ()
###############################################################################
list (APPEND UTIL_FILES
thread/event.hpp
thread/semaphore.hpp
thread/flag.hpp
thread/primitive.hpp
thread/semaphore.hpp
)
if (LINUX)

View File

@ -3,13 +3,13 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* Copyright 2018 Danny Robson <danny@nerdcruft.net>
* Copyright 2018-2019 Danny Robson <danny@nerdcruft.net>
*/
#ifndef CRUFT_UTIL_PARALLEL_QUEUE_HPP
#define CRUFT_UTIL_PARALLEL_QUEUE_HPP
#pragma once
#include "../maths.hpp"
#include "../thread/primitive.hpp"
#include <atomic>
#include <type_traits>
@ -78,7 +78,7 @@ namespace cruft::parallel {
// try to bump the write cursor to claim that slot
if (uint32_t orig = curr; !m_write.compare_exchange_weak (orig, next)) {
asm volatile ("pause;");
pause ();
continue;
}
@ -92,7 +92,7 @@ namespace cruft::parallel {
uint32_t orig = curr;
if (m_read.hi.compare_exchange_weak (orig, next))
break;
asm volatile ("pause;");
pause ();
} while (1);
return true;
@ -132,7 +132,7 @@ namespace cruft::parallel {
if (uint32_t orig = curr; m_read.lo.compare_exchange_weak (orig, next))
return true;
asm volatile ("pause;");
pause ();
} while (1);
}
@ -156,5 +156,3 @@ namespace cruft::parallel {
} m_read;
};
}
#endif

25
thread/primitive.hpp Normal file
View File

@ -0,0 +1,25 @@
/*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* Copyright 2019 Danny Robson <danny@nerdcruft.net>
*/
#pragma once
#include "../platform.hpp"
namespace cruft {
inline void pause [[gnu::always_inline]] (void)
{
#ifdef PROCESSOR_AMD64
asm volatile ("pause");
#elif PROCESSOR_ARM
asm volatile ("yield");
#else
#error "Unhandled processor type"
#endif
}
}

View File

@ -3,11 +3,13 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* Copyright 2018 Danny Robson <danny@nerdcruft.net>
* Copyright 2018-2019 Danny Robson <danny@nerdcruft.net>
*/
#include "spinlock.hpp"
#include "primitive.hpp"
#include "../debug.hpp"
using cruft::thread::spinlock;
@ -35,7 +37,7 @@ spinlock::lock (void)
return;
while (held)
__asm__ volatile ("pause");
pause ();
} while (true);
}

View File

@ -3,10 +3,11 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* Copyright 2018 Danny Robson <danny@nerdcruft.net>
* Copyright 2018-2019 Danny Robson <danny@nerdcruft.net>
*/
#include "ticketlock.hpp"
#include "primitive.hpp"
using cruft::thread::ticketlock;
@ -25,7 +26,7 @@ ticketlock::lock (void)
auto self = next++;
while (current != self)
__asm__ volatile ("pause");
pause ();
}