static value_t custom_tagged_ordering_compare(value_t a, value_t b) { CHECK_DOMAIN(vdCustomTagged, a); CHECK_DOMAIN(vdCustomTagged, b); custom_tagged_phylum_t a_phylum = get_custom_tagged_phylum(a); custom_tagged_phylum_t b_phylum = get_custom_tagged_phylum(b); if (a_phylum != b_phylum) return compare_signed_integers(a_phylum, b_phylum); phylum_behavior_t *behavior = get_custom_tagged_phylum_behavior(a_phylum); value_t (*ordering_compare)(value_t a, value_t b) = behavior->ordering_compare; if (ordering_compare == NULL) { return unordered(); } else { return ordering_compare(a, b); } }
static value_t object_ordering_compare(value_t a, value_t b) { CHECK_DOMAIN(vdHeapObject, a); CHECK_DOMAIN(vdHeapObject, b); heap_object_family_t a_family = get_heap_object_family(a); heap_object_family_t b_family = get_heap_object_family(b); if (a_family != b_family) // This may cause us to return a valid result even when a and b are not // comparable. return compare_signed_integers(a_family, b_family); family_behavior_t *behavior = get_heap_object_family_behavior(a); value_t (*ordering_compare)(value_t a, value_t b) = behavior->ordering_compare; if (ordering_compare == NULL) { return unordered(); } else { return ordering_compare(a, b); } }
value_t value_ordering_compare(value_t a, value_t b) { value_domain_t a_domain = get_value_domain(a); value_domain_t b_domain = get_value_domain(b); if (a_domain != b_domain) { int a_ordinal = get_value_domain_ordinal(a_domain); int b_ordinal = get_value_domain_ordinal(b_domain); return compare_signed_integers(a_ordinal, b_ordinal); } else { switch (a_domain) { case vdInteger: return integer_ordering_compare(a, b); case vdHeapObject: return object_ordering_compare(a, b); case vdCustomTagged: return custom_tagged_ordering_compare(a, b); default: return unordered(); } } }
static value_t integer_ordering_compare(value_t a, value_t b) { return compare_signed_integers(get_integer_value(a), get_integer_value(b)); }
TEST(tagged, integer_comparison) { ASSERT_TRUE(test_relation(compare_signed_integers(-1, 1), reLessThan)); ASSERT_TRUE(test_relation(compare_signed_integers(0, 1), reLessThan)); ASSERT_TRUE(test_relation(compare_signed_integers(0, 0), reEqual)); ASSERT_TRUE(test_relation(compare_signed_integers(0, -1), reGreaterThan)); }