mono_lock_free_queue_init (struct MonoLockFreeQueue * q)
{
  struct MonoLockFreeQueueNode * volatile iftmp.0;
  _Bool D.7423;
  int D.7424;
  struct MonoLockFreeQueueNode * D.7425;
  struct MonoLockFreeQueueNode * D.7426;
  int i;

  i = 0;
  goto <D.7366>;
  <D.7365>:
  if (i == 0) goto <D.7420>; else goto <D.7421>;
  <D.7420>:
  iftmp.0 = 4294967294B;
  goto <D.7422>;
  <D.7421>:
  iftmp.0 = 4294967293B;
  <D.7422>:
  q->dummies[i].node.next = iftmp.0;
  D.7423 = i == 0;
  D.7424 = (int) D.7423;
  q->dummies[i].in_use = D.7424;
  i = i + 1;
  <D.7366>:
  if (i <= 1) goto <D.7365>; else goto <D.7367>;
  <D.7367>:
  D.7425 = &q->dummies[0].node;
  D.7426 = D.7425;
  q->tail = D.7426;
  q->head = D.7426;
  q->has_dummy = 1;
}


mono_lock_free_queue_node_init (struct MonoLockFreeQueueNode * node, gboolean to_be_freed)
{
  struct MonoLockFreeQueueNode * volatile iftmp.1;

  if (to_be_freed != 0) goto <D.7428>; else goto <D.7429>;
  <D.7428>:
  iftmp.1 = 4294967295B;
  goto <D.7430>;
  <D.7429>:
  iftmp.1 = 4294967293B;
  <D.7430>:
  node->next = iftmp.1;
}


mono_lock_free_queue_node_free (struct MonoLockFreeQueueNode * node)
{
  struct MonoLockFreeQueueNode * D.7431;
  _Bool D.7432;
  long int D.7433;
  long int D.7434;

  D.7431 = node->next;
  D.7432 = D.7431 != 4294967295B;
  D.7433 = (long int) D.7432;
  D.7434 = __builtin_expect (D.7433, 0);
  if (D.7434 != 0) goto <D.7435>; else goto <D.7436>;
  <D.7435>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 92, "node->next == INVALID_NEXT");
  <D.7436>:
  node->next = 4294967293B;
}


mono_lock_free_queue_enqueue (struct MonoLockFreeQueue * q, struct MonoLockFreeQueueNode * node)
{
  struct MonoLockFreeQueueNode * D.7437;
  _Bool D.7438;
  long int D.7439;
  long int D.7440;
  struct MonoLockFreeQueueNode * volatile * D.7443;
  struct MonoLockFreeQueueNode * D.7444;
  _Bool D.7447;
  _Bool D.7448;
  _Bool D.7449;
  int D.7450;
  _Bool D.7451;
  long int D.7452;
  long int D.7453;
  _Bool D.7456;
  long int D.7457;
  long int D.7458;
  struct MonoLockFreeQueueNode * volatile * D.7463;
  void * D.7464;
  struct MonoLockFreeQueueNode * volatile * D.7467;
  struct MonoLockFreeQueueNode * volatile * D.7470;
  struct MonoThreadHazardPointers * hp;
  struct MonoLockFreeQueueNode * tail;

  hp = mono_hazard_pointer_get ();
  D.7437 = node->next;
  D.7438 = D.7437 != 4294967293B;
  D.7439 = (long int) D.7438;
  D.7440 = __builtin_expect (D.7439, 0);
  if (D.7440 != 0) goto <D.7441>; else goto <D.7442>;
  <D.7441>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 111, "node->next == FREE_NEXT");
  <D.7442>:
  node->next = 4294967294B;
  <D.7383>:
  {
    struct MonoLockFreeQueueNode * next;

    D.7443 = &q->tail;
    tail = get_hazardous_pointer (D.7443, hp, 0);
    mono_memory_read_barrier ();
    next = tail->next;
    mono_memory_read_barrier ();
    D.7444 = q->tail;
    if (D.7444 == tail) goto <D.7445>; else goto <D.7446>;
    <D.7445>:
    D.7447 = next == 4294967295B;
    D.7448 = next == 4294967293B;
    D.7449 = D.7447 | D.7448;
    D.7450 = (int) D.7449;
    D.7451 = D.7450 != 0;
    D.7452 = (long int) D.7451;
    D.7453 = __builtin_expect (D.7452, 0);
    if (D.7453 != 0) goto <D.7454>; else goto <D.7455>;
    <D.7454>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 127, "next != INVALID_NEXT && next != FREE_NEXT");
    <D.7455>:
    D.7456 = next == tail;
    D.7457 = (long int) D.7456;
    D.7458 = __builtin_expect (D.7457, 0);
    if (D.7458 != 0) goto <D.7459>; else goto <D.7460>;
    <D.7459>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 128, "next != tail");
    <D.7460>:
    if (next == 4294967294B) goto <D.7461>; else goto <D.7462>;
    <D.7461>:
    D.7463 = &tail->next;
    D.7464 = InterlockedCompareExchangePointer (D.7463, node, 4294967294B);
    if (D.7464 == 4294967294B) goto <D.7382>; else goto <D.7465>;
    <D.7465>:
    goto <D.7466>;
    <D.7462>:
    D.7467 = &q->tail;
    InterlockedCompareExchangePointer (D.7467, next, tail);
    <D.7466>:
    <D.7446>:
    mono_memory_write_barrier ();
    if (0 != 0) goto <D.7468>; else goto <D.7469>;
    <D.7468>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 147, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
    <D.7469>:
    hp->hazard_pointers[0] = 0B;
  }
  goto <D.7383>;
  <D.7382>:
  D.7470 = &q->tail;
  InterlockedCompareExchangePointer (D.7470, node, tail);
  mono_memory_write_barrier ();
  if (0 != 0) goto <D.7471>; else goto <D.7472>;
  <D.7471>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 154, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
  <D.7472>:
  hp->hazard_pointers[0] = 0B;
}


mono_memory_read_barrier ()
{
  mono_memory_barrier ();
}


mono_memory_barrier ()
{
  __sync_synchronize ();
}


InterlockedCompareExchangePointer (void * volatile * dest, void * exch, void * comp)
{
  void * D.7473;
  unsigned int comp.2;
  unsigned int exch.3;
  unsigned int D.7476;

  comp.2 = (unsigned int) comp;
  exch.3 = (unsigned int) exch;
  D.7476 = __sync_val_compare_and_swap_4 (dest, comp.2, exch.3);
  D.7473 = (void *) D.7476;
  return D.7473;
}


mono_memory_write_barrier ()
{
  mono_memory_barrier ();
}


mono_lock_free_queue_dequeue (struct MonoLockFreeQueue * q)
{
  struct MonoLockFreeQueueNode * volatile * D.7478;
  struct MonoLockFreeQueueNode * D.7479;
  _Bool D.7482;
  _Bool D.7483;
  _Bool D.7484;
  int D.7485;
  _Bool D.7486;
  long int D.7487;
  long int D.7488;
  _Bool D.7491;
  long int D.7492;
  long int D.7493;
  int D.7502;
  int D.7505;
  struct MonoLockFreeQueueNode * D.7508;
  struct MonoLockFreeQueueNode * volatile * D.7509;
  _Bool D.7511;
  long int D.7512;
  long int D.7513;
  struct MonoLockFreeQueueNode * volatile * D.7516;
  void * D.7517;
  struct MonoLockFreeQueueNode * D.7523;
  _Bool D.7524;
  long int D.7525;
  long int D.7526;
  int D.7529;
  int D.7532;
  _Bool D.7533;
  long int D.7534;
  long int D.7535;
  int D.7538;
  struct MonoThreadHazardPointers * hp;
  struct MonoLockFreeQueueNode * head;
  void retry = <<< error >>>;

  hp = mono_hazard_pointer_get ();
  retry:
  <D.7415>:
  {
    struct MonoLockFreeQueueNode * tail;
    struct MonoLockFreeQueueNode * next;

    D.7478 = &q->head;
    head = get_hazardous_pointer (D.7478, hp, 0);
    tail = q->tail;
    mono_memory_read_barrier ();
    next = head->next;
    mono_memory_read_barrier ();
    D.7479 = q->head;
    if (D.7479 == head) goto <D.7480>; else goto <D.7481>;
    <D.7480>:
    D.7482 = next == 4294967295B;
    D.7483 = next == 4294967293B;
    D.7484 = D.7482 | D.7483;
    D.7485 = (int) D.7484;
    D.7486 = D.7485 != 0;
    D.7487 = (long int) D.7486;
    D.7488 = __builtin_expect (D.7487, 0);
    if (D.7488 != 0) goto <D.7489>; else goto <D.7490>;
    <D.7489>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 229, "next != INVALID_NEXT && next != FREE_NEXT");
    <D.7490>:
    D.7491 = next == head;
    D.7492 = (long int) D.7491;
    D.7493 = __builtin_expect (D.7492, 0);
    if (D.7493 != 0) goto <D.7494>; else goto <D.7495>;
    <D.7494>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 230, "next != head");
    <D.7495>:
    if (head == tail) goto <D.7496>; else goto <D.7497>;
    <D.7496>:
    if (next == 4294967294B) goto <D.7498>; else goto <D.7499>;
    <D.7498>:
    if (0 != 0) goto <D.7500>; else goto <D.7501>;
    <D.7500>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 236, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
    <D.7501>:
    hp->hazard_pointers[0] = 0B;
    D.7502 = is_dummy (q, head);
    if (D.7502 == 0) goto <D.7503>; else goto <D.7504>;
    <D.7503>:
    D.7505 = try_reenqueue_dummy (q);
    if (D.7505 != 0) goto <D.7506>; else goto <D.7507>;
    <D.7506>:
    // predicted unlikely by continue predictor.
    goto <D.7413>;
    <D.7507>:
    <D.7504>:
    D.7508 = 0B;
    return D.7508;
    <D.7499>:
    D.7509 = &q->tail;
    InterlockedCompareExchangePointer (D.7509, next, tail);
    goto <D.7510>;
    <D.7497>:
    D.7511 = next == 4294967294B;
    D.7512 = (long int) D.7511;
    D.7513 = __builtin_expect (D.7512, 0);
    if (D.7513 != 0) goto <D.7514>; else goto <D.7515>;
    <D.7514>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 254, "next != END_MARKER");
    <D.7515>:
    D.7516 = &q->head;
    D.7517 = InterlockedCompareExchangePointer (D.7516, next, head);
    if (D.7517 == head) goto <D.7414>; else goto <D.7518>;
    <D.7518>:
    <D.7510>:
    <D.7481>:
    mono_memory_write_barrier ();
    if (0 != 0) goto <D.7519>; else goto <D.7520>;
    <D.7519>:
    monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 262, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
    <D.7520>:
    hp->hazard_pointers[0] = 0B;
  }
  <D.7413>:
  goto <D.7415>;
  <D.7414>:
  mono_memory_write_barrier ();
  if (0 != 0) goto <D.7521>; else goto <D.7522>;
  <D.7521>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 270, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
  <D.7522>:
  hp->hazard_pointers[0] = 0B;
  D.7523 = head->next;
  D.7524 = D.7523 == 0B;
  D.7525 = (long int) D.7524;
  D.7526 = __builtin_expect (D.7525, 0);
  if (D.7526 != 0) goto <D.7527>; else goto <D.7528>;
  <D.7527>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 272, "head->next");
  <D.7528>:
  head->next = 4294967295B;
  D.7529 = is_dummy (q, head);
  if (D.7529 != 0) goto <D.7530>; else goto <D.7531>;
  <D.7530>:
  D.7532 = q->has_dummy;
  D.7533 = D.7532 == 0;
  D.7534 = (long int) D.7533;
  D.7535 = __builtin_expect (D.7534, 0);
  if (D.7535 != 0) goto <D.7536>; else goto <D.7537>;
  <D.7536>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 286, "q->has_dummy");
  <D.7537>:
  q->has_dummy = 0;
  mono_memory_write_barrier ();
  mono_thread_hazardous_free_or_queue (head, free_dummy, 0, 1);
  D.7538 = try_reenqueue_dummy (q);
  if (D.7538 != 0) goto retry; else goto <D.7539>;
  <D.7539>:
  D.7508 = 0B;
  return D.7508;
  <D.7531>:
  D.7508 = head;
  return D.7508;
}


free_dummy (void * _dummy)
{
  struct MonoLockFreeQueueNode * D.7541;
  int D.7542;
  _Bool D.7543;
  long int D.7544;
  long int D.7545;
  struct MonoLockFreeQueueDummy * dummy;

  dummy = _dummy;
  D.7541 = &dummy->node;
  mono_lock_free_queue_node_free (D.7541);
  D.7542 = dummy->in_use;
  D.7543 = D.7542 == 0;
  D.7544 = (long int) D.7543;
  D.7545 = __builtin_expect (D.7544, 0);
  if (D.7545 != 0) goto <D.7546>; else goto <D.7547>;
  <D.7546>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "lock-free-queue.c", 162, "dummy->in_use");
  <D.7547>:
  mono_memory_write_barrier ();
  dummy->in_use = 0;
}


is_dummy (struct MonoLockFreeQueue * q, struct MonoLockFreeQueueNode * n)
{
  gboolean D.7548;
  int iftmp.4;
  struct MonoLockFreeQueueNode * D.7552;
  struct MonoLockFreeQueueNode * D.7554;

  D.7552 = &q->dummies[0].node;
  if (D.7552 <= n) goto <D.7553>; else goto <D.7550>;
  <D.7553>:
  D.7554 = &q->dummies[2].node;
  if (D.7554 > n) goto <D.7555>; else goto <D.7550>;
  <D.7555>:
  iftmp.4 = 1;
  goto <D.7551>;
  <D.7550>:
  iftmp.4 = 0;
  <D.7551>:
  D.7548 = iftmp.4;
  return D.7548;
}


try_reenqueue_dummy (struct MonoLockFreeQueue * q)
{
  int D.7557;
  gboolean D.7560;
  volatile gint32 * D.7563;
  int D.7564;
  struct MonoLockFreeQueueNode * D.7567;
  struct MonoLockFreeQueueDummy * dummy;

  D.7557 = q->has_dummy;
  if (D.7557 != 0) goto <D.7558>; else goto <D.7559>;
  <D.7558>:
  D.7560 = 0;
  return D.7560;
  <D.7559>:
  dummy = get_dummy (q);
  if (dummy == 0B) goto <D.7561>; else goto <D.7562>;
  <D.7561>:
  D.7560 = 0;
  return D.7560;
  <D.7562>:
  D.7563 = &q->has_dummy;
  D.7564 = InterlockedCompareExchange (D.7563, 1, 0);
  if (D.7564 != 0) goto <D.7565>; else goto <D.7566>;
  <D.7565>:
  dummy->in_use = 0;
  D.7560 = 0;
  return D.7560;
  <D.7566>:
  D.7567 = &dummy->node;
  mono_lock_free_queue_enqueue (q, D.7567);
  D.7560 = 1;
  return D.7560;
}


get_dummy (struct MonoLockFreeQueue * q)
{
  int D.7569;
  volatile gint32 * D.7572;
  int D.7573;
  struct MonoLockFreeQueueDummy * D.7576;
  int i;

  i = 0;
  goto <D.7395>;
  <D.7394>:
  {
    struct MonoLockFreeQueueDummy * dummy;

    dummy = &q->dummies[i];
    D.7569 = dummy->in_use;
    if (D.7569 != 0) goto <D.7570>; else goto <D.7571>;
    <D.7570>:
    // predicted unlikely by continue predictor.
    goto <D.7393>;
    <D.7571>:
    D.7572 = &dummy->in_use;
    D.7573 = InterlockedCompareExchange (D.7572, 1, 0);
    if (D.7573 == 0) goto <D.7574>; else goto <D.7575>;
    <D.7574>:
    D.7576 = dummy;
    return D.7576;
    <D.7575>:
  }
  <D.7393>:
  i = i + 1;
  <D.7395>:
  if (i <= 1) goto <D.7394>; else goto <D.7396>;
  <D.7396>:
  D.7576 = 0B;
  return D.7576;
}


InterlockedCompareExchange (volatile gint32 * dest, gint32 exch, gint32 comp)
{
  gint32 D.7578;
  unsigned int comp.5;
  unsigned int exch.6;
  unsigned int D.7581;

  comp.5 = (unsigned int) comp;
  exch.6 = (unsigned int) exch;
  D.7581 = __sync_val_compare_and_swap_4 (dest, comp.5, exch.6);
  D.7578 = (gint32) D.7581;
  return D.7578;
}


