Files
DocumentServer-v-9.2.0/core/DjVuFile/libdjvu/atomic.h
Yajbir Singh f1b860b25c
Some checks failed
check / markdownlint (push) Has been cancelled
check / spellchecker (push) Has been cancelled
updated
2025-12-11 19:03:17 +05:30

106 lines
3.6 KiB
C

/* -*- C -*-
// -------------------------------------------------------------------
// MiniLock - a quick user space lock
// Copyright (c) 2008 Leon Bottou. All rights reserved
//
// Permission is hereby granted, free of charge, to any person obtaining
// a copy of this software and associated documentation files (the
// "Software"), to deal in the Software without restriction, including
// without limitation the rights to use, copy, modify, merge, publish,
// distribute, sublicense, and/or sell copies of the Software, and to
// permit persons to whom the Software is furnished to do so, subject to
// the following conditions:
//
// The above copyright notice and this permission notice shall be
// included in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
//
// ------------------------------------------------------------------- */
#ifndef ATOMIC_H
#define ATOMIC_H
/* ------------------------------------------------------------
// These are primitives to implement very quick locks.
//
// Non-blocking usage:
// if (atomicAcquire(&lock)) {
// ... // do something protected by the lock
// atomicRelease(&lock);
// }
//
// Blocking usage:
// atomicAcquireOrSpin(&lock);
// // do something protected by the lock
// atomicRelease(&lock);
//
// Rules of thumb:
// - Acquire and release from the same function with
// no intervening function calls.
// - Do not use AcquireOrSpin for waiting a long time.
// No more than a few microseconds please.
//
// Memory ordering:
// Viewed from another processor
// - load/stores performed by this cpu after the acquire
// cannot appear to have happened before the acquire.
// - load/stores performed by this cpu before the release
// cannot appear to have happened after the release.
//
// Implementation:
// All depends on the definitions from the initial include file.
// To perform the non blocking operations:
// - use intel builtins if available (icc, gcc>=4.1).
// - use win32 interlocked operations (win32).
// - use inline assembly code for some platforms.
// - use pthreads
// To perform the waiting when spinning takes to long:
// - use win32 critical sections and events.
// - use pthreads mutex and conditions.
// This is controlled by the preprocessor symbols:
// WIN32
// __GNUC__ __GNUC_MAJOR__ __GNUC_MINOR__
// __INTEL_COMPILER
// and can be overriden by defining
// HAVE_INTEL_ATOMIC_BUILTINS
// OBEY_HAVE_INTEL_ATOMIC_BUILTINS
// and by tweaking the files include in atomic.h.
// ------------------------------------------------------------ */
# ifdef __cplusplus
extern "C" {
#endif
/* { int tmp = *lock; *lock = 1; return !tmp; }. */
int atomicAcquire(int volatile *lock);
/* { while (!atomicAcquire(lock)) { spin/yield/wait } } */
void atomicAcquireOrSpin(int volatile *lock);
/* { *lock = 0; } */
void atomicRelease(int volatile *lock);
/* { *var += 1; return *var; } */
int atomicIncrement(int volatile *var);
/* { *var -= 1; return *var; } */
int atomicDecrement(int volatile *var);
/* { if (*var == oldval) { *var = newval; return TRUE; } return FALSE; } */
int atomicCompareAndSwap(int volatile *var, int oldval, int newval);
# ifdef __cplusplus
}
#endif
#endif