ASN.1: Introduce helper function to free ASN.1 sequence
diff --git a/include/mbedtls/asn1.h b/include/mbedtls/asn1.h
index 5f15ddb..43ab9ae 100644
--- a/include/mbedtls/asn1.h
+++ b/include/mbedtls/asn1.h
@@ -343,6 +343,9 @@
  * \brief       Parses and splits an ASN.1 "SEQUENCE OF <tag>".
  *              Updates the pointer to immediately behind the full sequence tag.
  *
+ * This function allocates memory for the sequence elements. You can free
+ * the allocated memory with mbedtls_asn1_sequence_free().
+ *
  * \note        On error, this function may return a partial list in \p cur.
  *              You must set `cur->next = NULL` before calling this function!
  *              Otherwise it is impossible to distinguish a previously non-null
@@ -384,6 +387,28 @@
                                   const unsigned char *end,
                                   mbedtls_asn1_sequence *cur,
                                   int tag );
+/**
+ * \brief          Free a heap-allocated linked list presentation of
+ *                 an ASN.1 sequence, including the first element.
+ *
+ * There are two common ways to manage the memory used for the representation
+ * of a parsed ASN.1 sequence:
+ * - Allocate a head node `mbedtls_asn1_sequence *head` with mbedtls_calloc().
+ *   Pass this node as the `cur` argument to mbedtls_asn1_get_sequence_of().
+ *   When you have finished processing the sequence,
+ *   call mbedtls_asn1_sequence_free() on `head`.
+ * - Allocate a head node `mbedtls_asn1_sequence *head` in any manner,
+ *   for example on the stack. Make sure that `head->next == NULL`.
+ *   Pass `head` as the `cur` argument to mbedtls_asn1_get_sequence_of().
+ *   When you have finished processing the sequence,
+ *   call mbedtls_asn1_sequence_free() on `head->cur`,
+ *   then free `head` itself in the appropriate manner.
+ *
+ * \param seq      The address of the first sequence component. This may
+ *                 be \c NULL, in which case this functions returns
+ *                 immediately.
+ */
+void mbedtls_asn1_sequence_free( mbedtls_asn1_sequence *seq );
 
 #if defined(MBEDTLS_BIGNUM_C)
 /**
diff --git a/library/asn1parse.c b/library/asn1parse.c
index e7e4d13..3105d32 100644
--- a/library/asn1parse.c
+++ b/library/asn1parse.c
@@ -269,7 +269,16 @@
     return( 0 );
 }
 
-
+void mbedtls_asn1_sequence_free( mbedtls_asn1_sequence *seq )
+{
+    while( seq != NULL )
+    {
+        mbedtls_asn1_sequence *next = seq->next;
+        mbedtls_platform_zeroize( seq, sizeof( *seq ) );
+        mbedtls_free( seq );
+        seq = next;
+    }
+}
 
 /*
  *  Parses and splits an ASN.1 "SEQUENCE OF <tag>"
diff --git a/tests/suites/test_suite_asn1parse.function b/tests/suites/test_suite_asn1parse.function
index f07fd40..898f729 100644
--- a/tests/suites/test_suite_asn1parse.function
+++ b/tests/suites/test_suite_asn1parse.function
@@ -508,7 +508,7 @@
                       int expected_result )
 {
     mbedtls_asn1_sequence head = { { 0, 0, NULL }, NULL };
-    mbedtls_asn1_sequence *cur, *next;
+    mbedtls_asn1_sequence *cur;
     unsigned char *p = input->x;
     const char *rest = description;
     unsigned long n;
@@ -549,13 +549,7 @@
     }
 
 exit:
-    cur = head.next;
-    while( cur != NULL )
-    {
-        next = cur->next;
-        mbedtls_free( cur );
-        cur = next;
-    }
+    mbedtls_asn1_sequence_free( head.next );
 }
 /* END_CASE */