From b4b6e15d734099acd1e6d8a14f0118f9f8aea3b2 Mon Sep 17 00:00:00 2001 From: Alan Jowett Date: Thu, 17 Mar 2022 18:27:47 -0600 Subject: [PATCH] Move common interlocked API's into their own file (#815) Signed-off-by: Alan Jowett --- libs/platform/ebpf_epoch.c | 16 +--- libs/platform/ebpf_interlocked.c | 77 +++++++++++++++++++ libs/platform/ebpf_platform.h | 60 +++++++++++++++ libs/platform/kernel/ebpf_platform_kernel.c | 37 --------- libs/platform/kernel/platform_kernel.vcxproj | 1 + .../kernel/platform_kernel.vcxproj.filters | 3 + libs/platform/user/ebpf_platform_user.cpp | 37 --------- libs/platform/user/platform_user.vcxproj | 1 + .../user/platform_user.vcxproj.filters | 3 + 9 files changed, 149 insertions(+), 86 deletions(-) create mode 100644 libs/platform/ebpf_interlocked.c diff --git a/libs/platform/ebpf_epoch.c b/libs/platform/ebpf_epoch.c index 41f2038d16..7319937636 100644 --- a/libs/platform/ebpf_epoch.c +++ b/libs/platform/ebpf_epoch.c @@ -148,18 +148,10 @@ _ebpf_get_per_cpu_flag(_In_ const ebpf_epoch_cpu_entry_t* cpu_entry, ebpf_epoch_ static void _ebpf_set_per_cpu_flag(_In_ ebpf_epoch_cpu_entry_t* cpu_entry, ebpf_epoch_per_cpu_flags_t flag, bool state) { - for (;;) { - int32_t old_flag_value = cpu_entry->flags; - int32_t new_flag_value = old_flag_value; - if (state) { - new_flag_value |= flag; - } else { - new_flag_value &= flag; - } - if (ebpf_interlocked_compare_exchange_int32(&cpu_entry->flags, new_flag_value, old_flag_value) == - old_flag_value) { - break; - } + if (state) { + ebpf_interlocked_or_int32(&cpu_entry->flags, flag); + } else { + ebpf_interlocked_and_int32(&cpu_entry->flags, ~flag); } } diff --git a/libs/platform/ebpf_interlocked.c b/libs/platform/ebpf_interlocked.c new file mode 100644 index 0000000000..d3397d7dc4 --- /dev/null +++ b/libs/platform/ebpf_interlocked.c @@ -0,0 +1,77 @@ +// Copyright (c) Microsoft Corporation +// SPDX-License-Identifier: MIT + +#include "ebpf_platform.h" + +int32_t +ebpf_interlocked_or_int32(_Inout_ volatile int32_t* target, int32_t mask) +{ + return InterlockedOr((volatile long*)target, mask); +} + +int32_t +ebpf_interlocked_and_int32(_Inout_ volatile int32_t* target, int32_t mask) +{ + return InterlockedAnd((volatile long*)target, mask); +} + +int32_t +ebpf_interlocked_xor_int32(_Inout_ volatile int32_t* target, int32_t mask) +{ + return InterlockedXor((volatile long*)target, mask); +} + +int64_t +ebpf_interlocked_or_int64(_Inout_ volatile int64_t* target, int64_t mask) +{ + return InterlockedOr64(target, mask); +} + +int64_t +ebpf_interlocked_and_int64(_Inout_ volatile int64_t* target, int64_t mask) +{ + return InterlockedAnd64(target, mask); +} + +int64_t +ebpf_interlocked_xor_int64(_Inout_ volatile int64_t* target, int64_t mask) +{ + return InterlockedXor64(target, mask); +} + +int32_t +ebpf_interlocked_increment_int32(_Inout_ volatile int32_t* addend) +{ + return InterlockedIncrement((volatile long*)addend); +} + +int32_t +ebpf_interlocked_decrement_int32(_Inout_ volatile int32_t* addend) +{ + return InterlockedDecrement((volatile long*)addend); +} + +int64_t +ebpf_interlocked_increment_int64(_Inout_ volatile int64_t* addend) +{ + return InterlockedIncrement64(addend); +} + +int64_t +ebpf_interlocked_decrement_int64(_Inout_ volatile int64_t* addend) +{ + return InterlockedDecrement64(addend); +} + +int32_t +ebpf_interlocked_compare_exchange_int32(_Inout_ volatile int32_t* destination, int32_t exchange, int32_t comperand) +{ + return InterlockedCompareExchange((long volatile*)destination, exchange, comperand); +} + +void* +ebpf_interlocked_compare_exchange_pointer( + _Inout_ void* volatile* destination, _In_opt_ const void* exchange, _In_opt_ const void* comperand) +{ + return InterlockedCompareExchangePointer((void* volatile*)destination, (void*)exchange, (void*)comperand); +} diff --git a/libs/platform/ebpf_platform.h b/libs/platform/ebpf_platform.h index abefd5e8db..bf4c267e6a 100644 --- a/libs/platform/ebpf_platform.h +++ b/libs/platform/ebpf_platform.h @@ -667,6 +667,66 @@ extern "C" ebpf_interlocked_compare_exchange_pointer( _Inout_ void* volatile* destination, _In_opt_ const void* exchange, _In_opt_ const void* comperand); + /** + * @brief Performs an atomic OR of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int32_t + ebpf_interlocked_or_int32(_Inout_ volatile int32_t* destination, int32_t mask); + + /** + * @brief Performs an atomic AND of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int32_t + ebpf_interlocked_and_int32(_Inout_ volatile int32_t* destination, int32_t mask); + + /** + * @brief Performs an atomic XOR of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int32_t + ebpf_interlocked_xor_int32(_Inout_ volatile int32_t* destination, int32_t mask); + + /** + * @brief Performs an atomic OR of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int64_t + ebpf_interlocked_or_int64(_Inout_ volatile int64_t* destination, int64_t mask); + + /** + * @brief Performs an atomic AND of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int64_t + ebpf_interlocked_and_int64(_Inout_ volatile int64_t* destination, int64_t mask); + + /** + * @brief Performs an atomic XOR of the value stored at destination with mask and stores the result in destination. + * + * @param[in,out] destination A pointer to the memory for this operation to be applied to. + * @param[in] mask Value to be applied to the value stored at the destination. + * @return The original value stored at destination. + */ + int64_t + ebpf_interlocked_xor_int64(_Inout_ volatile int64_t* destination, int64_t mask); + typedef void (*ebpf_extension_change_callback_t)( _In_ void* client_binding_context, _In_ const void* provider_binding_context, diff --git a/libs/platform/kernel/ebpf_platform_kernel.c b/libs/platform/kernel/ebpf_platform_kernel.c index 4478e6b96a..b7ce52adcf 100644 --- a/libs/platform/kernel/ebpf_platform_kernel.c +++ b/libs/platform/kernel/ebpf_platform_kernel.c @@ -373,43 +373,6 @@ _Requires_lock_held_(*lock) _Releases_lock_(*lock) _IRQL_requires_(DISPATCH_LEVE KeReleaseSpinLock(lock, state); } -int32_t -ebpf_interlocked_increment_int32(_Inout_ volatile int32_t* addend) -{ - return InterlockedIncrement((volatile long*)addend); -} - -int32_t -ebpf_interlocked_decrement_int32(_Inout_ volatile int32_t* addend) -{ - return InterlockedDecrement((volatile long*)addend); -} - -int64_t -ebpf_interlocked_increment_int64(_Inout_ volatile int64_t* addend) -{ - return InterlockedIncrement64(addend); -} - -int64_t -ebpf_interlocked_decrement_int64(_Inout_ volatile int64_t* addend) -{ - return InterlockedDecrement64(addend); -} - -int32_t -ebpf_interlocked_compare_exchange_int32(_Inout_ volatile int32_t* destination, int32_t exchange, int32_t comperand) -{ - return InterlockedCompareExchange((long volatile*)destination, exchange, comperand); -} - -void* -ebpf_interlocked_compare_exchange_pointer( - _Inout_ void* volatile* destination, _In_opt_ const void* exchange, _In_opt_ const void* comperand) -{ - return InterlockedCompareExchangePointer((void* volatile*)destination, (void*)exchange, (void*)comperand); -} - ebpf_result_t ebpf_set_current_thread_affinity(uintptr_t new_thread_affinity_mask, _Out_ uintptr_t* old_thread_affinity_mask) { diff --git a/libs/platform/kernel/platform_kernel.vcxproj b/libs/platform/kernel/platform_kernel.vcxproj index 42ae1c4b4c..621b7b41b8 100644 --- a/libs/platform/kernel/platform_kernel.vcxproj +++ b/libs/platform/kernel/platform_kernel.vcxproj @@ -45,6 +45,7 @@ + diff --git a/libs/platform/kernel/platform_kernel.vcxproj.filters b/libs/platform/kernel/platform_kernel.vcxproj.filters index 126cc92799..e8ef223155 100644 --- a/libs/platform/kernel/platform_kernel.vcxproj.filters +++ b/libs/platform/kernel/platform_kernel.vcxproj.filters @@ -67,6 +67,9 @@ Source Files + + Source Files + diff --git a/libs/platform/user/ebpf_platform_user.cpp b/libs/platform/user/ebpf_platform_user.cpp index fb238dfa45..e11dd6bd7a 100644 --- a/libs/platform/user/ebpf_platform_user.cpp +++ b/libs/platform/user/ebpf_platform_user.cpp @@ -375,43 +375,6 @@ _Requires_lock_held_(*lock) _Releases_lock_(*lock) _IRQL_requires_(DISPATCH_LEVE ReleaseSRWLockExclusive(reinterpret_cast(lock)); } -int32_t -ebpf_interlocked_increment_int32(_Inout_ volatile int32_t* addend) -{ - return InterlockedIncrement((volatile long*)addend); -} - -int32_t -ebpf_interlocked_decrement_int32(_Inout_ volatile int32_t* addend) -{ - return InterlockedDecrement((volatile long*)addend); -} - -int64_t -ebpf_interlocked_increment_int64(_Inout_ volatile int64_t* addend) -{ - return InterlockedIncrement64(addend); -} - -int64_t -ebpf_interlocked_decrement_int64(_Inout_ volatile int64_t* addend) -{ - return InterlockedDecrement64(addend); -} - -int32_t -ebpf_interlocked_compare_exchange_int32(_Inout_ volatile int32_t* destination, int32_t exchange, int32_t comperand) -{ - return InterlockedCompareExchange((long volatile*)destination, exchange, comperand); -} - -void* -ebpf_interlocked_compare_exchange_pointer( - _Inout_ void* volatile* destination, _In_opt_ const void* exchange, _In_opt_ const void* comperand) -{ - return InterlockedCompareExchangePointer((void* volatile*)destination, (void*)exchange, (void*)comperand); -} - uint32_t ebpf_random_uint32() { diff --git a/libs/platform/user/platform_user.vcxproj b/libs/platform/user/platform_user.vcxproj index f6569086be..92946c252b 100644 --- a/libs/platform/user/platform_user.vcxproj +++ b/libs/platform/user/platform_user.vcxproj @@ -29,6 +29,7 @@ + diff --git a/libs/platform/user/platform_user.vcxproj.filters b/libs/platform/user/platform_user.vcxproj.filters index 3633bd80d3..c216c6079a 100644 --- a/libs/platform/user/platform_user.vcxproj.filters +++ b/libs/platform/user/platform_user.vcxproj.filters @@ -70,6 +70,9 @@ Source Files + + Source Files +