[PATCH 1/2] uintset: add l_uintset_subtract

James Prestwood <[email protected]>
Newsgroups dev.linux.lists.ell
Message-ID <[email protected]>
This subtracts set_b from set_a, and returns the new set.
---
 ell/ell.sym   |  1 +
 ell/uintset.c | 37 +++++++++++++++++++++++++++++++++++++
 ell/uintset.h |  3 +++
 3 files changed, 41 insertions(+)

diff --git a/ell/ell.sym b/ell/ell.sym
index 8f4e59d..f454921 100644
--- a/ell/ell.sym
+++ b/ell/ell.sym
@@ -537,6 +537,7 @@ global:
 	l_uintset_foreach;
 	l_uintset_clone;
 	l_uintset_intersect;
+	l_uintset_subtract;
 	l_uintset_isempty;
 	l_uintset_size;
 	/* uuid */
diff --git a/ell/uintset.c b/ell/uintset.c
index 863bc56..4837bcf 100644
--- a/ell/uintset.c
+++ b/ell/uintset.c
@@ -532,6 +532,43 @@ LIB_EXPORT struct l_uintset *l_uintset_intersect(const struct l_uintset *set_a,
 	return intersection;
 }
 
+/**
+ * l_uintset_subtract:
+ * @set_a: The set of numbers
+ * @set_b: The set of numbers to subtract from set_a
+ *
+ * Subtracts two sets of numbers of an equal base, e.g.:
+ * l_uintset_get_min(set_a) must be equal to l_uintset_get_min(set_b) and
+ * l_uintset_get_max(set_a) must be equal to l_uintset_get_max(set_b)
+ *
+ * Returns: A newly allocated l_uintset containing set_a - set_b
+ */
+LIB_EXPORT struct l_uintset *l_uintset_subtract(const struct l_uintset *set_a,
+						const struct l_uintset *set_b)
+{
+	struct l_uintset *subtraction;
+	uint32_t offset;
+	uint32_t offset_max;
+
+	if (unlikely(!set_a || !set_b))
+		return NULL;
+
+	if (unlikely(set_a->min != set_b->min || set_a->max != set_b->max))
+		return NULL;
+
+	subtraction = l_uintset_new_from_range(set_a->min, set_a->max);
+
+	offset_max = (set_a->size + BITS_PER_LONG - 1) / BITS_PER_LONG;
+
+	/* Subtract by: set_a & ~set_b */
+	for (offset = 0; offset < offset_max; offset++) {
+		subtraction->bits[offset] =
+				set_a->bits[offset] & ~(set_b->bits[offset]);
+	}
+
+	return subtraction;
+}
+
 /**
  * l_uintset_isempty
  * @set: The set of numbers
diff --git a/ell/uintset.h b/ell/uintset.h
index aa9de48..86ce8f7 100644
--- a/ell/uintset.h
+++ b/ell/uintset.h
@@ -60,6 +60,9 @@ void l_uintset_foreach(const struct l_uintset *set,
 struct l_uintset *l_uintset_clone(const struct l_uintset *original);
 struct l_uintset *l_uintset_intersect(const struct l_uintset *set_a,
 						const struct l_uintset *set_b);
+struct l_uintset *l_uintset_subtract(const struct l_uintset *set_a,
+						const struct l_uintset *set_b);
+
 bool l_uintset_isempty(const struct l_uintset *set);
 uint32_t l_uintset_size(const struct l_uintset *set);
 
-- 
2.34.1
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.