get_hazardous_pointer_with_mask (void * volatile * pp, struct MonoThreadHazardPointers * hp, int hazard_index)
{
  void * D.5668;
  unsigned int hazard_index.0;
  _Bool D.5670;
  long int D.5671;
  long int D.5672;
  void * D.5675;
  void * D.5676;
  void * p;

  <D.5630>:
  p = *pp;
  if (hp == 0B) goto <D.5666>; else goto <D.5667>;
  <D.5666>:
  D.5668 = p;
  return D.5668;
  <D.5667>:
  hazard_index.0 = (unsigned int) hazard_index;
  D.5670 = hazard_index.0 > 2;
  D.5671 = (long int) D.5670;
  D.5672 = __builtin_expect (D.5671, 0);
  if (D.5672 != 0) goto <D.5673>; else goto <D.5674>;
  <D.5673>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 40, "(hazard_index) >= 0 && (hazard_index) < HAZARD_POINTER_COUNT");
  <D.5674>:
  D.5675 = mono_lls_pointer_unmask (p);
  hp->hazard_pointers[hazard_index] = D.5675;
  mono_memory_write_barrier ();
  mono_memory_barrier ();
  D.5676 = *pp;
  if (D.5676 != p) goto <D.5677>; else goto <D.5678>;
  <D.5677>:
  hazard_index.0 = (unsigned int) hazard_index;
  D.5670 = hazard_index.0 > 2;
  D.5671 = (long int) D.5670;
  D.5672 = __builtin_expect (D.5671, 0);
  if (D.5672 != 0) goto <D.5679>; else goto <D.5680>;
  <D.5679>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 47, "(hazard_index) >= 0 && (hazard_index) < HAZARD_POINTER_COUNT");
  <D.5680>:
  hp->hazard_pointers[hazard_index] = 0B;
  // predicted unlikely by continue predictor.
  goto <D.5628>;
  <D.5678>:
  goto <D.5629>;
  <D.5628>:
  goto <D.5630>;
  <D.5629>:
  D.5668 = p;
  return D.5668;
}


mono_lls_pointer_unmask (void * p)
{
  void * D.5682;
  long unsigned int p.1;
  long unsigned int D.5684;

  p.1 = (long unsigned int) p;
  D.5684 = p.1 & 18446744073709551612;
  D.5682 = (void *) D.5684;
  return D.5682;
}


mono_memory_write_barrier ()
{
  mono_memory_barrier ();
}


mono_memory_barrier ()
{
  __sync_synchronize ();
}


mono_lls_init (struct MonoLinkedListSet * list, void (*<Tbf>) (void *) free_node_func)
{
  list->head = 0B;
  list->free_node_func = free_node_func;
}


mono_lls_find (struct MonoLinkedListSet * list, struct MonoThreadHazardPointers * hp, uintptr_t key)
{
  gboolean D.5690;
  struct MonoLinkedListSetNode * * D.5691;
  struct MonoLinkedListSetNode * D.5692;
  long unsigned int D.5694;
  _Bool D.5699;
  void * D.5703;
  void (*<Tbf>) (void *) D.5707;
  struct MonoLinkedListSetNode * cur;
  struct MonoLinkedListSetNode * next;
  struct MonoLinkedListSetNode * * prev;
  uintptr_t cur_key;
  void try_again = <<< error >>>;

  try_again:
  prev = &list->head;
  if (0 != 0) goto <D.5686>; else goto <D.5687>;
  <D.5686>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 95, "(2) >= 0 && (2) < HAZARD_POINTER_COUNT");
  <D.5687>:
  hp->hazard_pointers[2] = prev;
  mono_memory_write_barrier ();
  cur = get_hazardous_pointer_with_mask (prev, hp, 1);
  <D.5646>:
  if (cur == 0B) goto <D.5688>; else goto <D.5689>;
  <D.5688>:
  D.5690 = 0;
  return D.5690;
  <D.5689>:
  D.5691 = &cur->next;
  next = get_hazardous_pointer_with_mask (D.5691, hp, 0);
  cur_key = cur->key;
  mono_memory_read_barrier ();
  D.5692 = *prev;
  if (D.5692 != cur) goto try_again; else goto <D.5693>;
  <D.5693>:
  D.5694 = mono_lls_pointer_get_mark (next);
  if (D.5694 == 0) goto <D.5695>; else goto <D.5696>;
  <D.5695>:
  if (cur_key >= key) goto <D.5697>; else goto <D.5698>;
  <D.5697>:
  D.5699 = cur_key == key;
  D.5690 = (gboolean) D.5699;
  return D.5690;
  <D.5698>:
  prev = &cur->next;
  if (0 != 0) goto <D.5700>; else goto <D.5701>;
  <D.5700>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 120, "(2) >= 0 && (2) < HAZARD_POINTER_COUNT");
  <D.5701>:
  hp->hazard_pointers[2] = cur;
  mono_memory_write_barrier ();
  goto <D.5702>;
  <D.5696>:
  next = mono_lls_pointer_unmask (next);
  D.5703 = InterlockedCompareExchangePointer (prev, next, cur);
  if (D.5703 == cur) goto <D.5704>; else goto try_again;
  <D.5704>:
  mono_memory_write_barrier ();
  if (0 != 0) goto <D.5705>; else goto <D.5706>;
  <D.5705>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 126, "(1) >= 0 && (1) < HAZARD_POINTER_COUNT");
  <D.5706>:
  hp->hazard_pointers[1] = 0B;
  D.5707 = list->free_node_func;
  if (D.5707 != 0B) goto <D.5708>; else goto <D.5709>;
  <D.5708>:
  D.5707 = list->free_node_func;
  mono_thread_hazardous_free_or_queue (cur, D.5707, 0, 1);
  <D.5709>:
  <D.5702>:
  cur = mono_lls_pointer_unmask (next);
  if (0 != 0) goto <D.5710>; else goto <D.5711>;
  <D.5710>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 133, "(1) >= 0 && (1) < HAZARD_POINTER_COUNT");
  <D.5711>:
  hp->hazard_pointers[1] = cur;
  mono_memory_write_barrier ();
  goto <D.5646>;
}


mono_memory_read_barrier ()
{
  mono_memory_barrier ();
}


mono_lls_pointer_get_mark (void * n)
{
  uintptr_t D.5713;
  long unsigned int n.2;

  n.2 = (long unsigned int) n;
  D.5713 = n.2 & 1;
  return D.5713;
}


InterlockedCompareExchangePointer (void * volatile * dest, void * exch, void * comp)
{
  void * D.5716;
  long unsigned int comp.3;
  long unsigned int exch.4;
  long unsigned int D.5719;

  comp.3 = (long unsigned int) comp;
  exch.4 = (long unsigned int) exch;
  D.5719 = __sync_val_compare_and_swap_8 (dest, comp.3, exch.4);
  D.5716 = (void *) D.5719;
  return D.5716;
}


mono_lls_insert (struct MonoLinkedListSet * list, struct MonoThreadHazardPointers * hp, struct MonoLinkedListSetNode * value)
{
  long unsigned int D.5721;
  int D.5722;
  gboolean D.5725;
  void * D.5728;
  struct MonoLinkedListSetNode * cur;
  struct MonoLinkedListSetNode * * prev;

  mono_memory_barrier ();
  <D.5654>:
  D.5721 = value->key;
  D.5722 = mono_lls_find (list, hp, D.5721);
  if (D.5722 != 0) goto <D.5723>; else goto <D.5724>;
  <D.5723>:
  D.5725 = 0;
  return D.5725;
  <D.5724>:
  cur = hp->hazard_pointers[1];
  prev = hp->hazard_pointers[2];
  value->next = cur;
  if (0 != 0) goto <D.5726>; else goto <D.5727>;
  <D.5726>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 159, "(0) >= 0 && (0) < HAZARD_POINTER_COUNT");
  <D.5727>:
  hp->hazard_pointers[0] = value;
  mono_memory_write_barrier ();
  mono_memory_write_barrier ();
  D.5728 = InterlockedCompareExchangePointer (prev, value, cur);
  if (D.5728 == cur) goto <D.5729>; else goto <D.5730>;
  <D.5729>:
  D.5725 = 1;
  return D.5725;
  <D.5730>:
  goto <D.5654>;
}


mono_lls_remove (struct MonoLinkedListSet * list, struct MonoThreadHazardPointers * hp, struct MonoLinkedListSetNode * value)
{
  long unsigned int D.5732;
  int D.5733;
  gboolean D.5736;
  _Bool D.5737;
  long int D.5738;
  long int D.5739;
  struct MonoLinkedListSetNode * * D.5742;
  void * D.5743;
  void * D.5744;
  void * D.5747;
  void (*<Tbf>) (void *) D.5752;
  struct MonoLinkedListSetNode * cur;
  struct MonoLinkedListSetNode * * prev;
  struct MonoLinkedListSetNode * next;

  <D.5664>:
  D.5732 = value->key;
  D.5733 = mono_lls_find (list, hp, D.5732);
  if (D.5733 == 0) goto <D.5734>; else goto <D.5735>;
  <D.5734>:
  D.5736 = 0;
  return D.5736;
  <D.5735>:
  next = hp->hazard_pointers[0];
  cur = hp->hazard_pointers[1];
  prev = hp->hazard_pointers[2];
  D.5737 = cur != value;
  D.5738 = (long int) D.5737;
  D.5739 = __builtin_expect (D.5738, 0);
  if (D.5739 != 0) goto <D.5740>; else goto <D.5741>;
  <D.5740>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 185, "cur == value");
  <D.5741>:
  D.5742 = &cur->next;
  D.5743 = mask (next, 1);
  D.5744 = InterlockedCompareExchangePointer (D.5742, D.5743, next);
  if (D.5744 != next) goto <D.5745>; else goto <D.5746>;
  <D.5745>:
  // predicted unlikely by continue predictor.
  goto <D.5663>;
  <D.5746>:
  mono_memory_write_barrier ();
  D.5747 = InterlockedCompareExchangePointer (prev, next, cur);
  if (D.5747 == cur) goto <D.5748>; else goto <D.5749>;
  <D.5748>:
  mono_memory_write_barrier ();
  if (0 != 0) goto <D.5750>; else goto <D.5751>;
  <D.5750>:
  monoeg_assertion_message ("* Assertion at %s:%d, condition `%s\' not met\n", "mono-linked-list-set.c", 194, "(1) >= 0 && (1) < HAZARD_POINTER_COUNT");
  <D.5751>:
  hp->hazard_pointers[1] = 0B;
  D.5752 = list->free_node_func;
  if (D.5752 != 0B) goto <D.5753>; else goto <D.5754>;
  <D.5753>:
  D.5752 = list->free_node_func;
  mono_thread_hazardous_free_or_queue (value, D.5752, 0, 1);
  <D.5754>:
  goto <D.5755>;
  <D.5749>:
  D.5732 = value->key;
  mono_lls_find (list, hp, D.5732);
  <D.5755>:
  D.5736 = 1;
  return D.5736;
  <D.5663>:
  goto <D.5664>;
}


mask (void * n, uintptr_t bit)
{
  void * D.5757;
  long unsigned int n.5;
  long unsigned int D.5759;

  n.5 = (long unsigned int) n;
  D.5759 = n.5 | bit;
  D.5757 = (void *) D.5759;
  return D.5757;
}


