__sxchg -- Exchange Integer Value with Memory

Format

#include <builtin.h>
short _Builtin __sxchg(volatile short*lockptr, short value);

Language Level: Extension
__sxchg puts the specified value in the memory location pointed to by lockptr, and returns the value that was previously in that location.

Use this function to implement fast-RAM semaphores to serialize access to a critical resource (so that only one thread can use it at a time).

You can also use system semaphores to serialize resource access, but they are slower. Typically you would create both a fast-RAM semaphore and a system semaphore for the resource.

To implement a fast-RAM semaphore, allocate a volatile memory location lockptr (for __sxchg, it must be a short), and statically initialize it to 0 to indicate that the resource is free (not being used). To give a thread access to the resource, call __sxchg from the thread to exchange a non-zero value with that memory location. If __sxchg returns 0, the thread can access the resource; it has also set the memory location so that other threads can tell the resource is in use. When your thread no longer needs the resource, call __sxchg again to reset the memory location to 0.

If __sxchg returns a non-zero value, another thread is already using the resource, and the calling thread must wait for access using an OS/2 or Windows semaphore. You could then use the OS/2 or Windows semaphore to inform your waiting thread when the resource is unlocked by the thread currently using it.

It is important that you set the memory to a non-zero value when you are using the resource. You can use the same non-zero value for all threads, or a unique value for each.

Note: __sxchg is a built-in function, which means it is implemented as an inline instruction and has no backing code in the library. For this reason:

Return Value
__sxchg returns the previous value stored in the memory location pointed to by lockptr.

Example
This example shows how __sxchg swaps two values.

#include <builtin.h>
#include <stdio.h>
void myswap (short *x, short *y ) {
   *x = __sxchg (y, *x);
}
int main (void) {
   short x, y;
   x=1;
   y=2;
   printf ("before swap, x=%d, y=%d\n", x, y);
   myswap (&x, &y);
   printf ("after swap, x=%d, y=%d\n", x, y);
   return 0;
   /*******************************************
      The output should be:
      before swap, x=1, y=2
      after swap, x=2, y=1
   *******************************************/
}


__cxchg -- Exchange Character Value with Memory
__lxchg -- Exchange Integer Value with Memory
<builtin.h>