/* * Copyright 2010 Stefan Lankes, Chair for Operating Systems, * RWTH Aachen University * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * * This file is part of MetalSVM. */ #ifndef __ARCH_ATOMIC_H__ #define __ARCH_ATOMIC_H__ #include #ifdef __cplusplus extern "C" { #endif typedef uint32_t atomic_uint32_t; /* * Intel manuals: If a memory operand is referenced, the processor's locking * protocol is automatically implemented for the duration of the exchange * operation, regardless of the presence or absence of the LOCK prefix. */ inline static atomic_uint32_t atomic_uint32_test_and_set(atomic_uint32_t* d) { atomic_uint32_t ret = 1; asm volatile ("xchgl %0, %1" : "=r"(ret) : "m"(*d), "0"(ret) : "memory"); return ret; } inline static void atomic_uint32_inc(atomic_uint32_t* d) { asm volatile ("lock addl 1, %0" : "+m"(*d)); } inline static void atomic_uint32_dec(atomic_uint32_t* d) { asm volatile ("lock subl 1, %0" : "+m"(*d)); } inline static void atomic_uint32_add(atomic_uint32_t *d, int32_t i) { asm volatile("lock addl %1, %0" : "+m" (*d) : "ir" (i)); } inline static void atomic_uint32_sub(atomic_uint32_t *d, int32_t i) { asm volatile("lock subl %1, %0" : "+m" (*d) : "ir" (i)); } inline static atomic_uint32_t atomic_uint32_read(atomic_uint32_t *d) { return *d; } inline static void atomic_uint32_set(atomic_uint32_t *d, uint32_t v) { *d = v; } #define atomic_size_t atomic_uint32_t #define atomic_size_read atomic_uint32_read #define atomic_size_set atomic_uint32_set #define atomic_size_inc atomic_uint32_inc #define atomic_size_dec atomic_uint32_dec #define atomic_size_add atomic_uint32_add #define atomic_size_sub atomic_uint32_sub #ifdef __cplusplus } #endif #endif