lib: Add macro ARRAY_DEL_ELEMENT()
authorVolker Lendecke <vl@samba.org>
Wed, 25 Mar 2020 21:07:44 +0000 (22:07 +0100)
committerRalph Boehme <slow@samba.org>
Thu, 26 Mar 2020 14:43:31 +0000 (14:43 +0000)
Every time I have to remove an element from within an array I have to
scratch my head about the memmove arguments. Make this easier to use.

Signed-off-by: Volker Lendecke <vl@samba.org>
Reviewed-by: Ralph Boehme <slow@samba.org>
lib/replace/replace.h
lib/replace/tests/testsuite.c

index 177be37edbe0d3270dbe946bcf4334fd5f425f74..59f0b60f8a0beff244870ef772479dd16c3b0882 100644 (file)
@@ -849,6 +849,12 @@ typedef unsigned long long ptrdiff_t ;
 #endif
 #define ARRAY_SIZE(a) (sizeof(a)/sizeof(a[0]))
 
+/**
+ * Remove an array element by moving the rest one down
+ */
+#define ARRAY_DEL_ELEMENT(a,i,n) \
+if((i)<((n)-1)){memmove(&((a)[(i)]),&((a)[(i)+1]),(sizeof(*(a))*((n)-(i)-1)));}
+
 /**
  * Pointer difference macro
  */
index 7f9801e9f98db0f44b619ed1160d4d76e0793a0a..2ece95332d23ec74ef962025187dda01f566deda 100644 (file)
@@ -1095,6 +1095,47 @@ static bool test_closefrom(void)
        return true;
 }
 
+static bool test_array_del_element(void)
+{
+       int a[] = { 1,2,3,4,5 };
+
+       printf("test: array_del_element\n");
+
+       ARRAY_DEL_ELEMENT(a, 4, ARRAY_SIZE(a));
+
+       if ((a[0] != 1) ||
+           (a[1] != 2) ||
+           (a[2] != 3) ||
+           (a[3] != 4) ||
+           (a[4] != 5)) {
+               return false;
+       }
+
+       ARRAY_DEL_ELEMENT(a, 0, ARRAY_SIZE(a));
+
+       if ((a[0] != 2) ||
+           (a[1] != 3) ||
+           (a[2] != 4) ||
+           (a[3] != 5) ||
+           (a[4] != 5)) {
+               return false;
+       }
+
+       ARRAY_DEL_ELEMENT(a, 2, ARRAY_SIZE(a));
+
+       if ((a[0] != 2) ||
+           (a[1] != 3) ||
+           (a[2] != 5) ||
+           (a[3] != 5) ||
+           (a[4] != 5)) {
+               return false;
+       }
+
+       printf("success: array_del_element\n");
+
+       return true;
+}
+
 bool torture_local_replace(struct torture_context *ctx)
 {
        bool ret = true;
@@ -1145,6 +1186,7 @@ bool torture_local_replace(struct torture_context *ctx)
        ret &= test_utimes();
        ret &= test_memmem();
        ret &= test_closefrom();
+       ret &= test_array_del_element();
 
        return ret;
 }