ulong test_and_set_lock (ulong *memory, ulong increment) 
{
  /* Test and Set Lock */
  ulong result = 0;

  for (ulong cntr = 0; cntr < SEM32_MAX_LOCK_ATTEMPTS; cntr ++)
  {
    /* Read the current value */
    ulong current_value = LDREX (memory);
 
    /* Try to write new value */
    ulong new_value = current_value + increment;
    ulong rc = STREX (current_value, new_value, memory);

    /* When locked: */
    if (rc == 0) 
    {
      /* Flush L1 cache */
      DMB ();
            
      /* Written, return success */
      result = 1; break;
    }
  }
 
  return result;
}