chunk: Add helper to copy a chunk left-padded to a certain length
authorTobias Brunner <tobias@strongswan.org>
Mon, 8 Apr 2019 13:24:23 +0000 (15:24 +0200)
committerTobias Brunner <tobias@strongswan.org>
Wed, 24 Apr 2019 09:40:14 +0000 (11:40 +0200)
src/libstrongswan/tests/suites/test_chunk.c
src/libstrongswan/utils/chunk.c
src/libstrongswan/utils/chunk.h

index fbfb3ff..2f6b59f 100644 (file)
@@ -574,6 +574,40 @@ START_TEST(test_increment)
 END_TEST
 
 /*******************************************************************************
+ * chunk_copy_pad tests
+ */
+
+static struct {
+       size_t len;
+       u_char chr;
+       chunk_t src;
+       chunk_t exp;
+} copy_pad_data[] = {
+       {0, 0x00, { NULL, 0 }, { NULL, 0 }},
+       {4, 0x00, { NULL, 0 }, chunk_from_chars(0x00,0x00,0x00,0x00)},
+       {0, 0x00, chunk_from_chars(0x01), { NULL, 0 }},
+       {1, 0x00, chunk_from_chars(0x01), chunk_from_chars(0x01)},
+       {2, 0x00, chunk_from_chars(0x01), chunk_from_chars(0x00,0x01)},
+       {3, 0x00, chunk_from_chars(0x01), chunk_from_chars(0x00,0x00,0x01)},
+       {4, 0x00, chunk_from_chars(0x01), chunk_from_chars(0x00,0x00,0x00,0x01)},
+       {4, 0x02, chunk_from_chars(0x01), chunk_from_chars(0x02,0x02,0x02,0x01)},
+       {1, 0x00, chunk_from_chars(0x01,0x02,0x03,0x04), chunk_from_chars(0x04)},
+       {2, 0x00, chunk_from_chars(0x01,0x02,0x03,0x04), chunk_from_chars(0x03,0x04)},
+       {3, 0x00, chunk_from_chars(0x01,0x02,0x03,0x04), chunk_from_chars(0x02,0x03,0x04)},
+       {4, 0x00, chunk_from_chars(0x01,0x02,0x03,0x04), chunk_from_chars(0x01,0x02,0x03,0x04)},
+};
+
+START_TEST(test_copy_pad)
+{
+       chunk_t chunk;
+
+       chunk = chunk_copy_pad(chunk_alloca(copy_pad_data[_i].len),
+                                                  copy_pad_data[_i].src, copy_pad_data[_i].chr);
+       ck_assert_chunk_eq(chunk, copy_pad_data[_i].exp);
+}
+END_TEST
+
+/*******************************************************************************
  * chunk_printable tests
  */
 
@@ -1076,6 +1110,10 @@ Suite *chunk_suite_create()
        tcase_add_loop_test(tc, test_increment, 0, countof(increment_data));
        suite_add_tcase(s, tc);
 
+       tc = tcase_create("chunk_copy_pad");
+       tcase_add_loop_test(tc, test_copy_pad, 0, countof(copy_pad_data));
+       suite_add_tcase(s, tc);
+
        tc = tcase_create("chunk_printable");
        tcase_add_loop_test(tc, test_printable, 0, countof(printable_data));
        tcase_add_loop_test(tc, test_printable_sanitize, 0, countof(printable_data));
index 2393538..919b695 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2008-2013 Tobias Brunner
+ * Copyright (C) 2008-2019 Tobias Brunner
  * Copyright (C) 2005-2006 Martin Willi
  * Copyright (C) 2005 Jan Hutter
  * HSR Hochschule fuer Technik Rapperswil
@@ -752,6 +752,26 @@ bool chunk_increment(chunk_t chunk)
        return TRUE;
 }
 
+/*
+ * Described in header
+ */
+chunk_t chunk_copy_pad(chunk_t dst, chunk_t src, u_char chr)
+{
+       if (dst.ptr)
+       {
+               if (dst.len > src.len)
+               {
+                       memcpy(dst.ptr + dst.len - src.len, src.ptr, src.len);
+                       memset(dst.ptr, chr, dst.len - src.len);
+               }
+               else
+               {
+                       memcpy(dst.ptr, src.ptr + src.len - dst.len, dst.len);
+               }
+       }
+       return dst;
+}
+
 /**
  * Remove non-printable characters from a chunk.
  */
index 0dbe9dc..ea12746 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2008-2013 Tobias Brunner
+ * Copyright (C) 2008-2019 Tobias Brunner
  * Copyright (C) 2005-2008 Martin Willi
  * Copyright (C) 2005 Jan Hutter
  * HSR Hochschule fuer Technik Rapperswil
@@ -292,6 +292,16 @@ static inline chunk_t chunk_skip_zero(chunk_t chunk)
        return chunk;
 }
 
+/**
+ * Copy the data from src to dst, left-padded with chr if dst is longer,
+ * otherwise data is copied truncated on the left.
+ *
+ * @param dst                  data is copied here
+ * @param src                  data is copied from here
+ * @param chr                  value to use for padding if necessary
+ * @return                             the destination chunk
+ */
+chunk_t chunk_copy_pad(chunk_t dst, chunk_t src, u_char chr);
 
 /**
  *  Compare two chunks, returns zero if a equals b