Large public header documentataion improvement
diff --git a/inc/UsefulBuf.h b/inc/UsefulBuf.h
index 80d33ac..0bbe3b5 100644
--- a/inc/UsefulBuf.h
+++ b/inc/UsefulBuf.h
@@ -78,7 +78,7 @@
  The goal of this code is to make buffer and pointer manipulation
  easier and safer when working with binary data.
 
- The \ref UsefulBuf, \ref UsefulOutBuf and \ref UsefulInputBuf
+ The @ref UsefulBuf, @ref UsefulOutBuf and @ref UsefulInputBuf
  structures are used to represent buffers rather than ad hoc pointers and
  lengths.
 
@@ -101,12 +101,12 @@
 
  This code consists of a lot of inline functions and a few that are
  not.  It should not generate very much object code, especially with
- the optimizer turned up to \c -Os or \c -O3.
+ the optimizer turned up to @c -Os or @c -O3.
  */
 
 
 /**
- \ref UsefulBufC and \ref UsefulBuf are simple data structures to hold
+ @ref UsefulBufC and @ref UsefulBuf are simple data structures to hold
  a pointer and length for binary data.  In C99 this data structure can
  be passed on the stack making a lot of code cleaner than carrying
  around a pointer and length as two parameters.
@@ -121,31 +121,31 @@
  gigabit-per-second IP router), it is probably better to have cleaner
  code you can be most certain about the security of.
 
- The non-const \ref UsefulBuf is usually used to refer a buffer to be
+ The non-const @ref UsefulBuf is usually used to refer a buffer to be
  filled in.  The length is the size of the buffer.
 
- The const \ref UsefulBufC is usually used to refer to some data that
+ The const @ref UsefulBufC is usually used to refer to some data that
  has been filled in. The length is amount of valid data pointed to.
 
- A common use is to pass a \ref UsefulBuf to a function, the function
- fills it in, the function returns a \ref UsefulBufC. The pointer is
+ A common use is to pass a @ref UsefulBuf to a function, the function
+ fills it in, the function returns a @ref UsefulBufC. The pointer is
  the same in both.
 
- A \ref UsefulBuf is null, it has no value, when \c ptr in it is \c NULL.
+ A @ref UsefulBuf is null, it has no value, when @c ptr in it is @c NULL.
 
  There are utility functions for the following:
   - Initializing
-  - Create initialized const \ref UsefulBufC from compiler literals
-  - Create initialized const \ref UsefulBufC from NULL-terminated string
-  - Make an empty \ref UsefulBuf on the stack
-  - Checking whether a \ref UsefulBuf is null, empty or both
+  - Create initialized const @ref UsefulBufC from compiler literals
+  - Create initialized const @ref UsefulBufC from NULL-terminated string
+  - Make an empty @ref UsefulBuf on the stack
+  - Checking whether a @ref UsefulBuf is null, empty or both
   - Copying, copying with offset, copying head or tail
   - Comparing and finding substrings
 
- See also \ref UsefulOutBuf. It is a richer structure that has both
+ See also @ref UsefulOutBuf. It is a richer structure that has both
  the size of the valid data and the size of the buffer.
 
- \ref UsefulBuf is only 16 or 8 bytes on a 64- or 32-bit machine so it
+ @ref UsefulBuf is only 16 or 8 bytes on a 64- or 32-bit machine so it
  can go on the stack and be a function parameter or return value.
 
  Another way to look at it is this. C has the NULL-terminated string
@@ -153,7 +153,7 @@
  binary strings. Other languages do have such means, Rust, an
  efficient compiled language, for example.
 
- \ref UsefulBuf is kind of like the Useful Pot Pooh gave Eeyore on his
+ @ref UsefulBuf is kind of like the Useful Pot Pooh gave Eeyore on his
  birthday.  Eeyore's balloon fits beautifully, "it goes in and out
  like anything".
 */
@@ -164,8 +164,8 @@
 
 
 /**
- This non-const \ref UsefulBuf is typically used for some allocated
- memory that is to be filled in. The \c len is the amount of memory,
+ This non-const @ref UsefulBuf is typically used for some allocated
+ memory that is to be filled in. The @c len is the amount of memory,
  not the length of the valid data in the buffer.
  */
 typedef struct q_useful_buf {
@@ -175,65 +175,65 @@
 
 
 /**
- A null \ref UsefulBufC is one that has no value in the same way a \c
- NULL pointer has no value.  A \ref UsefulBufC is \c NULL when the \c
- ptr field is \c NULL. It doesn't matter what \c len is.  See
+ A null @ref UsefulBufC is one that has no value in the same way a @c
+ NULL pointer has no value.  A @ref UsefulBufC is @c NULL when the @c
+ ptr field is @c NULL. It doesn't matter what @c len is.  See
  UsefulBuf_IsEmpty() for the distinction between null and empty.
  */
 #define NULLUsefulBufC  ((UsefulBufC) {NULL, 0})
 
 
 /**
- A null \ref UsefulBuf is one that has no memory associated the same
- way \c NULL points to nothing. It does not matter what \c len is.
+ A null @ref UsefulBuf is one that has no memory associated the same
+ way @c NULL points to nothing. It does not matter what @c len is.
  */
 #define NULLUsefulBuf   ((UsefulBuf) {NULL, 0})
 
 
 /**
- @brief Check if a \ref UsefulBuf is \ref NULLUsefulBuf or not.
+ @brief Check if a @ref UsefulBuf is @ref NULLUsefulBuf or not.
 
  @param[in] UB The UsefulBuf to check.
 
- @return 1 if it is \ref NULLUsefulBuf, 0 if not.
+ @return 1 if it is @ref NULLUsefulBuf, 0 if not.
  */
 static inline int UsefulBuf_IsNULL(UsefulBuf UB);
 
 
 /**
- @brief Check if a \ref UsefulBufC is \ref NULLUsefulBufC or not.
+ @brief Check if a @ref UsefulBufC is @ref NULLUsefulBufC or not.
 
- @param[in] UB The \ref UsefulBufC to check.
+ @param[in] UB The @ref UsefulBufC to check.
 
- @return 1 if it is \c NULLUsefulBufC, 0 if not.
+ @return 1 if it is @c NULLUsefulBufC, 0 if not.
  */
 static inline int UsefulBuf_IsNULLC(UsefulBufC UB);
 
 
 /**
- @brief Check if a \ref UsefulBuf is empty or not.
+ @brief Check if a @ref UsefulBuf is empty or not.
 
- @param[in] UB The \ref UsefulBuf to check.
+ @param[in] UB The @ref UsefulBuf to check.
 
  @return 1 if it is empty, 0 if not.
 
- An "empty" \ref UsefulBuf is one that has a value and can be
+ An "empty" @ref UsefulBuf is one that has a value and can be
  considered to be set, but that value is of zero length.  It is empty
- when \c len is zero. It doesn't matter what the \c ptr is.
+ when @c len is zero. It doesn't matter what the @c ptr is.
 
- A lot of uses will not need to clearly distinguish a \c NULL \ref
- UsefulBuf from an empty one and can have the \c ptr \c NULL and the
- \c len 0.  However if a use of \ref UsefulBuf needs to make a
- distinction then \c ptr should not be \c NULL when the \ref UsefulBuf
- is considered empty, but not \c NULL.
+ A lot of uses will not need to clearly distinguish a @c NULL @ref
+ UsefulBuf from an empty one and can have the @c ptr @c NULL and the
+ @c len 0.  However if a use of @ref UsefulBuf needs to make a
+ distinction then @c ptr should not be @c NULL when the @ref UsefulBuf
+ is considered empty, but not @c NULL.
  */
 static inline int UsefulBuf_IsEmpty(UsefulBuf UB);
 
 
 /**
- @brief Check if a \ref UsefulBufC is empty or not.
+ @brief Check if a @ref UsefulBufC is empty or not.
 
- @param[in] UB The \ref UsefulBufC to check.
+ @param[in] UB The @ref UsefulBufC to check.
 
  @return 1 if it is empty, 0 if not.
  */
@@ -241,49 +241,49 @@
 
 
 /**
- @brief Check if a \ref UsefulBuf is \ref NULLUsefulBuf or empty.
+ @brief Check if a @ref UsefulBuf is @ref NULLUsefulBuf or empty.
 
- @param[in] UB The \ref UsefulBuf to check.
+ @param[in] UB The @ref UsefulBuf to check.
 
- @return 1 if it is either \ref NULLUsefulBuf or empty, 0 if not.
+ @return 1 if it is either @ref NULLUsefulBuf or empty, 0 if not.
  */
 static inline int UsefulBuf_IsNULLOrEmpty(UsefulBuf UB);
 
 
 /**
- @brief Check if a \ref UsefulBufC is \ref NULLUsefulBufC or empty.
+ @brief Check if a @ref UsefulBufC is @ref NULLUsefulBufC or empty.
 
- @param[in] UB The \ref UsefulBufC to check.
+ @param[in] UB The @ref UsefulBufC to check.
 
- @return 1 if it is either \ref NULLUsefulBufC or empty, 0 if not.
+ @return 1 if it is either @ref NULLUsefulBufC or empty, 0 if not.
  */
 static inline int UsefulBuf_IsNULLOrEmptyC(UsefulBufC UB);
 
 
 /**
- @brief Convert a non-const \ref UsefulBuf to a const \ref UsefulBufC.
+ @brief Convert a non-const @ref UsefulBuf to a const @ref UsefulBufC.
 
- @param[in] UB The \ref UsefulBuf to convert.
+ @param[in] UB The @ref UsefulBuf to convert.
 
- @return A \ref UsefulBufC struct.
+ @return A @ref UsefulBufC struct.
  */
 static inline UsefulBufC UsefulBuf_Const(const UsefulBuf UB);
 
 
 /**
- @brief Convert a const \ref UsefulBufC to a non-const \ref UsefulBuf.
+ @brief Convert a const @ref UsefulBufC to a non-const @ref UsefulBuf.
 
- @param[in] UBC The \ref UsefulBuf to convert.
+ @param[in] UBC The @ref UsefulBuf to convert.
 
- @return A non-const \ref UsefulBuf struct.
+ @return A non-const @ref UsefulBuf struct.
  */
 static inline UsefulBuf UsefulBuf_Unconst(const UsefulBufC UBC);
 
 
 /**
- Convert a literal string to a \ref UsefulBufC.
+ Convert a literal string to a @ref UsefulBufC.
 
- \c szString must be a literal string that \c sizeof() works on.  This
+ @c szString must be a literal string that @c sizeof() works on.  This
  is better for literal strings than UsefulBuf_FromSZ() because it
  generates less code. It will not work on non-literal strings.
 
@@ -294,9 +294,9 @@
 
 
 /**
- Convert a literal byte array to a \ref UsefulBufC.
+ Convert a literal byte array to a @ref UsefulBufC.
 
- \c pBytes must be a literal string that \c sizeof() works on.  It
+ @c pBytes must be a literal string that @c sizeof() works on.  It
  will not work on non-literal arrays.
  */
 #define UsefulBuf_FROM_BYTE_ARRAY_LITERAL(pBytes) \
@@ -304,8 +304,8 @@
 
 
 /**
- Make an automatic variable named \c name of type \ref UsefulBuf and
- point it to a stack variable of the given \c size.
+ Make an automatic variable named @c name of type @ref UsefulBuf and
+ point it to a stack variable of the given @c size.
  */
 #define  UsefulBuf_MAKE_STACK_UB(name, size) \
     uint8_t    __pBuf##name[(size)];\
@@ -313,8 +313,8 @@
 
 
 /**
- Make a byte array in to a \ref UsefulBuf. This is usually used on
- stack variables or static variables.  Also see \ref
+ Make a byte array in to a @ref UsefulBuf. This is usually used on
+ stack variables or static variables.  Also see @ref
  UsefulBuf_MAKE_STACK_UB.
  */
 #define UsefulBuf_FROM_BYTE_ARRAY(pBytes) \
@@ -322,13 +322,13 @@
 
 
 /**
- @brief Convert a NULL-terminated string to a \ref UsefulBufC.
+ @brief Convert a NULL-terminated string to a @ref UsefulBufC.
 
  @param[in] szString The string to convert.
 
- @return A \ref UsefulBufC struct.
+ @return A @ref UsefulBufC struct.
 
- \c UsefulBufC.ptr points to the string so its lifetime must be
+ @c UsefulBufC.ptr points to the string so its lifetime must be
  maintained.
 
  The terminating \0 (NULL) is NOT included in the length.
@@ -337,63 +337,63 @@
 
 
 /**
- @brief Copy one \ref UsefulBuf into another at an offset.
+ @brief Copy one @ref UsefulBuf into another at an offset.
 
  @param[in] Dest     Destination buffer to copy into.
- @param[in] uOffset  The byte offset in \c Dest at which to copy to.
+ @param[in] uOffset  The byte offset in @c Dest at which to copy to.
  @param[in] Src      The bytes to copy.
 
- @return Pointer and length of the copy or \ref NULLUsefulBufC.
+ @return Pointer and length of the copy or @ref NULLUsefulBufC.
 
- This fails and returns \ref NULLUsefulBufC if \c offset is beyond the
- size of \c Dest.
+ This fails and returns @ref NULLUsefulBufC if @c offset is beyond the
+ size of @c Dest.
 
- This fails and returns \ref NULLUsefulBufC if the \c Src length plus
- \c uOffset is greater than the length of \c Dest.
+ This fails and returns @ref NULLUsefulBufC if the @c Src length plus
+ @c uOffset is greater than the length of @c Dest.
 
- The results are undefined if \c Dest and \c Src overlap.
+ The results are undefined if @c Dest and @c Src overlap.
 
- This assumes that there is valid data in \c Dest up to \c
- uOffset. The \ref UsefulBufC returned starts at the beginning of \c
- Dest and goes to \c Src.len \c + \c uOffset.
+ This assumes that there is valid data in @c Dest up to @c
+ uOffset. The @ref UsefulBufC returned starts at the beginning of @c
+ Dest and goes to @c Src.len @c + @c uOffset.
  */
 UsefulBufC UsefulBuf_CopyOffset(UsefulBuf Dest, size_t uOffset, const UsefulBufC Src);
 
 
 /**
- @brief Copy one \ref UsefulBuf into another.
+ @brief Copy one @ref UsefulBuf into another.
 
  @param[in] Dest  The destination buffer to copy into.
  @param[out] Src  The source to copy from.
 
- @return Filled in \ref UsefulBufC on success, \ref NULLUsefulBufC
+ @return Filled in @ref UsefulBufC on success, @ref NULLUsefulBufC
          on failure.
 
- This fails if \c Src.len is greater than \c Dest.len.
+ This fails if @c Src.len is greater than @c Dest.len.
 
- Note that like \c memcpy(), the pointers are not checked and this
- will crash rather than return \ref NULLUsefulBufC if they are \c
+ Note that like @c memcpy(), the pointers are not checked and this
+ will crash rather than return @ref NULLUsefulBufC if they are @c
  NULL or invalid.
 
- The results are undefined if \c Dest and \c Src overlap.
+ The results are undefined if @c Dest and @c Src overlap.
  */
 static inline UsefulBufC UsefulBuf_Copy(UsefulBuf Dest, const UsefulBufC Src);
 
 
 /**
- @brief Set all bytes in a \ref UsefulBuf to a value, for example to 0.
+ @brief Set all bytes in a @ref UsefulBuf to a value, for example to 0.
 
  @param[in] pDest  The destination buffer to copy into.
  @param[in] value  The value to set the bytes to.
 
- Note that like \c memset(), the pointer in \c pDest is not checked
- and this will crash if \c NULL or invalid.
+ Note that like @c memset(), the pointer in @c pDest is not checked
+ and this will crash if @c NULL or invalid.
  */
 static inline UsefulBufC UsefulBuf_Set(UsefulBuf pDest, uint8_t value);
 
 
 /**
- @brief Copy a pointer into a \ref UsefulBuf.
+ @brief Copy a pointer into a @ref UsefulBuf.
 
  @param[in,out] Dest  The destination buffer to copy into.
  @param[in] ptr       The source to copy from.
@@ -401,11 +401,11 @@
 
  @return 0 on success, 1 on failure.
 
- This fails and returns \ref NULLUsefulBufC if \c uLen is greater than
- \c pDest->len.
+ This fails and returns @ref NULLUsefulBufC if @c uLen is greater than
+ @c pDest->len.
 
- Note that like \c memcpy(), the pointers are not checked and this
- will crash, rather than return 1 if they are \c NULL or invalid.
+ Note that like @c memcpy(), the pointers are not checked and this
+ will crash, rather than return 1 if they are @c NULL or invalid.
  */
 static inline UsefulBufC UsefulBuf_CopyPtr(UsefulBuf Dest,
                                            const void *ptr,
@@ -413,51 +413,51 @@
 
 
 /**
-  @brief Returns a truncation of a \ref UsefulBufC.
+  @brief Returns a truncation of a @ref UsefulBufC.
 
   @param[in] UB       The buffer to get the head of.
   @param[in] uAmount  The number of bytes in the head.
 
-  @return A \ref UsefulBufC that is the head of UB.
+  @return A @ref UsefulBufC that is the head of UB.
  */
 static inline UsefulBufC UsefulBuf_Head(UsefulBufC UB, size_t uAmount);
 
 
 /**
- @brief  Returns bytes from the end of a \ref UsefulBufC.
+ @brief  Returns bytes from the end of a @ref UsefulBufC.
 
  @param[in] UB       The buffer to get the tail of.
  @param[in] uAmount  The offset from the start where the tail is to begin.
 
- @return A \ref UsefulBufC that is the tail of \c UB or \ref NULLUsefulBufC
-         if \c uAmount is greater than the length of the \ref UsefulBufC.
+ @return A @ref UsefulBufC that is the tail of @c UB or @ref NULLUsefulBufC
+         if @c uAmount is greater than the length of the @ref UsefulBufC.
 
- If \c UB.ptr is \c NULL, but \c UB.len is not zero, then the result will
- be a \ref UsefulBufC with a \c NULL \c ptr and \c len with the length
+ If @c UB.ptr is @c NULL, but @c UB.len is not zero, then the result will
+ be a @ref UsefulBufC with a @c NULL @c ptr and @c len with the length
  of the tail.
  */
 static inline UsefulBufC UsefulBuf_Tail(UsefulBufC UB, size_t uAmount);
 
 
 /**
- @brief Compare one \ref UsefulBufC to another.
+ @brief Compare one @ref UsefulBufC to another.
 
  @param[in] UB1  The first buffer to compare.
  @param[in] UB2  The second buffer to compare.
 
  @return 0, positive or negative value.
 
- Returns a negative value if \c UB1 if is less than \c UB2. \c UB1 is
- less than \c UB2 if it is shorter or the first byte that is not the
+ Returns a negative value if @c UB1 if is less than @c UB2. @c UB1 is
+ less than @c UB2 if it is shorter or the first byte that is not the
  same is less.
 
  Returns 0 if the inputs are the same.
 
- Returns a positive value if \c UB2 is less than \c UB1.
+ Returns a positive value if @c UB2 is less than @c UB1.
 
  All that is of significance is that the result is positive, negative
  or 0. (This doesn't return the difference between the first
- non-matching byte like \c memcmp() ).
+ non-matching byte like @c memcmp() ).
  */
 int UsefulBuf_Compare(const UsefulBufC UB1, const UsefulBufC UB2);
 
@@ -468,8 +468,8 @@
  @param[in] UB     The destination buffer for byte comparison.
  @param[in] uValue The byte value to compare to.
 
- @return  Offset of first byte that isn't \c uValue or
-          \c SIZE_MAX if all bytes are \c uValue.
+ @return  Offset of first byte that isn't @c uValue or
+          @c SIZE_MAX if all bytes are @c uValue.
 
  Note that unlike most comparison functions, 0
  does not indicate a successful comparison, so the
@@ -477,25 +477,25 @@
 
       UsefulBuf_IsValue(...) == SIZE_MAX
 
- If \c UB is null or empty, there is no match
+ If @c UB is null or empty, there is no match
  and 0 is returned.
  */
 size_t UsefulBuf_IsValue(const UsefulBufC UB, uint8_t uValue);
 
 
 /**
- @brief Find one \ref UsefulBufC in another.
+ @brief Find one @ref UsefulBufC in another.
 
  @param[in] BytesToSearch  Buffer to search through.
  @param[in] BytesToFind    Buffer with bytes to be found.
 
- @return Position of found bytes or \c SIZE_MAX if not found.
+ @return Position of found bytes or @c SIZE_MAX if not found.
  */
 size_t UsefulBuf_FindBytes(UsefulBufC BytesToSearch, UsefulBufC BytesToFind);
 
 
 #if 1 // NOT_DEPRECATED
-/** Deprecated macro; use \ref UsefulBuf_FROM_SZ_LITERAL instead */
+/** Deprecated macro; use @ref UsefulBuf_FROM_SZ_LITERAL instead */
 #define SZLiteralToUsefulBufC(szString) \
     ((UsefulBufC) {(szString), sizeof(szString)-1})
 
@@ -504,7 +504,7 @@
     uint8_t    __pBuf##name[(size)];\
     UsefulBuf  name = {__pBuf##name , sizeof( __pBuf##name )}
 
-/** Deprecated macro; use \ref UsefulBuf_FROM_BYTE_ARRAY_LITERAL instead */
+/** Deprecated macro; use @ref UsefulBuf_FROM_BYTE_ARRAY_LITERAL instead */
 #define ByteArrayLiteralToUsefulBufC(pBytes) \
     ((UsefulBufC) {(pBytes), sizeof(pBytes)})
 
@@ -519,11 +519,11 @@
 
 
 /**
- @brief Copy a \c float to a \c uint32_t.
+ @brief Copy a @c float to a @c uint32_t.
 
  @param[in] f  Float value to copy.
 
- @return  A \c uint32_t with the float bits.
+ @return  A @c uint32_t with the float bits.
 
  Convenience function to avoid type punning, compiler warnings and
  such. The optimizer usually reduces this to a simple assignment.  This
@@ -533,11 +533,11 @@
 
 
 /**
- @brief Copy a \c double to a \c uint64_t.
+ @brief Copy a @c double to a @c uint64_t.
 
  @param[in] d  Double value to copy.
 
- @return  A \c uint64_t with the double bits.
+ @return  A @c uint64_t with the double bits.
 
  Convenience function to avoid type punning, compiler warnings and
  such. The optimizer usually reduces this to a simple assignment.  This
@@ -547,11 +547,11 @@
 
 
 /**
- @brief Copy a \c uint32_t to a \c float.
+ @brief Copy a @c uint32_t to a @c float.
 
  @param[in] u32  Integer value to copy.
 
- @return  The value as a \c float.
+ @return  The value as a @c float.
 
  Convenience function to avoid type punning, compiler warnings and
  such. The optimizer usually reduces this to a simple assignment.  This
@@ -561,11 +561,11 @@
 
 
 /**
- @brief Copy a \c uint64_t to a \c double.
+ @brief Copy a @c uint64_t to a @c double.
 
  @param[in] u64  Integer value to copy.
 
- @return  The value as a \c double.
+ @return  The value as a @c double.
 
  Convenience function to avoid type punning, compiler warnings and
  such. The optimizer usually reduces this to a simple assignment.  This
@@ -582,19 +582,19 @@
  to file.
 
  The main idea is that all the pointer manipulation is performed by
- \ref UsefulOutBuf functions so the caller doesn't have to do any
+ @ref UsefulOutBuf functions so the caller doesn't have to do any
  pointer manipulation.  The pointer manipulation is centralized.  This
  code will have been reviewed and written carefully so it spares the
  caller of much of this work and results in safer code with less work.
 
- The \ref UsefulOutBuf methods that add data to the output buffer
+ The @ref UsefulOutBuf methods that add data to the output buffer
  always check the length and will never write off the end of the
  output buffer. If an attempt to add data that will not fit is made,
  an internal error flag will be set and further attempts to add data
  will not do anything.
 
  There is no way to ever write off the end of that buffer when calling
- the \c UsefulOutBuf_AddXxx() and \c UsefulOutBuf_InsertXxx()
+ the @c UsefulOutBuf_AddXxx() and @c UsefulOutBuf_InsertXxx()
  functions.
 
  The functions to add data do not return an error. The working model
@@ -610,9 +610,9 @@
 
  The general call flow is:
 
-    - Initialize by calling \ref UsefulOutBuf_Init(). The output
+    - Initialize by calling @ref UsefulOutBuf_Init(). The output
       buffer given to it can be from the heap, stack or
-      otherwise. \ref UsefulOutBuf_MakeOnStack is a convenience macro
+      otherwise. @ref UsefulOutBuf_MakeOnStack is a convenience macro
       that makes a buffer on the stack and initializes it.
 
     - Call methods like UsefulOutBuf_InsertString(),
@@ -623,12 +623,12 @@
     - Call UsefulOutBuf_OutUBuf() or UsefulOutBuf_CopyOut() to see
       there were no errors and to get the serialized output bytes.
 
- \ref UsefulOutBuf can be used in a size calculation mode to calculate
+ @ref UsefulOutBuf can be used in a size calculation mode to calculate
  the size of output that would be generated. This is useful to
  calculate the size of a buffer that is to be allocated to hold the
- output. To use \ref UsefulOutBuf in this mode, call
- UsefulOutBuf_Init() with the \c Storage \ref UsefulBuf as
- \c (UsefulBuf){NULL,MAX_UINT32}. Then call all the Insert and Add
+ output. To use @ref UsefulOutBuf in this mode, call
+ UsefulOutBuf_Init() with the @c Storage @ref UsefulBuf as
+ @c (UsefulBuf){NULL,MAX_UINT32}. Then call all the Insert and Add
  functions. No attempt will made to actually copy data, so only the
  lengths have to be valid for these calls.
 
@@ -636,7 +636,7 @@
  bytes order (big endian).
 
  The possible errors are:
-  - The \ref UsefulOutBuf was not initialized or was corrupted.
+  - The @ref UsefulOutBuf was not initialized or was corrupted.
 
   - An attempt was made to add data that will not fit.
 
@@ -654,7 +654,7 @@
  almost no pointer manipulation in it, is easier to read, and easier
  to review.
 
- A \ref UsefulOutBuf is small and can go on the stack:
+ A @ref UsefulOutBuf is small and can go on the stack:
    - 32 bytes (27 bytes plus alignment padding) on a 64-bit machine
    - 16 bytes (15 bytes plus alignment padding) on a 32-bit machines
  */
@@ -670,21 +670,21 @@
 /**
  @brief Initialize and supply the actual output buffer.
 
- @param[out] pUOutBuf  The \ref UsefulOutBuf to initialize.
+ @param[out] pUOutBuf  The @ref UsefulOutBuf to initialize.
  @param[in] Storage    Buffer to output into.
 
- Initializes  the \ref UsefulOutBuf with storage. Sets the current
+ Initializes  the @ref UsefulOutBuf with storage. Sets the current
  position to the beginning of the buffer clears the error.
 
- This must be called before the \ref UsefulOutBuf is used.
+ This must be called before the @ref UsefulOutBuf is used.
  */
 void UsefulOutBuf_Init(UsefulOutBuf *pUOutBuf, UsefulBuf Storage);
 
 
 /**
- Convenience macro to make a \ref UsefulOutBuf on the stack and
+ Convenience macro to make a @ref UsefulOutBuf on the stack and
  initialize it with a stack buffer of the given size. The variable
- will be named \c name.
+ will be named @c name.
  */
 #define  UsefulOutBuf_MakeOnStack(name, size) \
    uint8_t       __pBuf##name[(size)];\
@@ -693,9 +693,9 @@
 
 
 /**
- @brief Reset a \ref UsefulOutBuf for re use
+ @brief Reset a @ref UsefulOutBuf for re use
 
- @param[in] pUOutBuf Pointer to the \ref UsefulOutBuf
+ @param[in] pUOutBuf Pointer to the @ref UsefulOutBuf
 
  This sets the amount of data in the output buffer to none and clears
  the error state.
@@ -709,26 +709,26 @@
 
 
 /**
- @brief Returns position of end of data in the \ref UsefulOutBuf.
+ @brief Returns position of end of data in the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
 
  @return position of end of data.
 
- On a freshly initialized \ref UsefulOutBuf with no data added, this
+ On a freshly initialized @ref UsefulOutBuf with no data added, this
  will return 0. After 10 bytes have been added, it will return 10 and
  so on.
 
- Generally callers will not need this function for most uses of \ref
+ Generally callers will not need this function for most uses of @ref
  UsefulOutBuf.
  */
 static inline size_t UsefulOutBuf_GetEndPosition(UsefulOutBuf *pUOutBuf);
 
 
 /**
- @brief Returns whether any data has been added to the \ref UsefulOutBuf.
+ @brief Returns whether any data has been added to the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
 
  @return 1 if output position is at start.
  */
@@ -736,14 +736,14 @@
 
 
 /**
- @brief Inserts bytes into the \ref UsefulOutBuf.
+ @brief Inserts bytes into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] NewData   The bytes to insert.
  @param[in] uPos      Index in output buffer at which to insert.
 
- \c NewData is the pointer and length for the bytes to be added to the
- output buffer. There must be room in the output buffer for all of \c
+ @c NewData is the pointer and length for the bytes to be added to the
+ output buffer. There must be room in the output buffer for all of @c
  NewData or an error will occur.
 
  The insertion point must be between 0 and the current valid data. If
@@ -755,16 +755,16 @@
  and the end of data previously added to the output buffer are slid to
  the right to make room for the new data.
 
- Overlapping buffers are OK. \c NewData can point to data in the
+ Overlapping buffers are OK. @c NewData can point to data in the
  output buffer.
 
- If an error occurs an error state is set in the \ref UsefulOutBuf. No
+ If an error occurs an error state is set in the @ref UsefulOutBuf. No
  error is returned.  All subsequent attempts to add data will do
  nothing.
 
  The intended use is that all additions are made without checking for
  an error. The error will be taken into account when
- UsefulOutBuf_OutUBuf() returns \c NullUsefulBufC.
+ UsefulOutBuf_OutUBuf() returns @c NullUsefulBufC.
  UsefulOutBuf_GetError() can also be called to check for an error.
  */
 void UsefulOutBuf_InsertUsefulBuf(UsefulOutBuf *pUOutBuf,
@@ -773,16 +773,16 @@
 
 
 /**
- @brief Insert a data buffer into the \ref UsefulOutBuf.
+ @brief Insert a data buffer into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] pBytes    Pointer to the bytes to insert
  @param[in] uLen      Length of the bytes to insert
  @param[in] uPos      Index in output buffer at which to insert
 
  See UsefulOutBuf_InsertUsefulBuf() for details. This is the same with
  the difference being a pointer and length is passed in rather than an
- \ref UsefulBufC.
+ @ref UsefulBufC.
  */
 static inline void UsefulOutBuf_InsertData(UsefulOutBuf *pUOutBuf,
                                            const void *pBytes,
@@ -793,7 +793,7 @@
 /**
  @brief Insert a NULL-terminated string into the UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] szString  NULL-terminated string to insert.
  @param[in] uPos      Index in output buffer at which to insert.
  */
@@ -803,7 +803,7 @@
 
 
 /**
- @brief Insert a byte into the \ref UsefulOutBuf.
+ @brief Insert a byte into the @ref UsefulOutBuf.
 
  @param[in] pUOutBuf  Pointer to the UsefulOutBuf.
  @param[in] byte      Bytes to insert.
@@ -818,9 +818,9 @@
 
 
 /**
- @brief Insert a 16-bit integer into the \ref UsefulOutBuf.
+ @brief Insert a 16-bit integer into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger16  Integer to insert.
  @param[in] uPos        Index in output buffer at which to insert.
 
@@ -835,9 +835,9 @@
 
 
 /**
- @brief Insert a 32-bit integer into the \ref UsefulOutBuf.
+ @brief Insert a 32-bit integer into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger32  Integer to insert.
  @param[in] uPos        Index in output buffer at which to insert.
 
@@ -852,9 +852,9 @@
 
 
 /**
- @brief Insert a 64-bit integer into the \ref UsefulOutBuf.
+ @brief Insert a 64-bit integer into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger64  Integer to insert.
  @param[in] uPos        Index in output buffer at which to insert.
 
@@ -869,16 +869,16 @@
 
 
 /**
- @brief Insert a \c float into the \ref UsefulOutBuf.
+ @brief Insert a @c float into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
- @param[in] f         \c float to insert.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
+ @param[in] f         @c float to insert.
  @param[in] uPos      Index in output buffer at which to insert.
 
  See UsefulOutBuf_InsertUsefulBuf() for details. This is the same with
- the difference being a \c float is to be inserted.
+ the difference being a @c float is to be inserted.
 
- The \c float will be inserted in network byte order (big endian).
+ The @c float will be inserted in network byte order (big endian).
  */
 static inline void UsefulOutBuf_InsertFloat(UsefulOutBuf *pUOutBuf,
                                             float f,
@@ -886,16 +886,16 @@
 
 
 /**
- @brief Insert a \c double into the \ref UsefulOutBuf.
+ @brief Insert a @c double into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
- @param[in] d         \c double  to insert.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
+ @param[in] d         @c double  to insert.
  @param[in] uPos      Index in output buffer at which to insert.
 
  See UsefulOutBuf_InsertUsefulBuf() for details. This is the same with
- the difference being a \c double is to be inserted.
+ the difference being a @c double is to be inserted.
 
- The \c double will be inserted in network byte order (big endian).
+ The @c double will be inserted in network byte order (big endian).
  */
 static inline void UsefulOutBuf_InsertDouble(UsefulOutBuf *pUOutBuf,
                                              double d,
@@ -903,10 +903,10 @@
 
 
 /**
- @brief Append a \ref UsefulBuf into the \ref UsefulOutBuf.
+ @brief Append a @ref UsefulBuf into the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
- @param[in] NewData   The \ref UsefulBuf with the bytes to append.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
+ @param[in] NewData   The @ref UsefulBuf with the bytes to append.
 
  See UsefulOutBuf_InsertUsefulBuf() for details. This does the same
  with the insertion point at the end of the valid data.
@@ -916,11 +916,11 @@
 
 
 /**
- @brief Append bytes to the \ref UsefulOutBuf.
+ @brief Append bytes to the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] pBytes    Pointer to bytes to append.
- @param[in] uLen      Length of \c pBytes to append.
+ @param[in] uLen      Length of @c pBytes to append.
 
  See UsefulOutBuf_InsertData() for details. This does the same
  with the insertion point at the end of the valid data.
@@ -931,9 +931,9 @@
 
 
 /**
- @brief Append a NULL-terminated string to the \ref UsefulOutBuf
+ @brief Append a NULL-terminated string to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] szString  NULL-terminated string to append.
  */
 static inline void UsefulOutBuf_AppendString(UsefulOutBuf *pUOutBuf,
@@ -941,9 +941,9 @@
 
 
 /**
- @brief Append a byte to the \ref UsefulOutBuf
+ @brief Append a byte to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[in] byte      Bytes to append.
 
  See UsefulOutBuf_InsertByte() for details. This does the same
@@ -954,9 +954,9 @@
 
 
 /**
- @brief Append an integer to the \ref UsefulOutBuf
+ @brief Append an integer to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger16  Integer to append.
 
  See UsefulOutBuf_InsertUint16() for details. This does the same
@@ -969,9 +969,9 @@
 
 
 /**
- @brief Append an integer to the \ref UsefulOutBuf
+ @brief Append an integer to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger32  Integer to append.
 
  See UsefulOutBuf_InsertUint32() for details. This does the same
@@ -984,9 +984,9 @@
 
 
 /**
- @brief Append an integer to the \ref UsefulOutBuf
+ @brief Append an integer to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf.
  @param[in] uInteger64  Integer to append.
 
  See UsefulOutBuf_InsertUint64() for details. This does the same
@@ -999,10 +999,10 @@
 
 
 /**
- @brief Append a \c float to the \ref UsefulOutBuf
+ @brief Append a @c float to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
- @param[in] f         \c float to append.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
+ @param[in] f         @c float to append.
 
  See UsefulOutBuf_InsertFloat() for details. This does the same
  with the insertion point at the end of the valid data.
@@ -1014,10 +1014,10 @@
 
 
 /**
- @brief Append a \c double to the \ref UsefulOutBuf
+ @brief Append a @c double to the @ref UsefulOutBuf
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
- @param[in] d         \c double to append.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
+ @param[in] d         @c double to append.
 
  See UsefulOutBuf_InsertDouble() for details. This does the same
  with the insertion point at the end of the valid data.
@@ -1031,7 +1031,7 @@
 /**
  @brief Returns the current error status.
 
- @param[in] pUOutBuf Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf Pointer to the @ref UsefulOutBuf.
 
  @return 0 if all OK, 1 on error.
 
@@ -1051,7 +1051,7 @@
 /**
  @brief Returns number of bytes unused used in the output buffer.
 
- @param[in] pUOutBuf Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf Pointer to the @ref UsefulOutBuf.
 
  @return Number of unused bytes or zero.
 
@@ -1063,12 +1063,12 @@
 
 
 /**
- @brief Returns 1 if some number of bytes will fit in the \ref UsefulOutBuf.
+ @brief Returns 1 if some number of bytes will fit in the @ref UsefulOutBuf.
 
- @param[in] pUOutBuf    Pointer to the \ref UsefulOutBuf
+ @param[in] pUOutBuf    Pointer to the @ref UsefulOutBuf
  @param[in] uLen  Number of bytes for which to check
 
- @return 1 if \c uLen bytes will fit, 0 if not.
+ @return 1 if @c uLen bytes will fit, 0 if not.
 
  Because of the error handling strategy and checks in
  UsefulOutBuf_InsertUsefulBuf() it is usually not necessary to use
@@ -1080,12 +1080,12 @@
 /**
    @brief Returns the resulting valid data in a UsefulOutBuf
 
-   @param[in] pUOutBuf Pointer to the \ref UsefulOutBuf.
+   @param[in] pUOutBuf Pointer to the @ref UsefulOutBuf.
 
-   @return The valid data in \ref UsefulOutBuf or
-           \ref NULLUsefulBufC if there was an error adding data.
+   @return The valid data in @ref UsefulOutBuf or
+           @ref NULLUsefulBufC if there was an error adding data.
 
-   The storage for the returned data is the \c Storage parameter passed
+   The storage for the returned data is the @c Storage parameter passed
    to UsefulOutBuf_Init(). See also UsefulOutBuf_CopyOut().
 
    This can be called anytime and many times to get intermediate
@@ -1098,14 +1098,14 @@
 /**
  @brief Copies the valid data into a supplied buffer
 
- @param[in] pUOutBuf  Pointer to the \ref UsefulOutBuf.
+ @param[in] pUOutBuf  Pointer to the @ref UsefulOutBuf.
  @param[out] Dest     The destination buffer to copy into.
 
- @return Pointer and length of copied data or \c NULLUsefulBufC
-         if it will not fit in the \c Dest buffer.
+ @return Pointer and length of copied data or @c NULLUsefulBufC
+         if it will not fit in the @c Dest buffer.
 
  This is the same as UsefulOutBuf_OutUBuf() except it copies the data
- to \c Dest.
+ to @c Dest.
 */
 UsefulBufC UsefulOutBuf_CopyOut(UsefulOutBuf *pUOutBuf, UsefulBuf Dest);
 
@@ -1113,7 +1113,7 @@
 
 
 /**
- \ref UsefulInputBuf is the counterpart to \ref UsefulOutBuf and is
+ @ref UsefulInputBuf is the counterpart to @ref UsefulOutBuf and is
  for parsing data read or received.  Initialize it with the data from
  the network. Then use the functions here to get data chunks of
  various types. A position cursor is maintained internally.
@@ -1123,14 +1123,14 @@
  care called incorrectly, an attempt is made to seek of the end of the
  buffer, etc. This makes it easier to write safe and correct code.
  For example, the QCBOR decoder implementation is safer and easier to
- review through its use of \ref UsefulInputBuf.
+ review through its use of @ref UsefulInputBuf.
 
- \ref UsefulInputBuf maintains an internal error state.  The
+ @ref UsefulInputBuf maintains an internal error state.  The
  intended use is that data chunks can be fetched without error
  checking until the end.  Once data has been requested off the end of
  the buffer, the error state is entered. In the error state the
- \c UsefulInputBuf_GetXxxx() functions return 0, or \c NULL or
- \ref NULLUsefulBufC. As long as null are not dereferenced, the
+ @c UsefulInputBuf_GetXxxx() functions return 0, or @c NULL or
+ @ref NULLUsefulBufC. As long as null are not dereferenced, the
  error check can be put off until the end, simplifying the calling
  code.
 
@@ -1139,9 +1139,9 @@
  internet protocols.
 
  Lots of inline functions are used to keep code size down. The code
- optimizer, particularly with the \c -Os or \c -O3, also reduces code
+ optimizer, particularly with the @c -Os or @c -O3, also reduces code
  size a lot. The only non-inline code is UsefulInputBuf_GetBytes()
- which is less than 100 bytes so use of \ref UsefulInputBuf doesn't
+ which is less than 100 bytes so use of @ref UsefulInputBuf doesn't
  add much code for all the messy hard-to-get right issues with parsing
  in C that is solves.
 
@@ -1218,7 +1218,7 @@
  @param[in] pUInBuf  Pointer to the UsefulInputBuf.
  @param[in] uLen     Number of bytes to check availability for.
 
- @return 1 if \c uLen bytes are available after the cursor, and 0 if not.
+ @return 1 if @c uLen bytes are available after the cursor, and 0 if not.
  */
 static int UsefulInputBuf_BytesAvailable(UsefulInputBuf *pUInBuf, size_t uLen);
 
@@ -1231,33 +1231,33 @@
 
  @return Pointer to bytes.
 
- This consumes \c uNum bytes from the input buffer. It returns a
- pointer to the start of the \c uNum bytes.
+ This consumes @c uNum bytes from the input buffer. It returns a
+ pointer to the start of the @c uNum bytes.
 
- If there are not \c uNum bytes in the input buffer, \c NULL will be
+ If there are not @c uNum bytes in the input buffer, @c NULL will be
  returned and an error will be set.
 
- It advances the current position by \c uNum bytes.
+ It advances the current position by @c uNum bytes.
  */
 const void * UsefulInputBuf_GetBytes(UsefulInputBuf *pUInBuf, size_t uNum);
 
 
 /**
- @brief Get \ref UsefulBuf out of the input buffer.
+ @brief Get @ref UsefulBuf out of the input buffer.
 
  @param[in] pUInBuf  Pointer to the UsefulInputBuf.
  @param[in] uNum     Number of bytes to get.
 
- @return A \ref UsefulBufC with ptr and length of bytes consumed.
+ @return A @ref UsefulBufC with ptr and length of bytes consumed.
 
- This consumes \c uNum bytes from the input buffer and returns the
- pointer and length for them as a \ref UsefulBufC. The length returned
- will always be \c uNum.
+ This consumes @c uNum bytes from the input buffer and returns the
+ pointer and length for them as a @ref UsefulBufC. The length returned
+ will always be @c uNum.
 
- If there are not \c uNum bytes in the input buffer, \ref NULLUsefulBufC
+ If there are not @c uNum bytes in the input buffer, @ref NULLUsefulBufC
  will be returned and the error state is set.
 
- It advances the current position by \c uNum bytes.
+ It advances the current position by @c uNum bytes.
  */
 static inline UsefulBufC UsefulInputBuf_GetUsefulBuf(UsefulInputBuf *pUInBuf, size_t uNum);
 
@@ -1265,7 +1265,7 @@
 /**
  @brief Get a byte out of the input buffer.
 
- @param[in] pUInBuf  Pointer to the \ref UsefulInputBuf.
+ @param[in] pUInBuf  Pointer to the @ref UsefulInputBuf.
 
  @return The byte.
 
@@ -1276,8 +1276,8 @@
  to know whether the 0 was the real value or just returned in error,
  but you may not have to do that right away.  Check the error state
  with UsefulInputBuf_GetError().  You can also know you are in the
- error state if UsefulInputBuf_GetBytes() returns \c NULL or the \c
- ptr from UsefulInputBuf_GetUsefulBuf() is \c NULL.
+ error state if UsefulInputBuf_GetBytes() returns @c NULL or the @c
+ ptr from UsefulInputBuf_GetUsefulBuf() is @c NULL.
 
  It advances the current position by 1 byte.
  */
@@ -1285,14 +1285,14 @@
 
 
 /**
- @brief Get a \c uint16_t out of the input buffer.
+ @brief Get a @c uint16_t out of the input buffer.
 
  @param[in] pUInBuf  Pointer to the UsefulInputBuf.
 
- @return The \c uint16_t.
+ @return The @c uint16_t.
 
  See UsefulInputBuf_GetByte(). This works the same, except it returns
- a \c uint16_t and two bytes are consumed.
+ a @c uint16_t and two bytes are consumed.
 
  The input bytes must be in network order (big endian).
  */
@@ -1304,10 +1304,10 @@
 
  @param[in] pUInBuf  Pointer to the UsefulInputBuf.
 
- @return The \c uint32_t.
+ @return The @c uint32_t.
 
  See UsefulInputBuf_GetByte(). This works the same, except it returns
- a \c uint32_t and four bytes are consumed.
+ a @c uint32_t and four bytes are consumed.
 
  The input bytes must be in network order (big endian).
  */
@@ -1322,7 +1322,7 @@
  @return The uint64_t.
 
  See UsefulInputBuf_GetByte(). This works the same, except it returns
- a \c uint64_t and eight bytes are consumed.
+ a @c uint64_t and eight bytes are consumed.
 
  The input bytes must be in network order (big endian).
  */
@@ -1362,7 +1362,7 @@
 /**
  @brief Get the error status.
 
- @param[in] pUInBuf  Pointer to the \ref UsefulInputBuf.
+ @param[in] pUInBuf  Pointer to the @ref UsefulInputBuf.
 
  @return 0 if there is no error, 1 if there is.
 
@@ -1370,7 +1370,7 @@
  - Attempt to fetch data past the end of the buffer
  - Attempt to seek to a position past the end of the buffer
  - Attempt to get data from an uninitialized  or corrupt instance
-   of \ref UsefulInputBuf
+   of @ref UsefulInputBuf
 
  Once in the error state, it can only be cleared by calling
  UsefulInputBuf_Init().
diff --git a/inc/qcbor.h b/inc/qcbor.h
index eddf3fe..edf3e98 100644
--- a/inc/qcbor.h
+++ b/inc/qcbor.h
@@ -41,31 +41,30 @@
  This section contains comments describing changes made to the module.
  Notice that changes are listed in reverse chronological order.
 
- when               who             what, where, why
- --------           ----            ---------------------------------------------------
- 4/6/19             llundblade      Wrapped bstr returned now includes the wrapping bstr
- 02/16/19           llundblade      Redesign MemPool to fix memory access alignment bug
- 12/18/18           llundblade      Move decode malloc optional code to separate repository
- 12/13/18           llundblade      Documentatation improvements
- 11/29/18           llundblade      Rework to simpler handling of tags and labels.
- 11/9/18            llundblade      Error codes are now enums.
- 11/1/18            llundblade      Floating support.
- 10/31/18           llundblade      Switch to one license that is almost BSD-3.
- 10/15/18           llundblade      Indefinite length maps and arrays supported
- 10/8/18            llundblade      Indefinite length strings supported
- 09/28/18           llundblade      Added bstr wrapping feature for COSE implementation.
- 07/05/17           llundbla        Add bstr wrapping of maps/arrays for COSE.
- 03/01/17           llundbla        More data types; decoding improvements and fixes.
- 11/13/16           llundbla        Integrate most TZ changes back into github version.
- 09/30/16           gkanike         Porting to TZ.
- 03/15/16           llundbla        Initial Version.
+ when       who             what, where, why
+ --------   ----            ---------------------------------------------------
+ 04/26/19   llundblade      Big documentation & style update. No interface change.
+ 02/16/19   llundblade      Redesign MemPool to fix memory access alignment bug.
+ 12/18/18   llundblade      Move decode malloc optional code to separate repository.
+ 12/13/18   llundblade      Documentatation improvements.
+ 11/29/18   llundblade      Rework to simpler handling of tags and labels.
+ 11/9/18    llundblade      Error codes are now enums.
+ 11/1/18    llundblade      Floating support.
+ 10/31/18   llundblade      Switch to one license that is almost BSD-3.
+ 10/15/18   llundblade      indefinite-length maps and arrays supported
+ 10/8/18    llundblade      indefinite-length strings supported
+ 09/28/18   llundblade      Added bstr wrapping feature for COSE implementation.
+ 07/05/17   llundbla        Add bstr wrapping of maps/arrays for COSE.
+ 03/01/17   llundbla        More data types; decoding improvements and fixes.
+ 11/13/16   llundbla        Integrate most TZ changes back into github version.
+ 09/30/16   gkanike         Porting to TZ.
+ 03/15/16   llundbla        Initial Version.
 
  =====================================================================================*/
 
 #ifndef __QCBOR__qcbor__
 #define __QCBOR__qcbor__
 
-/*...... This is a ruler that is 80 characters long...........................*/
 
 /* ===========================================================================
    BEGINNING OF PRIVATE PART OF THIS FILE
@@ -122,7 +121,8 @@
    struct {
       // See function OpenArrayInternal() for detailed comments on how this works
       uint32_t  uStart;     // uStart is the byte position where the array starts
-      uint16_t  uCount;     // Number of items in the arrary or map; counts items in a map, not pairs of items
+      uint16_t  uCount;     // Number of items in the arrary or map; counts items
+                            // in a map, not pairs of items
       uint8_t   uMajorType; // Indicates if item is a map or an array
    } pArrays[QCBOR_MAX_ARRAY_NESTING1+1], // stored state for the nesting levels
    *pCurrentNesting; // the current nesting level
@@ -141,8 +141,9 @@
 */
 struct _QCBOREncodeContext {
    // PRIVATE DATA STRUCTURE
-   UsefulOutBuf      OutBuf;  // Pointer to output buffer, its length and position in it
-   uint8_t           uError;  // Error state
+   UsefulOutBuf      OutBuf;  // Pointer to output buffer, its length and
+                              // position in it
+   uint8_t           uError;  // Error state, always from QCBORError enum
    QCBORTrackNesting nesting; // Keep track of array and map nesting
 };
 
@@ -194,7 +195,7 @@
 
    QCBORDecodeNesting nesting;
 
-   // If a string allocator is configured for indefinite length
+   // If a string allocator is configured for indefinite-length
    // strings, it is configured here.
    QCORInternalAllocator StringAllocator;
 
@@ -261,8 +262,8 @@
 
 
 /*
- These are special values for the AdditionalInfo bits that are part of the first byte.
- Mostly they encode the length of the data item.
+ These are special values for the AdditionalInfo bits that are part of
+ the first byte.  Mostly they encode the length of the data item.
  */
 #define LEN_IS_ONE_BYTE    24
 #define LEN_IS_TWO_BYTES   25
@@ -276,59 +277,105 @@
 
 /*
  24 is a special number for CBOR. Integers and lengths
- less than it are encoded in the same byte as the major type
+ less than it are encoded in the same byte as the major type.
  */
 #define CBOR_TWENTY_FOUR   24
 
 
 /*
- Tags that are used with CBOR_MAJOR_TYPE_OPTIONAL. These are
- the ones defined in the CBOR spec.
+ Tags that are used with CBOR_MAJOR_TYPE_OPTIONAL. These
+ are types defined in RFC 7049 and some additional ones
+ in the IANA CBOR tags registry.
  */
-/** See QCBOREncode_AddDateString() below */
+/** See QCBOREncode_AddDateString(). */
 #define CBOR_TAG_DATE_STRING    0
-/** See QCBOREncode_AddDateEpoch_2() */
+/** See QCBOREncode_AddDateEpoch(). */
 #define CBOR_TAG_DATE_EPOCH     1
+/** See QCBOREncode_AddPositiveBignum(). */
 #define CBOR_TAG_POS_BIGNUM     2
+/** See QCBOREncode_AddNegativeBignum(). */
 #define CBOR_TAG_NEG_BIGNUM     3
+/** CBOR tag for a two-element array representing a fraction with a
+    mantissa and base-10 scaling factor. No API is provided for this
+    tag. */
 #define CBOR_TAG_FRACTION       4
+/** CBOR tag for a two-element array representing a fraction with a
+    mantissa and base-2 scaling factor. No API is provided for this
+    tag. */
 #define CBOR_TAG_BIGFLOAT       5
-
+/** Tag for COSE format encryption with no recipient
+    identification. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). No API is provided for this
+    tag. */
 #define CBOR_TAG_COSE_ENCRYPTO 16
+/** Tag for COSE format MAC'd data with no recipient
+    identification. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). No API is provided for this
+    tag.*/
 #define CBOR_TAG_COSE_MAC0     17
+/** Tag for COSE format single signature signing. No API is provided
+    for this tag. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). */
 #define CBOR_TAG_COSE_SIGN1    18
-
-/* The data in byte string should be converted in base 64 URL when encoding in JSON or similar text-based representations */
+/** A hint that the following byte string should be encoded in
+    Base64URL when converting to JSON or similar text-based
+    representations. Call @c
+    QCBOREncode_AddTag(pCtx,CBOR_TAG_ENC_AS_B64URL) before the call to
+    QCBOREncode_AddBytes(). */
 #define CBOR_TAG_ENC_AS_B64URL 21
-/* The data in byte string should be encoded in base 64 when encoding in JSON */
+/** A hint that the following byte string should be encoded in Base64
+    when converting to JSON or similar text-based
+    representations. Call @c
+    QCBOREncode_AddTag(pCtx,CBOR_TAG_ENC_AS_B64) before the call to
+    QCBOREncode_AddBytes(). */
 #define CBOR_TAG_ENC_AS_B64    22
-/* The data in byte string should be encoded in base 16 when encoding in JSON */
+/** A hint that the following byte string should be encoded in base-16
+    format per [RFC 4648] (https://tools.ietf.org/html/rfc4648) when
+    converting to JSON or similar text-based
+    representations. Essentially, Base-16 encoding is the standard
+    case- insensitive hex encoding and may be referred to as
+    "hex". Call @c QCBOREncode_AddTag(pCtx,CBOR_TAG_ENC_AS_B16) before
+    the call to QCBOREncode_AddBytes(). */
 #define CBOR_TAG_ENC_AS_B16    23
+/** Tag to indicate a byte string contains encoded CBOR. No API is
+    provided for this tag. */
 #define CBOR_TAG_CBOR          24
-/** The data in the string is a URIs, as defined in RFC3986 */
+/** See QCBOREncode_AddURI(). */
 #define CBOR_TAG_URI           32
-/** The data in the string is a base 64'd URL */
+/** See QCBOREncode_AddB64URLText(). */
 #define CBOR_TAG_B64URL        33
-/** The data in the string is base 64'd */
+/** See QCBOREncode_AddB64Text(). */
 #define CBOR_TAG_B64           34
-/** regular expressions in Perl Compatible Regular Expressions (PCRE) / JavaScript syntax ECMA262. */
+/** See QCBOREncode_AddRegex(). */
 #define CBOR_TAG_REGEX         35
-/** MIME messages (including all headers), as defined in RFC2045 */
+/** See QCBOREncode_AddMIMEData(). */
 #define CBOR_TAG_MIME          36
-/** Binary UUID */
+/** See QCBOREncode_AddBinaryUUID(). */
 #define CBOR_TAG_BIN_UUID      37
-
+/** The data is a CBOR Web Token per [RFC 8392]
+    (https://tools.ietf.org/html/rfc8932). No API is provided for this
+    tag. */
 #define CBOR_TAG_CWT           61
-
+/** Tag for COSE format encryption. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). No API is provided for this
+    tag. */
 #define CBOR_TAG_ENCRYPT       96
+/** Tag for COSE format MAC. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). No API is provided for this
+    tag. */
 #define CBOR_TAG_MAC           97
+/** Tag for COSE format signed data. See [RFC 8152, COSE]
+    (https://tools.ietf.org/html/rfc8152). No API is provided for this
+    tag. */
 #define CBOR_TAG_SIGN          98
-
+/** World geographic coordinates. See ISO 6709, [RFC 5870]
+    (https://tools.ietf.org/html/rfc5870) and WGS-84. No API is
+    provided for this tag. */
 #define CBOR_TAG_GEO_COORD    103
-
-
-/** The data is CBOR data */
+/** The magic number, self-described CBOR. No API is provided for this
+    tag. */
 #define CBOR_TAG_CBOR_MAGIC 55799
+
 #define CBOR_TAG_NONE  UINT64_MAX
 
 
@@ -361,33 +408,33 @@
 
  Q C B O R   E n c o d e / D e c o d e
 
- This implements CBOR -- Concise Binary Object Representation as defined
- in RFC 7049. More info is at http://cbor.io.  This is a near-complete
- implementation of the specification. Limitations are listed further down.
+ This implements CBOR -- Concise Binary Object Representation as
+ defined in [RFC 7049] (https://tools.ietf.org/html/rfc7049). More
+ info is at http://cbor.io.  This is a near-complete implementation of
+ the specification. Limitations are listed further down.
 
  CBOR is intentionally designed to be translatable to JSON, but not
  all CBOR can convert to JSON. See RFC 7049 for more info on how to
  construct CBOR that is the most JSON friendly.
 
- The memory model for encoding and decoding is that encoded CBOR
- must be in a contiguous buffer in memory.  During encoding the
- caller must supply an output buffer and if the encoding would go
- off the end of the buffer an error is returned.  During decoding
- the caller supplies the encoded CBOR in a contiguous buffer
- and the decoder returns pointers and lengths into that buffer
- for strings.
+ The memory model for encoding and decoding is that encoded CBOR must
+ be in a contiguous buffer in memory.  During encoding the caller must
+ supply an output buffer and if the encoding would go off the end of
+ the buffer an error is returned.  During decoding the caller supplies
+ the encoded CBOR in a contiguous buffer and the decoder returns
+ pointers and lengths into that buffer for strings.
 
  This implementation does not require malloc. All data structures
  passed in/out of the APIs can fit on the stack.
 
- Decoding of indefinite length strings is a special case that requires
+ Decoding of indefinite-length strings is a special case that requires
  a "string allocator" to allocate memory into which the segments of
- the string are coalesced. Without this, decoding will error out if
- an indefinite length string is encountered (indefinite length maps
- and arrays do not require the string allocator). A simple string
- allocator called MemPool is built-in and will work if supplied with
- a block of memory to allocate. The string allocator can optionally
- use malloc() or some other custom scheme.
+ the string are coalesced. Without this, decoding will error out if an
+ indefinite-length string is encountered (indefinite-length maps and
+ arrays do not require the string allocator). A simple string
+ allocator called MemPool is built-in and will work if supplied with a
+ block of memory to allocate. The string allocator can optionally use
+ malloc() or some other custom scheme.
 
  Here are some terms and definitions:
 
@@ -399,275 +446,311 @@
  - "Map": A collection of label/value pairs. Each pair is a data
  item. A JSON "object" is the same as a CBOR "map".
 
- - "Label": The data item in a pair in a map that names or identifies the
- pair, not the value. This implementation refers to it as a "label".
- JSON refers to it as the "name". The CBOR RFC refers to it this as a "key".
- This implementation chooses label instead because key is too easily confused
- with a cryptographic key. The COSE standard, which uses CBOR, has also
- chosen to use the term "label" rather than "key" for this same reason.
+ - "Label": The data item in a pair in a map that names or identifies
+ the pair, not the value. This implementation refers to it as a
+ "label".  JSON refers to it as the "name". The CBOR RFC refers to it
+ this as a "key".  This implementation chooses label instead because
+ key is too easily confused with a cryptographic key. The COSE
+ standard, which uses CBOR, has also chosen to use the term "label"
+ rather than "key" for this same reason.
 
  - "Key": See "Label" above.
 
- - "Tag": Optional info that can be added before each data item. This is always
- CBOR major type 6.
+ - "Tag": Optional integer that can be added before each data item
+ usually to indicate it is new or more specific data type. For
+ example, a tag can indicate an integer is a date, or that a map is to
+ be considered a type (analogous to a typedef in C).
 
- - "Initial Byte": The first byte of an encoded item. Encoding and decoding of
- this byte is taken care of by the implementation.
+ - "Initial Byte": The first byte of an encoded item. Encoding and
+ decoding of this byte is taken care of by the implementation.
 
- - "Additional Info": In addition to the major type, all data items have some
- other info. This is usually the length of the data, but can be several
- other things. Encoding and decoding of this is taken care of by the
- implementation.
+ - "Additional Info": In addition to the major type, all data items
+ have some other info. This is usually the length of the data but can
+ be several other things. Encoding and decoding of this is taken care
+ of by the implementation.
 
- CBOR has two mechanisms for tagging and labeling the data
- values like integers and strings. For example, an integer that
- represents someone's birthday in epoch seconds since Jan 1, 1970
- could be encoded like this:
+ CBOR has two mechanisms for tagging and labeling the data values like
+ integers and strings. For example, an integer that represents
+ someone's birthday in epoch seconds since Jan 1, 1970 could be
+ encoded like this:
 
- - First it is CBOR_MAJOR_TYPE_POSITIVE_INT, the primitive positive
- integer.
- - Next it has a "tag" CBOR_TAG_DATE_EPOCH indicating the integer
- represents a date in the form of the number of seconds since
- Jan 1, 1970.
- - Last it has a string "label" like "BirthDate" indicating
- the meaning of the data.
+ - First it is CBOR_MAJOR_TYPE_POSITIVE_INT (@ref QCBOR_TYPE_INT64),
+ the primitive positive integer.
+
+ - Next it has a "tag" @ref CBOR_TAG_DATE_EPOCH indicating the integer
+ represents a date in the form of the number of seconds since Jan 1,
+ 1970.
+
+ - Last it has a string "label" like "BirthDate" indicating the
+ meaning of the data.
 
  The encoded binary looks like this:
-   a1                      # Map of 1 item
-      69                   # Indicates text string of 9 bytes
-        426972746844617465 # The text "BirthDate"
-     c1                    # Tags next int as epoch date
-        1a                 # Indicates 4 byte integer
-            580d4172       # unsigned integer date 1477263730
 
- Implementors using this API will primarily work with labels. Generally
- tags are only needed for making up new data types. This implementation
- covers most of the data types defined in the RFC using tags. It also,
- allows for the creation of news tags if necessary.
+      a1                      # Map of 1 item
+         69                   # Indicates text string of 9 bytes
+           426972746844617465 # The text "BirthDate"
+        c1                    # Tags next integer as epoch date
+           1a                 # Indicates a 4-byte integer
+               580d4172       # unsigned integer date 1477263730
+
+ Implementors using this API will primarily work with
+ labels. Generally, tags are only needed for making up new data
+ types. This implementation covers most of the data types defined in
+ the RFC using tags. It also, allows for the use of custom tags if
+ necessary.
 
  This implementation explicitly supports labels that are text strings
- and integers. Text strings translate nicely into JSON objects and
- are very readable.  Integer labels are much less readable, but
- can be very compact. If they are in the range of -23 to
- 23 they take up only one byte.
+ and integers. Text strings translate nicely into JSON objects and are
+ very readable.  Integer labels are much less readable but can be very
+ compact. If they are in the range of 0 to 23, they take up only one
+ byte.
 
- CBOR allows a label to be any type of data including an array or
- a map. It is possible to use this API to construct and
- parse such labels, but it is not explicitly supported.
+ CBOR allows a label to be any type of data including an array or a
+ map. It is possible to use this API to construct and parse such
+ labels, but it is not explicitly supported.
 
  A common encoding usage mode is to invoke the encoding twice. First
  with no output buffer to compute the length of the needed output
  buffer. Then the correct sized output buffer is allocated. Last the
  encoder is invoked again, this time with the output buffer.
 
- The double invocation is not required if the max output buffer size
- can be predicted. This is usually possible for simple CBOR structures.
- If the double invocation is implemented, it can be
- in a loop or function as in the example code so that the code doesn't
- have to actually be written twice, saving code size.
+ The double invocation is not required if the maximum output buffer
+ size can be predicted. This is usually possible for simple CBOR
+ structures.  If the double invocation is implemented, it can be in a
+ loop or function as in the example code so that the code doesn't have
+ to actually be written twice, saving code size.
 
  If a buffer too small to hold the encoded output is given, the error
- QCBOR_ERR_BUFFER_TOO_SMALL will be returned. Data will never be
+ @ref QCBOR_ERR_BUFFER_TOO_SMALL will be returned. Data will never be
  written off the end of the output buffer no matter which functions
  here are called or what parameters are passed to them.
 
- The error handling is simple. The only possible errors are trying to
- encode structures that are too large or too complex. There are no
- internal malloc calls so there will be no failures for out of memory.
- Only the final call, QCBOREncode_Finish(), returns an error code.
- Once an error happens, the encoder goes into an error state and calls
- to it will do nothing so the encoding can just go on. An error
- check is not needed after every data item is added.
+ The encoding error handling is simple. The only possible errors are
+ trying to encode structures that are too large or too complex. There
+ are no internal malloc calls so there will be no failures for out of
+ memory.  Only the final call, QCBOREncode_Finish(), returns an error
+ code.  Once an error happens, the encoder goes into an error state
+ and calls to it will do nothing so the encoding can just go on. An
+ error check is not needed after every data item is added.
 
  Encoding generally proceeds by calling QCBOREncode_Init(), calling
- lots of "Add" functions and calling QCBOREncode_Finish(). There
- are many "Add" functions for various data types. The input
- buffers need only to be valid during the "Add" calls. The
- data is copied into the output buf during the "Add" call.
+ lots of @c QCBOREncode_AddXxx() functions and calling
+ QCBOREncode_Finish(). There are many @c QCBOREncode_AddXxx()
+ functions for various data types. The input buffers need only to be
+ valid during the @c QCBOREncode_AddXxx() calls as the data is copied
+ into the output buffer.
 
- There are three `Add` functions for each data type. The first
- / main one for the type is for adding the data item to an array.
- The second one's name ends in `ToMap`, is used for adding
- data items to maps and takes a string
- argument that is its label in the map. The third one ends in
- `ToMapN`, is also used for adding data items to maps, and
+ There are three `Add` functions for each data type. The first / main
+ one for the type is for adding the data item to an array.  The second
+ one's name ends in `ToMap`, is used for adding data items to maps and
+ takes a string argument that is its label in the map. The third one
+ ends in `ToMapN`, is also used for adding data items to maps, and
  takes an integer argument that is its label in the map.
 
  The simplest aggregate type is an array, which is a simple ordered
  set of items without labels the same as JSON arrays. Call
- QCBOREncode_OpenArray() to open a new array, then "Add" to
- put items in the array and then QCBOREncode_CloseArray(). Nesting
- to a limit is allowed.  All opens must be matched by closes or an
- encoding error will be returned.
+ QCBOREncode_OpenArray() to open a new array, then various @c
+ QCBOREncode_AddXxx() functions to put items in the array and then
+ QCBOREncode_CloseArray(). Nesting to the limit @ref
+ QCBOR_MAX_ARRAY_NESTING is allowed.  All opens must be matched by
+ closes or an encoding error will be returned.
 
- The other aggregate type is a map which does use labels. The
- `Add` functions that end in `ToMap` and `ToMapN` are convenient
- ways to add labeled data items to a map. You can also call
- any type of `Add` function once to add a label of any time and
- then call any type of `Add` again to add its value.
+ The other aggregate type is a map which does use labels. The `Add`
+ functions that end in `ToMap` and `ToMapN` are convenient ways to add
+ labeled data items to a map. You can also call any type of `Add`
+ function once to add a label of any time and then call any type of
+ `Add` again to add its value.
 
- Note that when you nest arrays or maps in a map, the nested
- array or map has a label.
+ Note that when you nest arrays or maps in a map, the nested array or
+ map has a label.
 
- Usually it is not necessary to add tags explicitly as most
- tagged types have functions here, but they can be added by
- calling QCBOREncode_AddTag().  There is an IANA registry for new tags that are
- for broad use and standardization as per RFC 7049. It is also
- allowed for protocols to make up new tags in the range above 256.
- Note that even arrays and maps can be tagged.
+ @anchor Tags-Overview
+ Any CBOR data item can be tagged to add semantics, define a new data
+ type or such. Some tags are fully standardized and some are just
+ registered. Others are not registered and used in a proprietary way.
+
+ Encoding and decoding of many of the registered tags is fully
+ implemented by QCBOR. It is also possible to encode and decode tags
+ that are not directly supported.  For many use cases the built-in tag
+ support should be adequate.
+
+ For example, the registered epoch date tag is supported in encoding
+ by QCBOREncode_AddDateEpoch() and in decoding by @ref
+ QCBOR_TYPE_DATE_EPOCH and the @c epochDate member of @ref
+ QCBORItem. This is typical of the built-in tag support. There is an
+ API to encode data for it and a @c QCBOR_TYPE_XXX when it is decoded.
+
+ Tags are registered in the [IANA CBOR Tags Registry]
+ (https://www.iana.org/assignments/cbor-tags/cbor-tags.xhtml). There
+ are roughly three options to create a new tag. First, a public
+ specification can be created and the new tag registered with IANA.
+ This is the most formal. Second, the new tag can be registered with
+ IANA with just a short description rather than a full specification.
+ These tags must be greater than 256. Third, a tag can be used without
+ any IANA registration, though the registry should be checked to see
+ that the new value doesn't collide with one that is registered. The
+ value of these tags must be 256 or larger.
+
+ The encoding side of tags not built-in is handled by
+ QCBOREncode_AddTag() and is relatively simple. Tag decoding is more
+ complex and mainly handled by QCBORDecode_GetNext(). Decoding of the
+ structure of tagged data not built-in (if there is any) has to be
+ implemented by the caller.
 
  Summary Limits of this implementation:
  - The entire encoded CBOR must fit into contiguous memory.
- - Max size of encoded / decoded CBOR data is UINT32_MAX (4GB).
+ - Max size of encoded / decoded CBOR data is @c UINT32_MAX (4GB).
  - Max array / map nesting level when encoding / decoding is
-   QCBOR_MAX_ARRAY_NESTING (this is typically 15).
+   @ref QCBOR_MAX_ARRAY_NESTING (this is typically 15).
  - Max items in an array or map when encoding / decoding is
-   QCBOR_MAX_ITEMS_IN_ARRAY (typically 65,536).
+   @ref QCBOR_MAX_ITEMS_IN_ARRAY (typically 65,536).
  - Does not support encoding indefinite lengths (decoding is supported).
  - Does not directly support some tagged types: decimal fractions, big floats
- - Does not directly support labels in maps other than text strings and ints.
- - Does not directly support int labels greater than INT64_MAX
- - Epoch dates limited to INT64_MAX (+/- 292 billion years)
- - Tags on labels are ignored during decoding
+ - Does not directly support labels in maps other than text strings and integers.
+ - Does not directly support integer labels greater than @c INT64_MAX.
+ - Epoch dates limited to @c INT64_MAX (+/- 292 billion years).
+ - Tags on labels are ignored during decoding.
+ - Works only on 32- and 64-bit CPUs (modifications could make it work
+   on 16-bit CPUs).
 
- This implementation is intended to run on 32 and 64-bit CPUs. Minor
- modifications are needed for it to work on 16-bit CPUs.
-
- The public interface uses size_t for all lengths. Internally the
+ The public interface uses @c size_t for all lengths. Internally the
  implementation uses 32-bit lengths by design to use less memory and
- fit structures on the stack. This limits the encoded
- CBOR it can work with to size UINT32_MAX (4GB) which should be
- enough.
+ fit structures on the stack. This limits the encoded CBOR it can work
+ with to size @c UINT32_MAX (4GB) which should be enough.
 
- This implementation assumes two's compliment integer
- machines. Stdint.h also requires this. It of course would be easy to
- fix this implementation for another integer representation, but all
- modern machines seem to be two's compliment.
+ This implementation assumes two's compliment integer machines. @c
+ <stdint.h> also requires this. It is possible to modify this
+ implementation for another integer representation, but all modern
+ machines seem to be two's compliment.
 
  */
 
 
 /**
- The maximum number of items in a single array or map when encoding of decoding.
+ The maximum number of items in a single array or map when encoding of
+ decoding.
 */
-// -1 is because the value UINT16_MAX is used to track indefinite length arraysUINT16_MAX
+// -1 is because the value UINT16_MAX is used to track indefinite-length arrays
 #define QCBOR_MAX_ITEMS_IN_ARRAY (UINT16_MAX-1)
 
 /**
  The maximum nesting of arrays and maps when encoding or decoding. The
- error QCBOR_ERR_ARRAY_NESTING_TOO_DEEP will be returned on encoding
- of decoding if it is exceeded
+ error @ref QCBOR_ERR_ARRAY_NESTING_TOO_DEEP will be returned on
+ encoding of decoding if it is exceeded.
 */
 #define QCBOR_MAX_ARRAY_NESTING  QCBOR_MAX_ARRAY_NESTING1
 
 /**
- The maximum number of tags that can be in QCBORTagListIn and passed to
+ The maximum number of tags that can be in @ref QCBORTagListIn and passed to
  QCBORDecode_SetCallerConfiguredTagList()
  */
 #define QCBOR_MAX_CUSTOM_TAGS    16
 
 
+/**
+ Error codes returned by QCBOR Encoder and Decoder.
+ */
 typedef enum {
    /** The encode or decode completely correctly. */
    QCBOR_SUCCESS = 0,
 
-   /** The buffer provided for the encoded output when doing encoding was
-       too small and the encoded output will not fit. Also, when the buffer
-       given to QCBORDecode_SetMemPool() is too small. */
-   QCBOR_ERR_BUFFER_TOO_SMALL,
+   /** The buffer provided for the encoded output when doing encoding
+       was too small and the encoded output will not fit. Also, when
+       the buffer given to QCBORDecode_SetMemPool() is too small. */
+   QCBOR_ERR_BUFFER_TOO_SMALL = 1,
 
-   /** During encoding or decoding, the array or map nesting was deeper than
-    this implementation can handle. Note that in the interest of code size
-    and memory use, this implementation has a hard limit on array nesting. The
-    limit is defined as the constant QCBOR_MAX_ARRAY_NESTING. */
-   QCBOR_ERR_ARRAY_NESTING_TOO_DEEP,
+   /** During encoding or decoding, the array or map nesting was
+       deeper than this implementation can handle. Note that in the
+       interest of code size and memory use, this implementation has a
+       hard limit on array nesting. The limit is defined as the
+       constant @ref QCBOR_MAX_ARRAY_NESTING. */
+   QCBOR_ERR_ARRAY_NESTING_TOO_DEEP = 2,
 
-   /** During decoding or encoding, the array or map had too many items in it.
-       This limit QCBOR_MAX_ITEMS_IN_ARRAY, typically 65,535. */
-   QCBOR_ERR_ARRAY_TOO_LONG,
+   /** During decoding or encoding, the array or map had too many
+       items in it.  This limit @ref QCBOR_MAX_ITEMS_IN_ARRAY,
+       typically 65,535. */
+   QCBOR_ERR_ARRAY_TOO_LONG = 3,
 
-   /** During encoding, more arrays or maps were closed than opened. This is a
-       coding error on the part of the caller of the encoder. */
-   QCBOR_ERR_TOO_MANY_CLOSES,
+   /** During encoding, more arrays or maps were closed than
+       opened. This is a coding error on the part of the caller of the
+       encoder. */
+   QCBOR_ERR_TOO_MANY_CLOSES = 4,
 
-   /** During decoding, some CBOR construct was encountered that this decoder
-        doesn't support, primarily this is the reserved additional info values,
-        28 through 30. */
-   QCBOR_ERR_UNSUPPORTED,
+   /** During decoding, some CBOR construct was encountered that this
+       decoder doesn't support, primarily this is the reserved
+       additional info values, 28 through 30. */
+   QCBOR_ERR_UNSUPPORTED = 5,
 
-   /** During decoding, hit the end of the given data to decode. For example,
-       a byte string of 100 bytes was expected, but the end of the input was
-       hit before finding those 100 bytes.  Corrupted CBOR input will often
-       result in this error. */
-   QCBOR_ERR_HIT_END,
+   /** During decoding, hit the end of the given data to decode. For
+       example, a byte string of 100 bytes was expected, but the end
+       of the input was hit before finding those 100 bytes.  Corrupted
+       CBOR input will often result in this error. */
+   QCBOR_ERR_HIT_END = 6,
 
-   /** During encoding, the length of the encoded CBOR exceeded UINT32_MAX.
-     */
-   QCBOR_ERR_BUFFER_TOO_LARGE,
+   /** During encoding, the length of the encoded CBOR exceeded @c
+       UINT32_MAX. */
+   QCBOR_ERR_BUFFER_TOO_LARGE = 7,
 
-   /** During decoding, an integer smaller than INT64_MIN was received (CBOR
-       can represent integers smaller than INT64_MIN, but C cannot). */
-   QCBOR_ERR_INT_OVERFLOW,
+   /** During decoding, an integer smaller than INT64_MIN was received
+       (CBOR can represent integers smaller than INT64_MIN, but C
+       cannot). */
+   QCBOR_ERR_INT_OVERFLOW = 8,
 
-   /** During decoding, the label for a map entry is bad. What causes this
-       error depends on the decoding mode. */
-   QCBOR_ERR_MAP_LABEL_TYPE,
+   /** During decoding, the label for a map entry is bad. What causes
+       this error depends on the decoding mode. */
+   QCBOR_ERR_MAP_LABEL_TYPE = 9,
 
-   /** During encoding or decoding, the number of array or map opens was not
-       matched by the number of closes. */
-   QCBOR_ERR_ARRAY_OR_MAP_STILL_OPEN,
+   /** During encoding or decoding, the number of array or map opens
+       was not matched by the number of closes. */
+   QCBOR_ERR_ARRAY_OR_MAP_STILL_OPEN = 10,
 
-   /** During encoding, the simple value is not between CBOR_SIMPLEV_FALSE
-       and CBOR_SIMPLEV_UNDEF. */
-   QCBOR_ERR_BAD_SIMPLE,
+   /** During decoding, a date greater than +- 292 billion years from
+       Jan 1 1970 encountered during parsing. */
+   QCBOR_ERR_DATE_OVERFLOW = 11,
 
-   /** During decoding, a date greater than +- 292 billion years from Jan 1
-       1970 encountered during parsing. */
-   QCBOR_ERR_DATE_OVERFLOW,
+   /** During decoding, the CBOR is not valid, primarily a simple type
+      is encoded in a prohibited way. */
+   QCBOR_ERR_BAD_TYPE_7 = 12,
 
-   /** During decoding, the CBOR is not valid, primarily a simple type is encoded in
-      a prohibited way. */
-   QCBOR_ERR_INVALID_CBOR,
+   /** Optional tagging that doesn't make sense (an integer is tagged
+       as a date string) or can't be handled. */
+   QCBOR_ERR_BAD_OPT_TAG = 13,
 
-   /** Optional tagging that doesn't make sense (an int is tagged as a
-       date string) or can't be handled. */
-   QCBOR_ERR_BAD_OPT_TAG,
+   /** Returned by QCBORDecode_Finish() if all the inputs bytes have
+       not been consumed. */
+   QCBOR_ERR_EXTRA_BYTES = 14,
 
-   /** Returned by QCBORDecode_Finish() if all the inputs bytes have not
-       been consumed. */
-   QCBOR_ERR_EXTRA_BYTES,
+   /** During encoding, @c QCBOREncode_CloseXxx() called with a
+       different type than is currently open. */
+   QCBOR_ERR_CLOSE_MISMATCH = 15,
 
-   /** During encoding, QCBOREncode_Close() call with a different type than
-       is currently open. */
-   QCBOR_ERR_CLOSE_MISMATCH,
+   /** Unable to decode an indefinite-length string because no string
+       allocator was configured. See QCBORDecode_SetMemPool() or
+       QCBORDecode_SetUpAllocator(). */
+   QCBOR_ERR_NO_STRING_ALLOCATOR = 16,
 
-   /** Unable to decode an indefinite length string because no string
-       allocator was configured. */
-   QCBOR_ERR_NO_STRING_ALLOCATOR,
+   /** One of the chunks in an indefinite-length string is not of the
+       type of the start of the string. */
+   QCBOR_ERR_INDEFINITE_STRING_CHUNK = 17,
 
-   /** One of the chunks in an indefinite length string is not of the type of
-       the string. */
-   QCBOR_ERR_INDEFINITE_STRING_CHUNK,
+   /** Error allocating space for a string, usually for an
+       indefinite-length string. */
+   QCBOR_ERR_STRING_ALLOCATE = 18,
 
-   /** Error allocating space for a string, usually for an indefinite length
-       string. */
-   QCBOR_ERR_STRING_ALLOCATE,
+   /** During decoding, a break occurred outside an indefinite-length
+       item. */
+   QCBOR_ERR_BAD_BREAK = 19,
 
-   /** During decoding, a break occurred outside an indefinite length item. */
-   QCBOR_ERR_BAD_BREAK,
-
-   /** During decoding, too many tags in the caller-configured tag list, or not
-       enough space in QCBORTagListOut. */
-   QCBOR_ERR_TOO_MANY_TAGS,
-
-   /** Returned by QCBORDecode_SetMemPool() when xx is too small. This should
-       never happen on a machine with 64-bit or smaller pointers. Fixing
-       it is probably by increasing QCBOR_DECODE_MIN_MEM_POOL_SIZE. */
-   QCBOR_ERR_MEM_POOL_INTERNAL
+   /** During decoding, too many tags in the caller-configured tag
+       list, or not enough space in @ref QCBORTagListOut. */
+   QCBOR_ERR_TOO_MANY_TAGS = 20,
 
 } QCBORError;
 
 
+/**
+ The decode mode options.
+ */
 typedef enum {
    /** See QCBORDecode_Init() */
    QCBOR_DECODE_MODE_NORMAL = 0,
@@ -682,43 +765,54 @@
 
 
 /* Do not renumber these. Code depends on some of these values. */
-/** The type is unknown, unset or invalid */
+/** The data type is unknown, unset or invalid. */
 #define QCBOR_TYPE_NONE           0
-/** Type for an integer that decoded either between INT64_MIN and INT32_MIN or INT32_MAX and INT64_MAX; val.int64 */
+/** Type for an integer that decoded either between @c INT64_MIN and
+    @c INT32_MIN or @c INT32_MAX and @c INT64_MAX. Data is in member
+    @c val.int64. */
 #define QCBOR_TYPE_INT64          2
-/** Type for an integer that decoded to a more than INT64_MAX and UINT64_MAX; val.uint64 */
+/** Type for an integer that decoded to a more than @c INT64_MAX and
+     @c UINT64_MAX.  Data is in member @c val.uint64. */
 #define QCBOR_TYPE_UINT64         3
-/** Type for an array. The number of items in the array is in val.uCount. */
+/** Type for an array. The number of items in the array is in @c
+    val.uCount. */
 #define QCBOR_TYPE_ARRAY          4
-/** Type for a map; number of items in map is in val.uCount */
+/** Type for a map; number of items in map is in @c val.uCount. */
 #define QCBOR_TYPE_MAP            5
-/** Type for a buffer full of bytes. Data is in val.string. */
+/** Type for a buffer full of bytes. Data is in @c val.string. */
 #define QCBOR_TYPE_BYTE_STRING    6
-/** Type for a UTF-8 string. It is not NULL terminated. Data is in val.string.  */
+/** Type for a UTF-8 string. It is not NULL-terminated. Data is in @c
+    val.string.  */
 #define QCBOR_TYPE_TEXT_STRING    7
-/** Type for a positive big number. Data is in val.bignum, a pointer and a length. */
-#define QCBOR_TYPE_POSBIGNUM     9
-/** Type for a negative big number. Data is in val.bignum, a pointer and a length. */
+/** Type for a positive big number. Data is in @c val.bignum, a
+    pointer and a length. */
+#define QCBOR_TYPE_POSBIGNUM      9
+/** Type for a negative big number. Data is in @c val.bignum, a
+    pointer and a length. */
 #define QCBOR_TYPE_NEGBIGNUM     10
-/** Type for RFC 3339 date string, possibly with time zone. Data is in val.dateString */
+/** Type for [RFC 3339] (https://tools.ietf.org/html/rfc3339) date
+    string, possibly with time zone. Data is in @c val.dateString */
 #define QCBOR_TYPE_DATE_STRING   11
-/** Type for integer seconds since Jan 1970 + floating point fraction. Data is in val.epochDate */
+/** Type for integer seconds since Jan 1970 + floating point
+    fraction. Data is in @c val.epochDate */
 #define QCBOR_TYPE_DATE_EPOCH    12
-/** A simple type that this CBOR implementation doesn't know about; Type is in val.uSimple. */
+/** A simple type that this CBOR implementation doesn't know about;
+    Type is in @c val.uSimple. */
 #define QCBOR_TYPE_UKNOWN_SIMPLE 13
-/** Type for the simple value false; nothing more; nothing in val union. */
+/** Type for the value false. */
 #define QCBOR_TYPE_FALSE         20
-/** Type for the simple value true; nothing more; nothing in val union. */
+/** Type for the value true. */
 #define QCBOR_TYPE_TRUE          21
-/** Type for the simple value null; nothing more; nothing in val union. */
+/** Type for the value null. */
 #define QCBOR_TYPE_NULL          22
-/** Type for the simple value undef; nothing more; nothing in val union. */
+/** Type for the value undef. */
 #define QCBOR_TYPE_UNDEF         23
-/** Type for a floating point number. Data is in val.float. */
+/** Type for a floating-point number. Data is in @c val.float. */
 #define QCBOR_TYPE_FLOAT         26
-/** Type for a double floating point number. Data is in val.double. */
+/** Type for a double floating-point number. Data is in @c val.double. */
 #define QCBOR_TYPE_DOUBLE        27
-/** For QCBOR_DECODE_MODE_MAP_AS_ARRAY decode mode, a map that is being traversed as an array. See QCBORDecode_Init() */
+/** For @ref QCBOR_DECODE_MODE_MAP_AS_ARRAY decode mode, a map that is
+     being traversed as an array. See QCBORDecode_Init() */
 #define QCBOR_TYPE_MAP_AS_ARRAY  32
 
 #define QCBOR_TYPE_BREAK         31 // Used internally; never returned
@@ -729,154 +823,186 @@
 
 /*
  Approx Size of this:
-   8 + 8 + 1 + 1 + 1 + (1 padding) + (4 padding on 64-bit machine) = 24 for first part (20 on a 32-bit machine)
+   8 + 8 + 1 + 1 + 1 + (1 padding) + (4 padding) = 24 for first part
+                                                  (20 on a 32-bit machine)
    16 bytes for the val union
    16 bytes for label union
    total = 56 bytes (52 bytes on 32-bit machine)
  */
 
 /**
- QCBORItem holds the type, value and other info for a decoded item returned by GetNextItem().
+ The main data structure that holds the type, value and other info for
+ a decoded item returned by QCBORDecode_GetNext() and
+ QCBORDecode_GetNextWithTags().
  */
 typedef struct _QCBORItem {
-   uint8_t  uDataType;     /** Tells what element of the val union to use. One of QCBOR_TYPE_XXXX */
-   uint8_t  uNestingLevel; /** How deep the nesting from arrays and maps are. 0 is the top level with no arrays or maps entered */
-   uint8_t  uLabelType;    /** Tells what element of the label union to use */
-   uint8_t  uDataAlloc;    /** 1 if allocated with string allocator, 0 if not. See QCBORDecode_MakeMallocStringAllocator() */
-   uint8_t  uLabelAlloc;   /** Like uDataAlloc, but for label */
-   uint8_t  uNextNestLevel; /** If not equal to uNestingLevel, this item closed out at least one map/array */
+   /** Tells what element of the @c val union to use. One of @c
+       QCBOR_TYPE_XXXX */
+   uint8_t  uDataType;
+   /** How deep the nesting from arrays and maps are. 0 is the top
+       level with no arrays or maps entered. */
+   uint8_t  uNestingLevel;
+    /** Tells what element of the label union to use. */
+   uint8_t  uLabelType;
+   /** 1 if allocated with string allocator, 0 if not. See
+       QCBORDecode_SetMemPool() or QCBORDecode_SetUpAllocator() */
+   uint8_t  uDataAlloc;
+   /** Like @c uDataAlloc, but for label. */
+   uint8_t  uLabelAlloc;
+   /** If not equal to @c uNestingLevel, this item closed out at least
+       one map/array */
+   uint8_t  uNextNestLevel;
 
+   /** The union holding the item's value. Select union member based
+       on @c uDataType */
    union {
-      int64_t     int64;      /** The value for uDataType QCBOR_TYPE_INT64 */
-      uint64_t    uint64;     /** The value for uDataType QCBOR_TYPE_UINT64 */
-
-      UsefulBufC  string;     /** The value for uDataType QCBOR_TYPE_BYTE_STRING and QCBOR_TYPE_TEXT_STRING */
-      uint16_t    uCount;     /** The "value" for uDataType QCBOR_TYPE_ARRAY or QCBOR_TYPE_MAP -- the number of items in the array or map
-                                  UINT16_MAX when decoding indefinite lengths maps and arrays. */
-      double      dfnum;      /** The value for uDataType QCBOR_TYPE_DOUBLE */
+      /** The value for @c uDataType @ref QCBOR_TYPE_INT64. */
+      int64_t     int64;
+      /** The value for uDataType @ref QCBOR_TYPE_UINT64. */
+      uint64_t    uint64;
+      /** The value for @c uDataType @ref QCBOR_TYPE_BYTE_STRING and
+          @ref QCBOR_TYPE_TEXT_STRING. */
+      UsefulBufC  string;
+      /** The "value" for @c uDataType @ref QCBOR_TYPE_ARRAY or @ref
+          QCBOR_TYPE_MAP -- the number of items in the array or map.
+          It is @c UINT16_MAX when decoding indefinite-lengths maps
+          and arrays. */
+      uint16_t    uCount;
+      /** The value for @c uDataType @ref QCBOR_TYPE_DOUBLE. */
+      double      dfnum;
+      /** The value for @c uDataType @ref QCBOR_TYPE_DATE_EPOCH. */
       struct {
          int64_t  nSeconds;
          double   fSecondsFraction;
-      } epochDate;            /** The value for uDataType QCBOR_TYPE_DATE_EPOCH */
-      UsefulBufC  dateString; /** The value for uDataType QCBOR_TYPE_DATE_STRING */
-      UsefulBufC  bigNum;     /** The value for uDataType QCBOR_TYPE_BIGNUM */
-      uint8_t     uSimple;    /** The integer value for unknown simple types */
-      uint64_t    uTagV;
+      } epochDate;
+      /** The value for @c uDataType @ref QCBOR_TYPE_DATE_STRING. */
+      UsefulBufC  dateString;
+      /** The value for @c uDataType @ref QCBOR_TYPE_POSBIGNUM and
+           @ref QCBOR_TYPE_NEGBIGNUM. */
+      UsefulBufC  bigNum;
+      /** The integer value for unknown simple types. */
+      uint8_t     uSimple;
+      uint64_t    uTagV;  // Used internally during decoding
 
-   } val;  /** The union holding the item's value. Select union member based on uDataType */
+   } val;
 
+   /** Union holding the different label types selected based on @c
+       uLabelType */
    union {
-      UsefulBufC  string;  /** The label for uLabelType QCBOR_TYPE_BYTE_STRING and QCBOR_TYPE_TEXT_STRING */
-      int64_t     int64;   /** The label for uLabelType for QCBOR_TYPE_INT64 */
-      uint64_t    uint64;  /** The label for uLabelType for QCBOR_TYPE_UINT64 */
-   } label; /** Union holding the different label types selected based on uLabelType */
+      /** The label for @c uLabelType @ref QCBOR_TYPE_BYTE_STRING and
+          @ref QCBOR_TYPE_TEXT_STRING */
+      UsefulBufC  string;
+      /** The label for @c uLabelType for @ref QCBOR_TYPE_INT64 */
+      int64_t     int64;
+      /** The label for @c uLabelType for @ref QCBOR_TYPE_UINT64 */
+      uint64_t    uint64;
+   } label;
 
-   uint64_t uTagBits; /** Bit indicating which tags (major type 6) on this item.  */
+   /** Bit indicating which tags (major type 6) on this item. See
+       QCBORDecode_IsTagged().  */
+   uint64_t uTagBits;
 
 } QCBORItem;
 
 
 
 /**
-  \brief The type defining what a string allocator function must do.
+  @brief The type defining what a string allocator function must do.
 
- * \param[in] pAllocateCxt  Pointer to context for the particular
-                             allocator implementation What is in the
-                             context is dependent on how a particular
-                             string allocator works. Typically, it
-                             will contain a pointer to the memory pool
-                             and some booking keeping data.
- \param[in] pOldMem          Points to some memory allocated by the
-                             allocator that is either to be freed or
-                             to be reallocated to be larger. It is
-                             NULL for new allocations and when call as
-                             a destructor to clean up the whole
-                             allocation.
- \param[in] uNewSize         Size of memory to be allocated or new
-                             size of chunk to be reallocated. Zero for
-                             a new allocation or when called as a
-                             destructor.
+  @param[in] pAllocateCxt  Pointer to context for the particular
+                            allocator implementation What is in the
+                            context is dependent on how a particular
+                            string allocator works. Typically, it
+                            will contain a pointer to the memory pool
+                            and some booking keeping data.
+ @param[in] pOldMem         Points to some memory allocated by the
+                            allocator that is either to be freed or
+                            to be reallocated to be larger. It is
+                            @c NULL for new allocations and when called as
+                            a destructor to clean up the whole
+                            allocation.
+ @param[in] uNewSize        Size of memory to be allocated or new
+                            size of chunk to be reallocated. Zero for
+                            a new allocation or when called as a
+                            destructor.
 
- \return   Either the allocated buffer is returned, or \c
-           NULLUsefulBufC. \c NULLUsefulBufC is returned on a failed
-           allocation or in the two cases where there is nothing to
+ @return   Either the allocated buffer is returned, or @ref
+           NULLUsefulBufC. @ref NULLUsefulBufC is returned on a failed
+           allocation and in the two cases where there is nothing to
            return.
 
  This is called in one of four modes:
 
- Allocate -- \c uNewSize is the amount to allocate. \c pOldMem is \c
+ Allocate -- @c uNewSize is the amount to allocate. @c pOldMem is @c
  NULL.
 
- Free -- \c uNewSize is 0. \c pOldMem points to the memory to be
+ Free -- @c uNewSize is 0. @c pOldMem points to the memory to be
  freed.  When the decoder calls this, it will always be the most
  recent block that was either allocated or reallocated.
 
- Reallocate -- \c pOldMem is the block to reallocate. \c uNewSize is
+ Reallocate -- @c pOldMem is the block to reallocate. @c uNewSize is
  its new size.  When the decoder calls this, it will always be the
  most recent block that was either allocated or reallocated.
 
- Destruct -- \c pOldMem is NULL and \c uNewSize is 0. This is called
+ Destruct -- @c pOldMem is @c NULL and @c uNewSize is 0. This is called
  when the decoding is complete by QCBORDecode_Finish(). Usually the
  strings allocated by a string allocator are in use after the decoding
  is completed so this usually will not free those strings. Many string
  allocators will not need to do anything in this mode.
 
- The strings allocated by this will have \c uDataAlloc set to true in
- the \ref QCBORItem when they are returned. The user of the strings
+ The strings allocated by this will have @c uDataAlloc set to true in
+ the @ref QCBORItem when they are returned. The user of the strings
  will have to free them. How they free them, depends on the string
  allocator.
 
  If QCBORDecode_SetMemPool() is called, the internal MemPool will be
- used. It has it's own internal implementation of this function, so
+ used. It has its own internal implementation of this function, so
  one does not need to be implemented.
-
  */
 typedef UsefulBuf (* QCBORStringAllocate)(void *pAllocateCxt, void *pOldMem, size_t uNewSize);
 
 
 /**
- This only matters if you use the built-in string allocator
- by settig it up with QCBORDecode_SetMemPool(). This is
- the size of the overhead needed needed by
- QCBORDecode_SetMemPool(). The amount of memory
- available for decoded strings will be the
- size of the buffer given to QCBORDecode_SetMemPool() less
- this amount.
+ This only matters if you use the built-in string allocator by setting
+ it up with QCBORDecode_SetMemPool(). This is the size of the overhead
+ needed by QCBORDecode_SetMemPool(). The amount of memory available
+ for decoded strings will be the size of the buffer given to
+ QCBORDecode_SetMemPool() less this amount.
 
- If you write your own
- string allocator or use the separately available malloc
- based string allocator, this size will not apply
+ If you write your own string allocator or use the separately
+ available malloc based string allocator, this size will not apply.
  */
 #define QCBOR_DECODE_MIN_MEM_POOL_SIZE 8
 
 
 /**
- This is used to tell the decoder about tags that it should
- record in uTagBits in QCBORItem beyond the built-in
- tags. puTags points to an
- array of uint64_t integers that are the tags. uNumTags
- is the number of integers in the array. The maximum
- size is QCBOR_MAX_CUSTOM_TAGS.  See QCBORDecode_IsTagged()
- and QCBORDecode_SetCallerAddedTagMap().
+ This is used by QCBORDecode_SetCallerConfiguredTagList() to set a
+ list of tags beyond the built-in ones.
+
+ See also QCBORDecode_GetNext() for general description of tag
+ decoding.
  */
 typedef struct {
+   /** The number of tags in the @c puTags. The maximum size is @ref
+       QCBOR_MAX_CUSTOM_TAGS. */
    uint8_t uNumTags;
+   /** An array of tags to add to recognize in addition to the
+       built-in ones. */
    const uint64_t *puTags;
 } QCBORTagListIn;
 
 
 /**
  This is for QCBORDecode_GetNextWithTags() to be able to return the
- full list of tags on an item. It not needed for most CBOR protocol
+ full list of tags on an item. It is not needed for most CBOR protocol
  implementations. Its primary use is for pretty-printing CBOR or
  protocol conversion to another format.
 
- On input, puTags points to a buffer to be filled in
- and uNumAllocated is the number of uint64_t values
- in the buffer.
+ On input, @c puTags points to a buffer to be filled in and
+ uNumAllocated is the number of @c uint64_t values in the buffer.
 
- On output the buffer contains the tags for the item.
- uNumUsed tells how many there are.
+ On output the buffer contains the tags for the item.  @c uNumUsed
+ tells how many there are.
  */
 typedef struct {
    uint8_t uNumUsed;
@@ -887,38 +1013,41 @@
 
 /**
  QCBOREncodeContext is the data type that holds context for all the
- encoding functions. It is less than 200 bytes, so it can go on
- the stack. The contents are opaque, and the caller should not access
- any internal items.  A context may be re used serially as long as
- it is re initialized.
+ encoding functions. It is less than 200 bytes, so it can go on the
+ stack. The contents are opaque, and the caller should not access
+ internal members.  A context may be re used serially as long as it is
+ re initialized.
  */
 typedef struct _QCBOREncodeContext QCBOREncodeContext;
 
 
 /**
- Initialize the the encoder to prepare to encode some CBOR.
+ Initialize the encoder to prepare to encode some CBOR.
 
- @param[in,out]  pCtx    The encoder context to initialize.
- @param[in]      Storage The buffer into which this encoded result will be placed.
+ @param[in,out]  pCtx     The encoder context to initialize.
+ @param[in]      Storage  The buffer into which this encoded result
+                          will be placed.
 
  Call this once at the start of an encoding of a CBOR structure. Then
- call the various QCBOREncode_AddXXX() functions to add the data
+ call the various @c QCBOREncode_AddXxx() functions to add the data
  items. Then call QCBOREncode_Finish().
 
- The maximum output buffer is UINT32_MAX (4GB). This is not a practical
- limit in any way and reduces the memory needed by the implementation.
- The error QCBOR_ERR_BUFFER_TOO_LARGE will be returned by QCBOR_Finish()
- if a larger buffer length is passed in.
+ The maximum output buffer is @c UINT32_MAX (4GB). This is not a
+ practical limit in any way and reduces the memory needed by the
+ implementation.  The error @ref QCBOR_ERR_BUFFER_TOO_LARGE will be
+ returned by QCBOREncode_Finish() if a larger buffer length is passed
+ in.
 
- If this is called with pBuf as NULL and uBufLen a large value like
- UINT32_MAX, all the QCBOREncode_AddXXXX() functions and
- QCBORE_Encode_Finish() can still be called. No data will be encoded,
- but the length of what would be encoded will be calculated. The
- length of the encoded structure will be handed back in the call to
- QCBOREncode_Finish(). You can then allocate a buffer of that size
- and call all the encoding again, this time to fill in the buffer.
+ If this is called with @c Storage.ptr as @c NULL and @c Storage.len a
+ large value like @c UINT32_MAX, all the QCBOREncode_AddXxx()
+ functions and QCBOREncode_Finish() can still be called. No data will
+ be encoded, but the length of what would be encoded will be
+ calculated. The length of the encoded structure will be handed back
+ in the call to QCBOREncode_Finish(). You can then allocate a buffer
+ of that size and call all the encoding again, this time to fill in
+ the buffer.
 
- A QCBORContext can be reused over and over as long as
+ A @ref QCBOREncodeContext can be reused over and over as long as
  QCBOREncode_Init() is called.
  */
 void QCBOREncode_Init(QCBOREncodeContext *pCtx, UsefulBuf Storage);
@@ -927,33 +1056,35 @@
 /**
  @brief  Add a signed 64-bit integer to the encoded output.
 
- @param[in] pCtx      The encoding context to add the integer to.
- @param[in] nNum      The integer to add.
+ @param[in] pCtx   The encoding context to add the integer to.
+ @param[in] nNum   The integer to add.
 
  The integer will be encoded and added to the CBOR output.
 
  This function figures out the size and the sign and encodes in the
- correct minimal CBOR. Specifically, it will select CBOR major type 0 or 1
- based on sign and will encode to 1, 2, 4 or 8 bytes depending on the
- value of the integer. Values less than 24 effectively encode to one
- byte because they are encoded in with the CBOR major type.  This is
- a neat and efficient characteristic of CBOR that can be taken
+ correct minimal CBOR. Specifically, it will select CBOR major type 0
+ or 1 based on sign and will encode to 1, 2, 4 or 8 bytes depending on
+ the value of the integer. Values less than 24 effectively encode to
+ one byte because they are encoded in with the CBOR major type.  This
+ is a neat and efficient characteristic of CBOR that can be taken
  advantage of when designing CBOR-based protocols. If integers like
  tags can be kept between -23 and 23 they will be encoded in one byte
  including the major type.
 
- If you pass a smaller int, say an int16_t or a small value, say 100,
- the encoding will still be CBOR's most compact that can represent the
- value.  For example, CBOR always encodes the value 0 as one byte,
- 0x00. The representation as 0x00 includes identification of the type
- as an integer too as the major type for an integer is 0. See RFC 7049
- Appendix A for more examples of CBOR encoding. This compact encoding
- is also canonical CBOR as per section 3.9 in RFC 7049.
+ If you pass a smaller int, say an @c int16_t or a small value, say
+ 100, the encoding will still be CBOR's most compact that can
+ represent the value.  For example, CBOR always encodes the value 0 as
+ one byte, 0x00. The representation as 0x00 includes identification of
+ the type as an integer too as the major type for an integer is 0. See
+ [RFC 7049] (https://tools.ietf.org/html/rfc7049) Appendix A for more
+ examples of CBOR encoding. This compact encoding is also canonical
+ CBOR as per section 3.9 in RFC 7049.
 
- There are no functions to add int16_t or int32_t because they are
- not necessary because this always encodes to the smallest number
+ There are no functions to add @c int16_t or @c int32_t because they
+ are not necessary because this always encodes to the smallest number
  of bytes based on the value (If this code is running on a 32-bit
- machine having a way to add 32-bit integers would reduce code size some).
+ machine having a way to add 32-bit integers would reduce code size
+ some).
 
  If the encoding context is in an error state, this will do
  nothing. If an error occurs when adding this integer, the internal
@@ -972,14 +1103,14 @@
 /**
  @brief  Add an unsigned 64-bit integer to the encoded output.
 
- @param[in] pCtx      The encoding context to add the integer to.
- @param[in] uNum      The integer to add.
+ @param[in] pCtx  The encoding context to add the integer to.
+ @param[in] uNum  The integer to add.
 
  The integer will be encoded and added to the CBOR output.
 
- The only reason so use this function is for integers larger than
- INT64_MAX and smaller than UINT64_MAX. Otherwise QCBOREncode_AddInt64()
- will work fine.
+ The only reason so use this function is for integers larger than @c
+ INT64_MAX and smaller than @c UINT64_MAX. Otherwise
+ QCBOREncode_AddInt64() will work fine.
 
  Error handling is the same as for QCBOREncode_AddInt64().
  */
@@ -991,20 +1122,19 @@
 
 
 /**
+ @brief  Add a UTF-8 text string to the encoded output.
 
- @brief  Add a UTF-8 text string to the encoded output
+ @param[in] pCtx   The context to initialize.
+ @param[in] Text   Pointer and length of text to add.
 
- @param[in] pCtx     The context to initialize.
- @param[in] Text    Pointer and length of text to add.
+ The text passed in must be unencoded UTF-8 according to [RFC 3629]
+ (https://tools.ietf.org/html/rfc3629). There is no NULL
+ termination. The text is added as CBOR major type 3.
 
- The text passed in must be unencoded UTF-8 according to RFC
- 3629. There is no NULL termination. The text is added as CBOR
- major type 3.
+ If called with @c nBytesLen equal to 0, an empty string will be
+ added. When @c nBytesLen is 0, @c pBytes may be @c NULL.
 
- If called with nBytesLen equal to 0, an empty string will be
- added. When nBytesLen is 0, pBytes may be NULL.
-
- Note that the restriction of the buffer length to an uint32_t is
+ Note that the restriction of the buffer length to a @c uint32_t is
  entirely intentional as this encoder is not capable of encoding
  lengths greater. This limit to 4GB for a text string should not be a
  problem.
@@ -1019,7 +1149,7 @@
 
 
 /**
- @brief  Add a UTF-8 text string to the encoded output
+ @brief  Add a UTF-8 text string to the encoded output.
 
  @param[in] pCtx      The context to initialize.
  @param[in] szString  Null-terminated text to add.
@@ -1034,23 +1164,23 @@
 
 
 /**
- @brief  Add a floating-point number to the encoded output
+ @brief  Add a floating-point number to the encoded output.
 
- @param[in] pCtx      The encoding context to add the float to.
- @param[in] dNum      The double precision number to add.
+ @param[in] pCtx  The encoding context to add the float to.
+ @param[in] dNum  The double precision number to add.
 
  This outputs a floating-point number with CBOR major type 7.
 
- This will selectively encode the double-precision floating point
+ This will selectively encode the double-precision floating-point
  number as either double-precision, single-precision or
  half-precision. It will always encode infinity, NaN and 0 has half
  precision. If no precision will be lost in the conversion to
- half-precision then it will be converted and encoded. If not and no
+ half-precision, then it will be converted and encoded. If not and no
  precision will be lost in conversion to single-precision, then it
  will be converted and encoded. If not, then no conversion is
  performed, and it encoded as a double.
 
- Half-precision floating point numbers take up 2 bytes, half that of
+ Half-precision floating-point numbers take up 2 bytes, half that of
  single-precision, one quarter of double-precision
 
  This automatically reduces the size of encoded messages a lot, maybe
@@ -1068,50 +1198,57 @@
 
 
 /**
- @brief[in] Add an optional tag
+ @brief Add an optional tag.
 
  @param[in] pCtx  The encoding context to add the integer to.
  @param[in] uTag  The tag to add
 
- This outputs a CBOR major type 6 optional tag.
+ This outputs a CBOR major type 6 item that tags the next data item
+ that is output usually to indicate it is some new data type.
+
+ For many of the common standard tags, a function to encode data using
+ it is provided and this is not needed. For example,
+ QCBOREncode_AddDateEpoch() already exists to output integers
+ representing dates with the right tag.
 
  The tag is applied to the next data item added to the encoded
- output. That data item that is to be tagged can be of any major
- CBOR type. Any number of tags can be added to a data item by calling
- this multiple times before the data item is added.
+ output. That data item that is to be tagged can be of any major CBOR
+ type. Any number of tags can be added to a data item by calling this
+ multiple times before the data item is added.
 
- For many of the common standard tags a function to encode
- data using it already exists and this is not needed. For example,
- QCBOREncode_AddDateEpoch() already exists to output
- integers representing dates with the right tag.
+ See @ref Tags-Overview for discussion of creating new non-standard
+ tags. See QCBORDecode_GetNext() for discussion of decoding custom
+ tags.
 */
 void QCBOREncode_AddTag(QCBOREncodeContext *pCtx,uint64_t uTag);
 
 
 /**
- @brief  Add an epoch-based date
+ @brief  Add an epoch-based date.
 
- @param[in] pCtx     The encoding context to add the simple value to.
- @param[in] date     Number of seconds since 1970-01-01T00:00Z in UTC time.
+ @param[in] pCtx  The encoding context to add the simple value to.
+ @param[in] date  Number of seconds since 1970-01-01T00:00Z in UTC time.
 
  As per RFC 7049 this is similar to UNIX/Linux/POSIX dates. This is
- the most compact way to specify a date and time in CBOR. Note that this
- is always UTC and does not include the time zone.  Use
+ the most compact way to specify a date and time in CBOR. Note that
+ this is always UTC and does not include the time zone.  Use
  QCBOREncode_AddDateString() if you want to include the time zone.
 
- The integer encoding rules apply here so the date will be encoded in a
- minimal number of 1, 2 4 or 8 bytes. Until about the year 2106 these
- dates should encode in 6 bytes -- one byte for the tag, one byte for the type
- and 4 bytes for the integer.
+ The integer encoding rules apply here so the date will be encoded in
+ a minimal number of bytes. Until about the year 2106 these dates will
+ encode in 6 bytes -- one byte for the tag, one byte for the type and
+ 4 bytes for the integer. After that it will encode to 10 bytes.
 
- If you care about leap-seconds and that level of accuracy, make sure the
- system you are running this code on does it correctly. This code just takes
- the value passed in.
+ Negative values are supported for dates before 1970.
 
- This implementation cannot encode fractional seconds using float or double
- even though that is allowed by CBOR, but you can encode them if you
- want to by calling QCBOREncode_AddDouble()
- with the right parameters.
+ If you care about leap-seconds and that level of accuracy, make sure
+ the system you are running this code on does it correctly. This code
+ just takes the value passed in.
+
+ This implementation cannot encode fractional seconds using float or
+ double even though that is allowed by CBOR, but you can encode them
+ if you want to by calling QCBOREncode_AddDouble() and
+ QCBOREncode_AddTag().
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -1125,13 +1262,13 @@
 /**
  @brief Add a byte string to the encoded output.
 
- @param[in] pCtx      The context to initialize.
- @param[in] Bytes     Pointer and length of the input data.
+ @param[in] pCtx   The context to initialize.
+ @param[in] Bytes  Pointer and length of the input data.
 
  Simply adds the bytes to the encoded output as CBOR major type 2.
 
- If called with Bytes.len equal to 0, an empty string will be
- added. When Bytes.len is 0, Bytes.ptr may be NULL.
+ If called with @c Bytes.len equal to 0, an empty string will be
+ added. When @c Bytes.len is 0, @c Bytes.ptr may be @c NULL.
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -1146,13 +1283,14 @@
 /**
  @brief Add a binary UUID to the encoded output.
 
- @param[in] pCtx      The context to initialize.
- @param[in] Bytes     Pointer and length of the binary UUID.
+ @param[in] pCtx   The context to initialize.
+ @param[in] Bytes  Pointer and length of the binary UUID.
 
- A binary UUID as defined in RFC 4122 is added to the ouput.
+ A binary UUID as defined in [RFC 4122]
+ (https://tools.ietf.org/html/rfc4122) is added to the output.
 
- It is output as CBOR major type 2, a binary string, with
- optional tag 36 indicating the binary string is a UUID.
+ It is output as CBOR major type 2, a binary string, with tag @ref
+ CBOR_TAG_BIN_UUID indicating the binary string is a UUID.
  */
 static void QCBOREncode_AddBinaryUUID(QCBOREncodeContext *pCtx, UsefulBufC Bytes);
 
@@ -1164,19 +1302,19 @@
 /**
  @brief Add a positive big number to the encoded output.
 
- @param[in] pCtx      The context to initialize.
- @param[in] Bytes     Pointer and length of the big number.
+ @param[in] pCtx   The context to initialize.
+ @param[in] Bytes  Pointer and length of the big number.
 
- Big numbers are integers larger than 64-bits. Their format
- is described in RFC 7049.
+ Big numbers are integers larger than 64-bits. Their format is
+ described in [RFC 7049] (https://tools.ietf.org/html/rfc7049).
 
- It is output as CBOR major type 2, a binary string, with
- optional tag 2 indicating the binary string is a positive big
+ It is output as CBOR major type 2, a binary string, with tag @ref
+ CBOR_TAG_POS_BIGNUM indicating the binary string is a positive big
  number.
 
- Often big numbers are used to represent cryptographic keys,
- however, COSE which defines representations for keys chose not
- to use this particular type.
+ Often big numbers are used to represent cryptographic keys, however,
+ COSE which defines representations for keys chose not to use this
+ particular type.
  */
 static void QCBOREncode_AddPositiveBignum(QCBOREncodeContext *pCtx, UsefulBufC Bytes);
 
@@ -1188,19 +1326,19 @@
 /**
  @brief Add a negative big number to the encoded output.
 
- @param[in] pCtx      The context to initialize.
- @param[in] Bytes     Pointer and length of the big number.
+ @param[in] pCtx   The context to initialize.
+ @param[in] Bytes  Pointer and length of the big number.
 
- Big numbers are integers larger than 64-bits. Their format
- is described in RFC 7049.
+ Big numbers are integers larger than 64-bits. Their format is
+ described in [RFC 7049] (https://tools.ietf.org/html/rfc7049).
 
- It is output as CBOR major type 2, a binary string, with
- optional tag 2 indicating the binary string is a negative big
+ It is output as CBOR major type 2, a binary string, with tag @ref
+ CBOR_TAG_NEG_BIGNUM indicating the binary string is a negative big
  number.
 
- Often big numbers are used to represent cryptographic keys,
- however, COSE which defines representations for keys chose not
- to use this particular type.
+ Often big numbers are used to represent cryptographic keys, however,
+ COSE which defines representations for keys chose not to use this
+ particular type.
  */
 static void QCBOREncode_AddNegativeBignum(QCBOREncodeContext *pCtx, UsefulBufC Bytes);
 
@@ -1212,13 +1350,19 @@
 /**
  @brief Add a text URI to the encoded output.
 
- @param[in] pCtx    The context to initialize.
- @param[in] URI     Pointer and length of the URI.
+ @param[in] pCtx  The context to initialize.
+ @param[in] URI   Pointer and length of the URI.
 
- The format of URI is RFC 3986.
+ The format of URI must be per [RFC 3986]
+ (https://tools.ietf.org/html/rfc3986).
 
- It is output as CBOR major type 3, a text string, with
- optional tag 32 indicating the text string is a URI.
+ It is output as CBOR major type 3, a text string, with tag @ref
+ CBOR_TAG_URI indicating the text string is a URI.
+
+ A URI in a NULL-terminated string, @c szURI, can be easily added with
+ this code:
+
+      QCBOREncode_AddURI(pCtx, UsefulBuf_FromSZ(szURI));
  */
 static void QCBOREncode_AddURI(QCBOREncodeContext *pCtx, UsefulBufC URI);
 
@@ -1228,15 +1372,16 @@
 
 
 /**
- @brief Add base 64-encoded text to encoded output.
+ @brief Add Base64-encoded text to encoded output.
 
  @param[in] pCtx     The context to initialize.
  @param[in] B64Text  Pointer and length of the base-64 encoded text.
 
- The text content is base 64 encoded data per RFC 4648.
+ The text content is Base64 encoded data per [RFC 4648]
+ (https://tools.ietf.org/html/rfc4648).
 
- It is output as CBOR major type 3, a text string, with
- optional tag 34 indicating the text string is a URI.
+ It is output as CBOR major type 3, a text string, with tag @ref
+ CBOR_TAG_B64 indicating the text string is Base64 encoded.
  */
 static void QCBOREncode_AddB64Text(QCBOREncodeContext *pCtx, UsefulBufC B64Text);
 
@@ -1246,15 +1391,16 @@
 
 
 /**
- @brief Add base 64URL -encoded URL to encoded output.
+ @brief Add base64url encoded data to encoded output.
 
- @param[in] pCtx    The context to initialize.
- @param[in] B64Text  Pointer and length of the base-64 encoded text.
+ @param[in] pCtx     The context to initialize.
+ @param[in] B64Text  Pointer and length of the base64url encoded text.
 
- The text content is base 64 URL format encoded text as per RFC 4648.
+ The text content is base64URL encoded text as per [RFC 4648]
+ (https://tools.ietf.org/html/rfc4648).
 
- It is output as CBOR major type 3, a text string, with
- optional tag 33 indicating the text string is a URI.
+ It is output as CBOR major type 3, a text string, with tag @ref
+ CBOR_TAG_B64URL indicating the text string is a Base64url encoded.
  */
 static void QCBOREncode_AddB64URLText(QCBOREncodeContext *pCtx, UsefulBufC B64Text);
 
@@ -1264,7 +1410,7 @@
 
 
 /**
- @brief Add Perl Compatible Regular Expression
+ @brief Add Perl Compatible Regular Expression.
 
  @param[in] pCtx    The context to initialize.
  @param[in] Regex   Pointer and length of the regular expression.
@@ -1272,8 +1418,8 @@
  The text content is Perl Compatible Regular
  Expressions (PCRE) / JavaScript syntax [ECMA262].
 
- It is output as CBOR major type 3, a text string, with
- optional tag 35 indicating the text string is a regular expression.
+ It is output as CBOR major type 3, a text string, with tag @ref
+ CBOR_TAG_REGEX indicating the text string is a regular expression.
  */
 static void QCBOREncode_AddRegex(QCBOREncodeContext *pCtx, UsefulBufC Regex);
 
@@ -1288,10 +1434,13 @@
  @param[in] pCtx      The context to initialize.
  @param[in] MIMEData  Pointer and length of the regular expression.
 
- The text content is in MIME format per RFC 2045 including the headers.
+ The text content is in MIME format per [RFC 2045]
+ (https://tools.ietf.org/html/rfc2045) including the headers. Note
+ that this only supports text-format MIME. Binary MIME is not
+ supported.
 
- It is output as CBOR major type 3, a text string, with
- optional tag 36 indicating the text string is MIME data.
+ It is output as CBOR major type 3, a text string, with tag
+ @ref CBOR_TAG_MIME indicating the text string is MIME data.
  */
 static void QCBOREncode_AddMIMEData(QCBOREncodeContext *pCtx, UsefulBufC MIMEData);
 
@@ -1303,11 +1452,14 @@
 /**
  @brief  Add an RFC 3339 date string
 
- @param[in] pCtx      The encoding context to add the simple value to.
- @param[in] szDate    Null-terminated string with date to add
+ @param[in] pCtx    The encoding context to add the simple value to.
+ @param[in] szDate  Null-terminated string with date to add.
 
- The string szDate should be in the form of RFC 3339 as defined by section
- 3.3 in RFC 4287. This is as described in section 2.4.1 in RFC 7049.
+ The string szDate should be in the form of [RFC 3339]
+ (https://tools.ietf.org/html/rfc3339) as defined by section 3.3 in
+ [RFC 4287] (https://tools.ietf.org/html/rfc4287). This is as
+ described in section 2.4.1 in [RFC 7049]
+ (https://tools.ietf.org/html/rfc7049).
 
  Note that this function doesn't validate the format of the date string
  at all. If you add an incorrect format date string, the generated
@@ -1323,12 +1475,12 @@
 
 
 /**
- @brief  Add a standard boolean.
+ @brief  Add a standard Boolean.
 
  @param[in] pCtx   The encoding context to add the simple value to.
- @param[in] b      true or false from stdbool. Anything will result in an error.
+ @param[in] b      true or false from @c <stdbool.h>. Anything will result in an error.
 
- Adds a boolean value as CBOR major type 7.
+ Adds a Boolean value as CBOR major type 7.
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -1343,12 +1495,12 @@
 /**
  @brief  Add a NULL to the encoded output.
 
- @param[in] pCtx   The encoding context to add the simple value to.
+ @param[in] pCtx  The encoding context to add the simple value to.
 
  Adds the NULL value as CBOR major type 7.
 
- This NULL doesn't have any special meaning in CBOR such as a terminating
- value for a string or an empty value.
+ This NULL doesn't have any special meaning in CBOR such as a
+ terminating value for a string or an empty value.
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -1362,14 +1514,14 @@
 /**
  @brief  Add an "undef" to the encoded output.
 
- @param[in] pCtx   The encoding context to add the simple value to.
+ @param[in] pCtx  The encoding context to add the simple value to.
 
  Adds the undef value as CBOR major type 7.
 
  Note that this value will not translate to JSON.
 
- This Undef doesn't have any special meaning in CBOR such as a terminating
- value for a string or an empty value.
+ This Undef doesn't have any special meaning in CBOR such as a
+ terminating value for a string or an empty value.
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -1386,28 +1538,30 @@
  @param[in] pCtx The encoding context to open the array in.
 
  Arrays are the basic CBOR aggregate or structure type. Call this
- function to start or open an array. Then call the various AddXXX
- functions to add the items that go into the array. Then call
- QCBOREncode_CloseArray() when all items have been added. The data
- items in the array can be of any type and can be of mixed types.
+ function to start or open an array. Then call the various @c
+ QCBOREncode_AddXxx() functions to add the items that go into the
+ array. Then call QCBOREncode_CloseArray() when all items have been
+ added. The data items in the array can be of any type and can be of
+ mixed types.
 
  Nesting of arrays and maps is allowed and supported just by calling
- QCBOREncode_OpenArray() again before calling CloseArray.  While CBOR
- has no limit on nesting, this implementation does in order to keep it
- smaller and simpler.  The limit is QCBOR_MAX_ARRAY_NESTING. This is
- the max number of times this can be called without calling
- QCBOREncode_CloseArray(). QCBOREncode_Finish() will return
+ QCBOREncode_OpenArray() again before calling
+ QCBOREncode_CloseArray().  While CBOR has no limit on nesting, this
+ implementation does in order to keep it smaller and simpler.  The
+ limit is @ref QCBOR_MAX_ARRAY_NESTING. This is the max number of
+ times this can be called without calling
+ QCBOREncode_CloseArray(). QCBOREncode_Finish() will return @ref
  QCBOR_ERR_ARRAY_NESTING_TOO_DEEP when it is called as this function
  just sets an error state and returns no value when this occurs.
 
- If you try to add more than QCBOR_MAX_ITEMS_IN_ARRAY items to a
- single array or map, QCBOR_ERR_ARRAY_TOO_LONG will be returned when
- QCBOREncode_Finish() is called.
+ If you try to add more than @ref QCBOR_MAX_ITEMS_IN_ARRAY items to a
+ single array or map, @ref QCBOR_ERR_ARRAY_TOO_LONG will be returned
+ when QCBOREncode_Finish() is called.
 
  An array itself must have a label if it is being added to a map.
  Note that array elements do not have labels (but map elements do).
 
- An array itself may be tagged.
+ An array itself may be tagged by calling QCBOREncode_AddTag() before this call.
  */
 static void QCBOREncode_OpenArray(QCBOREncodeContext *pCtx);
 
@@ -1430,10 +1584,10 @@
  QCBOREncode_Finish() is called.
 
  If this has been called more times than QCBOREncode_OpenArray(), then
- QCBOR_ERR_TOO_MANY_CLOSES will be returned when QCBOREncode_Finish()
+ @ref QCBOR_ERR_TOO_MANY_CLOSES will be returned when QCBOREncode_Finish()
  is called.
 
- If this is called and it is not an array that is currently open,
+ If this is called and it is not an array that is currently open, @ref
  QCBOR_ERR_CLOSE_MISMATCH will be returned when QCBOREncode_Finish()
  is called.
  */
@@ -1457,17 +1611,18 @@
  typically, integers as this gives the most compact output. They might
  also be text strings which gives readability and translation to JSON.
 
- Every QCBOREncode_AddXXX() call has once version that is "InMap" for
- adding items to maps with string labels and on that is "InMapN" that
- is for adding with integer labels.
+ Every @c QCBOREncode_AddXxx() call has one version that ends with @c
+ InMap for adding items to maps with string labels and one that ends
+ with @c InMapN that is for adding with integer labels.
 
  RFC 7049 uses the term "key" instead of "label".
 
- If you wish to use map labels that are neither integer labels or
- text strings, then just call the QCBOREncode_AddXXX() function
+ If you wish to use map labels that are neither integer labels nor
+ text strings, then just call the QCBOREncode_AddXxx() function
  explicitly to add the label. Then call it again to add the value.
 
- See the RFC7049 for a lot more information on creating maps.
+ See the [RFC 7049] (https://tools.ietf.org/html/rfc7049) for a lot
+ more information on creating maps.
  */
 static void QCBOREncode_OpenMap(QCBOREncodeContext *pCtx);
 
@@ -1482,7 +1637,7 @@
 
  @param[in] pCtx The context to add to.
 
- The closes a map opened by QCBOREncode_OpenMap(). It reduces nesting
+ This closes a map opened by QCBOREncode_OpenMap(). It reduces nesting
  level by one.
 
  When an error occurs as a result of this call, the encoder records
@@ -1490,11 +1645,11 @@
  QCBOREncode_Finish() is called.
 
  If this has been called more times than QCBOREncode_OpenMap(),
- then QCBOR_ERR_TOO_MANY_CLOSES will be returned when
+ then @ref QCBOR_ERR_TOO_MANY_CLOSES will be returned when
  QCBOREncode_Finish() is called.
 
- If this is called and it is not a map that is currently
- open, QCBOR_ERR_CLOSE_MISMATCH will be returned when QCBOREncode_Finish()
+ If this is called and it is not a map that is currently open, @ref
+ QCBOR_ERR_CLOSE_MISMATCH will be returned when QCBOREncode_Finish()
  is called.
  */
 static void QCBOREncode_CloseMap(QCBOREncodeContext *pCtx);
@@ -1511,11 +1666,12 @@
  contain encoded CBOR.
 
  The typical use case is for encoded CBOR that is to be
- cryptographically hashed, as part of a COSE (RFC 8152)
- implementation. This avoids having to encode the items first in one
- buffer (e.g., the COSE payload) and then add that buffer as a bstr to
- another encoding (e.g. the COSE to-be-signed bytes, the
- Sig_structure) potentially saving a lot of memory.
+ cryptographically hashed, as part of a [RFC 8152, COSE]
+ (https://tools.ietf.org/html/rfc8152) implementation. This avoids
+ having to encode the items first in one buffer (e.g., the COSE
+ payload) and then add that buffer as a bstr to another encoding
+ (e.g. the COSE to-be-signed bytes, the @c Sig_structure) potentially
+ saving a lot of memory.
 
  When constructing cryptographically signed CBOR objects, maps or
  arrays, they typically are encoded normally and then wrapped as a
@@ -1541,32 +1697,32 @@
 /**
  @brief Close a wrapping bstr.
 
- @param[in]  pCtx          The context to add to.
- @param[out] pWrappedCBOR  UsefulBufC containing wrapped bytes,
+ @param[in] pCtx           The context to add to.
+ @param[out] pWrappedCBOR  A @ref UsefulBufC containing wrapped bytes.
 
- The closes a wrapping bstr opened by QCBOREncode_BstrWrap(). It reduces
+ The closes a wrapping bstr opened by QCBOREncode_CloseBstrWrap(). It reduces
  nesting level by one.
 
- A pointer and length of the wrapped and encoded CBOR is returned in
- *pWrappedCBOR if it is not NULL. This includes the wrapping bstr
- itself.  The main purpose of this is so this data can be hashed
- (e.g., with SHA-256) as part of a COSE (RFC 8152)
+ A pointer and length of the enclosed encoded CBOR is returned in @c
+ *pWrappedCBOR if it is not @c NULL. The main purpose of this is so
+ this data can be hashed (e.g., with SHA-256) as part of a [RFC 8152,
+ COSE] (https://tools.ietf.org/html/rfc8152)
  implementation. **WARNING**, this pointer and length should be used
- right away before any other calls to QCBOREncode_xxxx() as they will
- move data around and the pointer and length will no longer be to the
- correct encoded CBOR.
+ right away before any other calls to @c QCBOREncode_Xxx() as they
+ will move data around and the pointer and length will no longer be to
+ the correct encoded CBOR.
 
  When an error occurs as a result of this call, the encoder records
  the error and enters the error state. The error will be returned when
  QCBOREncode_Finish() is called.
 
- If this has been called more times then QCBOREncode_BstrWrap(),
- then QCBOR_ERR_TOO_MANY_CLOSES will be returned when
+ If this has been called more times than QCBOREncode_BstrWrap(),
+ then @ref QCBOR_ERR_TOO_MANY_CLOSES will be returned when
  QCBOREncode_Finish() is called.
 
  If this is called and it is not a wrapping bstr that is currently
- open, QCBOR_ERR_CLOSE_MISMATCH will be returned when QCBOREncode_Finish()
- is called.
+ open, @ref QCBOR_ERR_CLOSE_MISMATCH will be returned when
+ QCBOREncode_Finish() is called.
  */
 static void QCBOREncode_CloseBstrWrap(QCBOREncodeContext *pCtx, UsefulBufC *pWrappedCBOR);
 
@@ -1574,8 +1730,8 @@
 /**
  @brief Add some already-encoded CBOR bytes.
 
- @param[in] pCtx The context to add to.
- @param[in] Encoded The already-encoded CBOR to add to the context.
+ @param[in] pCtx     The context to add to.
+ @param[in] Encoded  The already-encoded CBOR to add to the context.
 
  The encoded CBOR being added must be fully conforming CBOR. It must
  be complete with no arrays or maps that are incomplete. While this
@@ -1600,31 +1756,58 @@
 /**
  @brief Get the encoded result.
 
- @param[in] pCtx  The context to finish encoding with.
+ @param[in] pCtx           The context to finish encoding with.
  @param[out] pEncodedCBOR  Pointer and length of encoded CBOR.
 
- @return
- One of the CBOR error codes.
+ @retval QCBOR_ERR_TOO_MANY_CLOSES         Nesting error
 
- If this returns success QCBOR_SUCCESS the encoding was a success and
- the return length is correct and complete.
+ @retval QCBOR_ERR_CLOSE_MISMATCH          Nesting error
 
- If no buffer was passed to QCBOR_Init(), then only the length and
- number of items was computed. The length is in
- pEncodedCBOR->Bytes.len. pEncodedCBOR->Bytes.ptr is NULL.
+ @retval QCBOR_ERR_ARRAY_OR_MAP_STILL_OPEN Nesting error
 
- If a buffer was passed, then pEncodedCBOR->Bytes.ptr is the same as
- the buffer passed to QCBOR_Init() and contains the encoded CBOR
- and the length is filled in.
+ @retval QCBOR_ERR_BUFFER_TOO_LARGE        Encoded output buffer size
+
+ @retval QCBOR_ERR_BUFFER_TOO_SMALL        Encoded output buffer size
+
+ @retval QCBOR_ERR_ARRAY_NESTING_TOO_DEEP  Implementation limit
+
+ @retval QCBOR_ERR_ARRAY_TOO_LONG          Implementation limit
+
+ If this returns success @ref QCBOR_SUCCESS the encoding was a success
+ and the return length is correct and complete.
+
+ If no buffer was passed to QCBOREncode_Init(), then only the length
+ was computed. If a buffer was passed, then the encoded CBOR is in the
+ buffer.
+
+ All encoding errors manifest here as no other encoding function
+ returns any errors. They just set the error state in the encode
+ context after which no encoding function does anything.
+
+ Three types of errors manifest here. The first type are nesting
+ errors where the number of @c QCBOREncode_OpenXxx() calls do not
+ match the number @c QCBOREncode_CloseXxx() calls. The solution is to
+ fix the calling code.
+
+ The second type of error is because the buffer given is either too
+ small or too large. The remedy is to give a correctly sized buffer.
+
+ The third type are due to limits in this implementation.  @ref
+ QCBOR_ERR_ARRAY_NESTING_TOO_DEEP can be worked around by encoding the
+ CBOR in two (or more) phases and adding the CBOR from the first phase
+ to the second with @c QCBOREncode_AddEncoded().
 
  If an error is returned, the buffer may have partially encoded
  incorrect CBOR in it and it should not be used. Likewise, the length
  may be incorrect and should not be used.
 
- Note that the error could have occurred in one of the many
- QCBOR_AddXXX calls long before QCBOREncode_Finish() was called. This
- error handling approach reduces the CBOR implementation size, but makes
- debugging a problem a little more difficult.
+ Note that the error could have occurred in one of the many @c
+ QCBOREncode_AddXxx() calls long before QCBOREncode_Finish() was
+ called. This error handling reduces the CBOR implementation size but
+ makes debugging harder.
+
+ This may be called multiple times. It will always return the same. It
+ can also be interleaved with calls to QCBOREncode_FinishGetSize().
  */
 QCBORError QCBOREncode_Finish(QCBOREncodeContext *pCtx, UsefulBufC *pEncodedCBOR);
 
@@ -1632,27 +1815,14 @@
 /**
  @brief Get the encoded CBOR and error status.
 
- @param[in] pCtx  The context to finish encoding with.
- @param[out] uEncodedLen The length of the encoded or potentially encoded CBOR in bytes.
+ @param[in] pCtx          The context to finish encoding with.
+ @param[out] uEncodedLen  The length of the encoded or potentially
+                          encoded CBOR in bytes.
 
- @return
- One of the CBOR error codes.
+ @return The same errors as QCBOREncode_Finish().
 
- If this returns success QCBOR_SUCCESS the encoding was a success and
- the return length is correct and complete.
-
- If no buffer was passed to QCBOR_Init(), then only the length was
- computed. If a buffer was passed, then the encoded CBOR is in the
- buffer.
-
- If an error is returned, the buffer may have partially encoded
- incorrect CBOR in it and it should not be used. Likewise, the length
- may be incorrect and should not be used.
-
- Note that the error could have occurred in one of the many
- QCBOR_AddXXX calls long before QCBOREncode_Finish() was called. This
- error handling reduces the CBOR implementation size, but makes
- debugging harder.
+ This functions the same as QCBOREncode_Finish(), but only returns the
+ size of the encoded output.
  */
 QCBORError QCBOREncode_FinishGetSize(QCBOREncodeContext *pCtx, size_t *uEncodedLen);
 
@@ -1663,8 +1833,8 @@
 
 /**
  QCBORDecodeContext is the data type that holds context decoding the
- data items for some received CBOR.  It is about 100 bytes, so it can go
- on the stack.  The contents are opaque, and the caller should not
+ data items for some received CBOR.  It is about 100 bytes, so it can
+ go on the stack.  The contents are opaque, and the caller should not
  access any internal items.  A context may be re used serially as long
  as it is re initialized.
  */
@@ -1674,105 +1844,106 @@
 /**
  Initialize the CBOR decoder context.
 
- @param[in] pCtx The context to initialize.
- @param[in] EncodedCBOR The buffer with CBOR encoded bytes to be decoded.
- @param[in] nMode One of QCBOR_DECODE_MODE_xxx
+ @param[in] pCtx         The context to initialize.
+ @param[in] EncodedCBOR  The buffer with CBOR encoded bytes to be decoded.
+ @param[in] nMode        See below and @ref QCBORDecodeMode.
 
- Initialize context for a pre-order travesal of the encoded CBOR tree.
+ Initialize context for a pre-order traversal of the encoded CBOR
+ tree.
 
  Most CBOR decoding can be completed by calling this function to start
  and QCBORDecode_GetNext() in a loop.
 
- If indefinite length strings are to be decoded, then
+ If indefinite-length strings are to be decoded, then
  QCBORDecode_SetMemPool() or QCBORDecode_SetUpAllocator() must be
  called to set up a string allocator.
 
- If tags other than built-in tags are to be recognized, then
- QCBORDecode_SetCallerAddedTagMap() must be called. The built-in tags
- are those for which a macro of the form  CBOR_TAG_XXX is defined.
+ If tags other than built-in tags are to be recognized and recorded in
+ @c uTagBits, then QCBORDecode_SetCallerConfiguredTagList() must be
+ called. The built-in tags are those for which a macro of the form @c
+ CBOR_TAG_XXX is defined.
 
- Three decoding modes are supported.  In normal mode,
- QCBOR_DECODE_MODE_NORMAL, maps are decoded and strings and ints are
- accepted as map labels. If a label is other than these, the error
- QCBOR_ERR_MAP_LABEL_TYPE is returned by QCBORDecode_GetNext().
+ Three decoding modes are supported.  In normal mode, @ref
+ QCBOR_DECODE_MODE_NORMAL, maps are decoded and strings and integers
+ are accepted as map labels. If a label is other than these, the error
+ @ref QCBOR_ERR_MAP_LABEL_TYPE is returned by QCBORDecode_GetNext().
 
- In strings-only mode, QCBOR_DECODE_MODE_MAP_STRINGS_ONLY, only text
- strings are accepted for map labels.  This lines up with CBOR that
- converts to JSON. The error QCBOR_ERR_MAP_LABEL_TYPE is returned by
- QCBORDecode_GetNext() if anything but a text string label is
- encountered.
+ In strings-only mode, @ref QCBOR_DECODE_MODE_MAP_STRINGS_ONLY, only
+ text strings are accepted for map labels.  This lines up with CBOR
+ that converts to JSON. The error @ref QCBOR_ERR_MAP_LABEL_TYPE is
+ returned by QCBORDecode_GetNext() if anything but a text string label
+ is encountered.
 
- In QCBOR_DECODE_MODE_MAP_AS_ARRAY maps are treated as special arrays.
- They will be return with special uDataType QCBOR_TYPE_MAP_AS_ARRAY
- and uCount, the number of items, will be double what it would be
- for a normal map because the labels are also counted. This mode
- is useful for decoding CBOR that has labels that are not
- integers or text strings, but the caller must manage much of
+ In @ref QCBOR_DECODE_MODE_MAP_AS_ARRAY maps are treated as special
+ arrays.  They will be return with special @c uDataType @ref
+ QCBOR_TYPE_MAP_AS_ARRAY and @c uCount, the number of items, will be
+ double what it would be for a normal map because the labels are also
+ counted. This mode is useful for decoding CBOR that has labels that
+ are not integers or text strings, but the caller must manage much of
  the map decoding.
  */
 void QCBORDecode_Init(QCBORDecodeContext *pCtx, UsefulBufC EncodedCBOR, QCBORDecodeMode nMode);
 
 
 /**
- @brief Set up the MemPool string allocator for indefinite length strings.
+ @brief Set up the MemPool string allocator for indefinite-length strings.
 
  @param[in] pCtx         The decode context.
  @param[in] MemPool      The pointer and length of the memory pool.
-
  @param[in] bAllStrings  If true, all strings, even of definite
                          length, will be allocated with the string
                          allocator.
 
- @return Error if the MemPool was less than \ref QCBOR_DECODE_MIN_MEM_POOL_SIZE.
+ @return Error if the MemPool was less than @ref QCBOR_DECODE_MIN_MEM_POOL_SIZE.
 
- Indefinite length strings (text and byte) cannot be decoded unless
+ indefinite-length strings (text and byte) cannot be decoded unless
  there is a string allocator configured. MemPool is a simple built-in
  string allocator that allocates bytes from a memory pool handed to it
  by calling this function.  The memory pool is just a pointer and
  length for some block of memory that is to be used for string
  allocation. It can come from the stack, heap or other.
 
- The memory pool must be \ref QCBOR_DECODE_MIN_MEM_POOL_SIZE plus
+ The memory pool must be @ref QCBOR_DECODE_MIN_MEM_POOL_SIZE plus
  space for all the strings allocated.  There is no overhead per string
  allocated. A conservative way to size this buffer is to make it the
- same size as the CBOR being decoded plus \ref
+ same size as the CBOR being decoded plus @ref
  QCBOR_DECODE_MIN_MEM_POOL_SIZE.
 
- This memory pool is used for all indefinite length strings that are
+ This memory pool is used for all indefinite-length strings that are
  text strings or byte strings, including strings used as labels.
 
- The pointers to strings in \ref QCBORItem will point into the memory
+ The pointers to strings in @ref QCBORItem will point into the memory
  pool set here. They do not need to be individually freed. Just
  discard the buffer when they are no longer needed.
 
- If \c bAllStrings is set, then the size will be the overhead plus the
- space to hold **all** strings, definite and indefinite length, value
+ If @c bAllStrings is set, then the size will be the overhead plus the
+ space to hold **all** strings, definite and indefinite-length, value
  or label. The advantage of this is that after the decode is complete,
  the original memory holding the encoded CBOR does not need to remain
  valid.
 
  If this function is never called because there is no need to support
- indefinite length strings, the internal MemPool implementation should
+ indefinite-length strings, the internal MemPool implementation should
  be dead-stripped by the loader and not add to code size.
  */
 QCBORError QCBORDecode_SetMemPool(QCBORDecodeContext *pCtx, UsefulBuf MemPool, bool bAllStrings);
 
 
 /**
- @brief Sets up a custom string allocator for indefinite length strings
+ @brief Sets up a custom string allocator for indefinite-length strings
 
  @param[in] pCtx                 The decoder context to set up an
                                  allocator for.
  @param[in] pfAllocateFunction   Pointer to function that will be
                                  called by QCBOR for allocations and
                                  frees.
- @param[in] pAllocateContext     Context passed to \c
+ @param[in] pAllocateContext     Context passed to @c
                                  pfAllocateFunction.
  @param[in] bAllStrings          If true, all strings, even of definite
                                  length, will be allocated with the
                                  string allocator.
 
- Indefinite length strings (text and byte) cannot be decoded unless
+ indefinite-length strings (text and byte) cannot be decoded unless
  there a string allocator is configured. QCBORDecode_SetUpAllocator()
  allows the caller to configure an external string allocator
  implementation if the internal string allocator is not suitable. See
@@ -1780,19 +1951,19 @@
  that the internal allocator is not automatically set up.
 
  The string allocator configured here can be a custom one designed and
- implemented by the caller.  See \ref QCBORStringAllocate for the
+ implemented by the caller.  See @ref QCBORStringAllocate for the
  requirements for a string allocator implementation.
 
  A malloc-based string external allocator can be obtained by calling
- \c QCBORDecode_MakeMallocStringAllocator(). It will return a function
- and pointer that can be given here as \c pAllocatorFunction and \c
- pAllocatorContext. It uses standard \c malloc() so \c free() must be
- called onall strings marked by \c uDataAlloc \c == \c 1 or \c
- uLabelAlloc \c == \c 1 in \ref QCBORItem.
+ @c QCBORDecode_MakeMallocStringAllocator(). It will return a function
+ and pointer that can be given here as @c pAllocatorFunction and @c
+ pAllocatorContext. It uses standard @c malloc() so @c free() must be
+ called on all strings marked by @c uDataAlloc @c == @c 1 or @c
+ uLabelAlloc @c == @c 1 in @ref QCBORItem.
 
  Note that an older version of this function took an allocator
  structure, rather than single function and pointer.  The older
- version \c QCBORDecode_MakeMallocStringAllocator() also implemented
+ version @c QCBORDecode_MakeMallocStringAllocator() also implemented
  the older interface.
  */
 void QCBORDecode_SetUpAllocator(QCBORDecodeContext *pCtx,
@@ -1801,46 +1972,88 @@
                                 bool bAllStrings);
 
 /**
- @brief Configure list of caller selected tags to be recognized
+ @brief Configure list of caller-selected tags to be recognized.
 
- @param[in] pCtx The decode context.
- @param[out] pTagList Structure holding the list of tags to configure
+ @param[in] pCtx       The decode context.
+ @param[out] pTagList  Structure holding the list of tags to configure.
 
  This is used to tell the decoder about tags beyond those that are
- built-in that should be recognized. The built-in tags are those
- with macros of the form CBOR_TAG_XXX.
+ built-in that should be recognized. The built-in tags are those with
+ macros of the form @c CBOR_TAG_XXX.
 
- See description of QCBORTagListIn.
+ The list pointed to by @c pTagList must persist during decoding.  No
+ copy of it is made.
+
+ The maximum number of tags that can be added is @ref
+ QCBOR_MAX_CUSTOM_TAGS.  If a list larger than this is given, the
+ error will be returned when QCBORDecode_GetNext() is called, not
+ here.
+
+ See description of @ref QCBORTagListIn.
  */
 void QCBORDecode_SetCallerConfiguredTagList(QCBORDecodeContext *pCtx, const QCBORTagListIn *pTagList);
 
 
 /**
- @brief Gets the next item (integer, byte string, array...) in pre order traversal of CBOR tree
+ @brief Gets the next item (integer, byte string, array...) in
+        preorder traversal of CBOR tree.
 
  @param[in]  pCtx          The decoder context.
  @param[out] pDecodedItem  Holds the CBOR item just decoded.
 
- @return 0 or error. All errors except QCBOR_ERR_TOO_MANY_TAGS
- and QCBOR_ERR_STRING_ALLOCATE indicate that the CBOR input
- could not be decoded. In most cases
- this is because the CBOR is invalid. In a few cases
- (QCBOR_ERR_ARRAY_NESTING_TOO_DEEP, QCBOR_ERR_INT_OVERFLOW,
- QCBOR_ERR_DATE_OVERFLOW) it is because the CBOR is beyond
- the limits of what this implementation can handle.
- QCBOR_ERR_NO_STRING_ALLOCATOR indicates CBOR that cannot
- be handled unless a string allocator is configured.
- QCBOR_ERR_MAP_LABEL_TYPE is in a way a limitation of
- this implementation, but can be avoided by decoding
- in QCBOR_DECODE_MODE_MAP_AS_ARRAY mode.
+ @retval QCBOR_ERR_INDEFINITE_STRING_CHUNK  Not well-formed, one of the
+                                            chunks in indefinite-length
+                                            string is wrong type.
 
- pDecodedItem is filled in with the value parsed. Generally, the
- following data is returned in the structure.
+ @retval QCBOR_ERR_ARRAY_OR_MAP_STILL_OPEN  Not well-formed, array or map
+                                            not closed.
 
- - The data type in uDataType which indicates which member of the val
-   union the data is in. This decoder figures out the type based on the
-   CBOR major type, the CBOR "additionalInfo", the CBOR optional tags
-   and the value of the integer.
+ @retval QCBOR_ERR_UNSUPPORTED     Not well-formed, input contains
+                                   unsupported CBOR.
+
+ @retval QCBOR_ERR_HIT_END         Not well-formed, unexpected ran out
+                                   of bytes.
+
+ @retval QCBOR_ERR_BAD_TYPE_7      Not well-formed, bad simple type value.
+
+ @retval QCBOR_ERR_BAD_BREAK       Not well-formed, break occurs where
+                                   not allowed.
+
+ @retval QCBOR_ERR_EXTRA_BYTES     Not well-formed, unprocessed bytes at
+                                   the end.
+
+ @retval QCBOR_ERR_BAD_OPT_TAG     Invalid CBOR, tag on wrong type.
+
+ @retval QCBOR_ERR_ARRAY_TOO_LONG  Implementation limit, array or map
+                                   too long.
+
+ @retval QCBOR_ERR_INT_OVERFLOW    Implementation limit, negative
+                                   integer too large.
+
+ @retval QCBOR_ERR_DATE_OVERFLOW   Implementation limit, date larger
+                                   than can be handled.
+
+ @retval QCBOR_ERR_ARRAY_NESTING_TOO_DEEP  Implementation limit, nesting
+                                           too deep.
+
+ @retval QCBOR_ERR_STRING_ALLOCATE Resource exhaustion, string allocator
+                                   failed.
+
+ @retval QCBOR_ERR_MAP_LABEL_TYPE  Configuration error / Implementation
+                                   limit encountered a map label this is
+                                   not a string on an integer.
+
+ @retval QCBOR_ERR_NO_STRING_ALLOCATOR  Configuration error, encountered
+                                        indefinite-length string with no
+                                        allocator configured.
+
+ @c pDecodedItem is filled in with the value parsed. Generally, the
+ following data is returned in the structure:
+
+ - @c uDataType which indicates which member of the @c val union the
+   data is in. This decoder figures out the type based on the CBOR
+   major type, the CBOR "additionalInfo", the CBOR optional tags and
+   the value of the integer.
 
  - The value of the item, which might be an integer, a pointer and a
    length, the count of items in an array, a floating-point number or
@@ -1848,30 +2061,31 @@
 
  - The nesting level for maps and arrays.
 
- - The label for an item in a map, which may be a text or byte string or an integer.
+ - The label for an item in a map, which may be a text or byte string
+   or an integer.
 
  - The CBOR optional tag or tags.
 
- See documentation on in the data type QCBORItem for all the details
- on what is returned.
+ See documentation on in the data type @ref _QCBORItem for all the
+ details on what is returned.
 
- This function also handles arrays and maps. When first encountered a
- QCBORItem will be returned with major type CBOR_MAJOR_TYPE_ARRAY or
- CBOR_MAJOR_TYPE_ARRAY_MAP. QCBORItem.val.uCount will indicate the number
+ This function handles arrays and maps. When first encountered a @ref
+ QCBORItem will be returned with major type @ref QCBOR_TYPE_ARRAY or
+ @ref QCBOR_TYPE_MAP. @c QCBORItem.val.uCount will indicate the number
  of Items in the array or map.  Typically, an implementation will call
  QCBORDecode_GetNext() in a for loop to fetch them all. When decoding
- indefinite length maps and arrays, QCBORItem.val.uCount is UINT16_MAX
- and uNextNestLevel must be used to know when the end of a map
- or array is reached.
+ indefinite-length maps and arrays, @c QCBORItem.val.uCount is @c
+ UINT16_MAX and @c uNextNestLevel must be used to know when the end of
+ a map or array is reached.
 
- Nesting level 0 is the outside top-most nesting level. For example, in
- a CBOR structure with two items, an integer and a byte string only,
- both would be at nesting level 0.  A CBOR structure with an array
- open, an integer and a byte string, would have the integer and byte
- string as nesting level 1.
+ Nesting level 0 is the outside top-most nesting level. For example,
+ in a CBOR structure with two items, an integer and a byte string
+ only, both would be at nesting level 0.  A CBOR structure with an
+ array open, an integer and a byte string, would have the integer and
+ byte string as nesting level 1.
 
  Here is an example of how the nesting level is reported with no arrays
- or maps at all
+ or maps at all.
 
  @verbatim
  CBOR Structure           Nesting Level
@@ -1879,7 +2093,7 @@
  Byte String                0
  @endverbatim
 
- Here is an example of how the nesting level is reported with an a simple
+ Here is an example of how the nesting level is reported with a simple
  array and some top-level items.
 
  @verbatim
@@ -1904,62 +2118,112 @@
  byte string                1
  @endverbatim
 
- In QCBORItem, uNextNestLevel is the nesting level for the next call
- to QCBORDecode_GetNext(). It indicates if any maps or arrays were closed
- out during the processing of the just-fecthed QCBORItem. This processing
- includes a look-ahead for any breaks that close out indefinite length
- arrays or maps. This value is needed to be able to understand the
- hierarchical structure. If uNextNestLevel is not equal to uNestLevel
- the end of the current map or array has been encountered. This
- works the same for both definite and indefinite length arrays.
+ In @ref _QCBORItem, @c uNextNestLevel is the nesting level for the
+ next call to QCBORDecode_GetNext(). It indicates if any maps or
+ arrays were closed out during the processing of the just-fetched @ref
+ QCBORItem. This processing includes a look-ahead for any breaks that
+ close out indefinite-length arrays or maps. This value is needed to
+ be able to understand the hierarchical structure. If @c
+ uNextNestLevel is not equal to @c uNestLevel the end of the current
+ map or array has been encountered. This works the same for both
+ definite and indefinite-length arrays.
 
- Most uses of this decoder will not need to do anything extra for
- tag handling. The built-in tags, those with a macro of the form
- CBOR_TAG_XXXX, will be enough.
+ This decoder support CBOR type 6 tagging. The decoding of particular
+ given tag value may be supported in one of three different ways.
 
- If tags beyond built-in tags are to be recognized, they must be
- configured by calling QCBORDecode_SetCallerConfiguredTags(). If
- a tag is not recognized it is silently ignored.
+ First, some common tags are fully and transparently supported by
+ automatically decoding them and returning them in a @ref QCBORItem.
+ These tags have a @c QCBOR_TYPE_XXX associated with them and manifest
+ pretty much the same as a standard CBOR type. @ref
+ QCBOR_TYPE_DATE_EPOCH and the @c epochDate member of @ref QCBORItem
+ is an example.
 
- Several tagged types are automatically recognized and decoded and
- returned in their decoded form.
+ Second are tags that are automatically recognized, but not decoded.
+ These are tags that have a @c \#define of the form @c CBOR_TAG_XXX.
+ These are recorded in the @c uTagBits member of @ref QCBORItem. There
+ is an internal table that maps each bit to a particular tag value
+ allowing up to 64 tags on an individual item to be reported (it is
+ rare to have more than one or two). To find out if a particular tag
+ value is set call QCBORDecode_IsTagged() on the @ref QCBORItem.  See
+ also QCBORDecode_GetNextWithTags().
 
- To find out if a QCBORItem was tagged with a particular tag
- call QCBORDecode_IsTagged(). This works only for built-in
- tags and caller-configured tags.
+ Third are tags that are not automatically recognized, because they
+ are proprietary, custom or more recently registered with [IANA]
+ (https://www.iana.org/assignments/cbor-tags/cbor-tags.xhtml). The
+ internal mapping table has to be configured to recognize these. Call
+ QCBORDecode_SetCallerConfiguredTagList() to do that. Then
+ QCBORDecode_IsTagged() will work with them.
 
- To get the full list of tags on an Item without having to
- pre-configure any predetermined list of tags use
- QCBORDecode_GetNextWithTags().
+ The actual decoding of tags supported in the second and third way
+ must be handled by the caller. Often this is simply verifying that
+ the expected tag is present on a map, byte string or such.  In other
+ cases, there might a complicated map structure to decode.
+
+ See @ref Tags-Overview for a description of how to go about creating
+ custom tags.
+
+ This tag decoding design is to be open-ended and flexible to be able
+ to handle newly defined tags, while using very little memory, in
+ particular keeping @ref QCBORItem as small as possible.
+
+ Errors fall in several categories as noted in list above:
+
+ - Not well-formed errors are those where there is something
+ syntactically and fundamentally wrong with the CBOR being
+ decoded. Encoding should stop completely.
+
+ - Invalid CBOR is well-formed, but still not correct. It is probably
+ best to stop decoding, but not necessary.
+
+ - This implementation has some size limits. They should rarely be
+ encountered. If they are it may because something is wrong with the
+ CBOR, for example an array size is incorrect.
+
+ - Resource exhaustion. This only occurs when a string allocator is
+ configured to handle indefinite-length strings as other than that,
+ this implementation does no dynamic memory allocation.
+
+ - There are a few CBOR constructs that are not handled without some
+ extra configuration. These are indefinite length strings and maps
+ with labels that are not strings or integers. See QCBORDecode_Init().
+
  */
 QCBORError QCBORDecode_GetNext(QCBORDecodeContext *pCtx, QCBORItem *pDecodedItem);
 
 
 /**
- @brief Gets the next item including full list of tags for item
+ @brief Gets the next item including full list of tags for item.
 
  @param[in]  pCtx          The decoder context.
  @param[out] pDecodedItem  Holds the CBOR item just decoded.
- @param[in,out] pTagList   On input array to put tags in; on output the tags on this item.
+ @param[in,out] pTagList   On input array to put tags in; on output
+                           the tags on this item. See
+                           @ref QCBORTagListOut.
 
- @return 0 or error.
+ @return See return values for QCBORDecode_GetNext().
 
- This works the same as QCBORDecode_GetNext() except that it also returns
- the full list of tags for the data item. This function should only
- be needed when parsing CBOR to print it out or convert it to some other
- format. It should not be needed in an actual CBOR protocol implementation.
+ @retval QCBOR_ERR_TOO_MANY_TAGS  The size of @c pTagList is too small.
+
+ This works the same as QCBORDecode_GetNext() except that it also
+ returns the full list of tags for the data item. This function should
+ only be needed when parsing CBOR to print it out or convert it to
+ some other format. It should not be needed to implement a CBOR-based
+ protocol.  See QCBORDecode_GetNext() for the main description of tag
+ decoding.
 
  Tags will be returned here whether or not they are in the built-in or
  caller-configured tag lists.
 
  CBOR has no upper bound of limit on the number of tags that can be
- associated with a data item. In practice the number of tags on an item
- will usually be small, perhaps less than five. This will return an error
- if the array in pTagList is too small to hold all the tags for an item.
+ associated with a data item though in practice the number of tags on
+ an item will usually be small, perhaps less than five. This will
+ return @ref QCBOR_ERR_TOO_MANY_TAGS if the array in @c pTagList is
+ too small to hold all the tags for the item.
 
- (This function is separate from  QCBORDecode_GetNext() so as to not have to
- make QCBORItem large enough to be able to hold a full list of tags. Even a list of
- five tags would nearly double its size because tags can be a uint64_t).
+ (This function is separate from QCBORDecode_GetNext() so as to not
+ have to make @ref QCBORItem large enough to be able to hold a full
+ list of tags. Even a list of five tags would nearly double its size
+ because tags can be a @c uint64_t ).
  */
 QCBORError QCBORDecode_GetNextWithTags(QCBORDecodeContext *pCtx, QCBORItem *pDecodedItem, QCBORTagListOut *pTagList);
 
@@ -1968,29 +2232,24 @@
  @brief Determine if a CBOR item was tagged with a particular tag
 
  @param[in] pCtx    The decoder context.
- @param[in] pItem   The CBOR item to check
- @param[in] uTag    The tag to check
+ @param[in] pItem   The CBOR item to check.
+ @param[in] uTag    The tag to check, one of @c CBOR_TAG_XXX.
 
  @return 1 if it was tagged, 0 if not
 
- QCBORDecode_GetNext() processes tags by looking them up
- in two lists and setting a bit corresponding to the tag
- in uTagBits in the QCBORItem. To find out if a
- QCBORItem was tagged with a particular tag, call
- this function. It handles the mapping between
- the two lists of tags and the bits set for it.
+ See QCBORDecode_GetNext() for the main description of tag
+ handling. For tags that are not fully decoded a bit corresponding to
+ the tag is set in in @c uTagBits in the @ref QCBORItem. The
+ particular bit depends on an internal mapping table. This function
+ checks for set bits against the mapping table.
 
- The first tag list is the built-in tags, those
- with a macro of the form CBOR_TAG_XXX in this
- header file. There are up to 48 of these,
- corresponding to the lower 48 tag bits.
+ Typically, a protocol implementation just wants to know if a
+ particular tag is present. That is what this provides. To get the
+ full list of tags on a data item, see QCBORDecode_GetNextWithTags().
 
- The other optional tag list is the ones
- the caller configured using QCBORDecode_SetCallerConfiguredTagList()
- There are QCBOR_MAX_CUSTOM_TAGS (16) of these corresponding to the
- upper 16 tag bits.
-
- See also QCBORDecode_GetTags() and QCBORDecode_GetNextWithTags().
+ Also see QCBORDecode_SetCallerConfiguredTagList() for the means to
+ add new tags to the internal list so they can be checked for with
+ this function.
  */
 int QCBORDecode_IsTagged(QCBORDecodeContext *pCtx, const QCBORItem *pItem, uint64_t uTag);
 
@@ -1998,14 +2257,14 @@
 /**
  Check whether all the bytes have been decoded and maps and arrays closed.
 
- @param[in]  pCtx          The context to check
+ @param[in]  pCtx  The context to check.
 
- @return QCBOR_SUCCESS or error
+ @return An error or @ref QCBOR_SUCCESS.
 
- This tells you if all the bytes given to QCBORDecode_Init() have
- been consumed and whether all maps and arrays were closed.
- The decode is considered to be incorrect or incomplete if not
- and an error will be returned.
+ This tells you if all the bytes given to QCBORDecode_Init() have been
+ consumed and whether all maps and arrays were closed.  The decode is
+ considered to be incorrect or incomplete if not and an error will be
+ returned.
  */
 QCBORError QCBORDecode_Finish(QCBORDecodeContext *pCtx);
 
@@ -2013,37 +2272,37 @@
 
 
 /**
-  Convert int64_t to smaller int's safely
+ @brief Convert int64_t to smaller integers safely.
 
- @param [in]  src    An int64_t
- @param [out] dest   A smaller sized int to convert to
+ @param [in]  src   An @c int64_t.
+ @param [out] dest  A smaller sized integer to convert to.
 
  @return 0 on success -1 if not
 
- When decoding an integer, the CBOR decoder will return the value as an
- int64_t unless the integer is in the range of INT64_MAX and
+ When decoding an integer, the CBOR decoder will return the value as
+ an int64_t unless the integer is in the range of @c INT64_MAX and @c
  UINT64_MAX. That is, unless the value is so large that it can only be
- represented as a uint64_t, it will be an int64_t.
+ represented as a @c uint64_t, it will be an @c int64_t.
 
  CBOR itself doesn't size the individual integers it carries at
  all. The only limits it puts on the major integer types is that they
  are 8 bytes or less in length. Then encoders like this one use the
  smallest number of 1, 2, 4 or 8 bytes to represent the integer based
  on its value. There is thus no notion that one data item in CBOR is
- an 1 byte integer and another is a 4 byte integer.
+ a 1-byte integer and another is a 4-byte integer.
 
  The interface to this CBOR encoder only uses 64-bit integers. Some
  CBOR protocols or implementations of CBOR protocols may not want to
  work with something smaller than a 64-bit integer.  Perhaps an array
  of 1000 integers needs to be sent and none has a value larger than
- 50,000 and are represented as uint16_t.
+ 50,000 and are represented as @c uint16_t.
 
  The sending / encoding side is easy. Integers are temporarily widened
  to 64-bits as a parameter passing through QCBOREncode_AddInt64() and
  encoded in the smallest way possible for their value, possibly in
- less than an uint16_t.
+ less than an @c uint16_t.
 
- On the decoding side the integers will be returned at int64_t even if
+ On the decoding side the integers will be returned at @c int64_t even if
  they are small and were represented by only 1 or 2 bytes in the
  encoded CBOR. The functions here will convert integers to a small
  representation with an overflow check.
@@ -2142,15 +2401,15 @@
  @param[in] Bytes      The bytes to add.
 
  Use QCBOREncode_AddText() or QCBOREncode_AddBytes() or
- QCBOREncode_AddEncoded() instead. They are inline functions
- that call this and supply the correct major type. This function
- is public to make the inline functions work to keep the overall
- code size down and because the C language has no way to make
- it private.
+ QCBOREncode_AddEncoded() instead. They are inline functions that call
+ this and supply the correct major type. This function is public to
+ make the inline functions work to keep the overall code size down and
+ because the C language has no way to make it private.
 
- If this is called the major type should be CBOR_MAJOR_TYPE_TEXT_STRING,
- CBOR_MAJOR_TYPE_BYTE_STRING or CBOR_MAJOR_NONE_TYPE_RAW. The last
- one is special for adding already-encoded CBOR.
+ If this is called the major type should be @c
+ CBOR_MAJOR_TYPE_TEXT_STRING, @c CBOR_MAJOR_TYPE_BYTE_STRING or @c
+ CBOR_MAJOR_NONE_TYPE_RAW. The last one is special for adding
+ already-encoded CBOR.
  */
 void QCBOREncode_AddBuffer(QCBOREncodeContext *pCtx, uint8_t uMajorType, UsefulBufC Bytes);
 
@@ -2158,8 +2417,8 @@
 /**
  @brief Semi-private method to open a map, array or bstr wrapped CBOR
 
- @param[in] pCtx The context to add to.
- @param[in] uMajorType The major CBOR type to close
+ @param[in] pCtx        The context to add to.
+ @param[in] uMajorType  The major CBOR type to close
 
  Call QCBOREncode_OpenArray(), QCBOREncode_OpenMap() or
  QCBOREncode_BstrWrap() instead of this.
@@ -2170,9 +2429,9 @@
 /**
  @brief Semi-private method to close a map, array or bstr wrapped CBOR
 
- @param[in] pCtx The context to add to.
- @param[in] uMajorType The major CBOR type to close
- @param[out] pWrappedCBOR UsefulBufC containing wrapped bytes
+ @param[in] pCtx           The context to add to.
+ @param[in] uMajorType     The major CBOR type to close.
+ @param[out] pWrappedCBOR  Pointer to @ref UsefulBufC containing wrapped bytes.
 
  Call QCBOREncode_CloseArray(), QCBOREncode_CloseMap() or
  QCBOREncode_CloseBstrWrap() instead of this.
@@ -2183,17 +2442,18 @@
 /**
  @brief  Semi-private method to add simple types.
 
- @param[in] pCtx      The encoding context to add the simple value to.
- @param[in] uSize     Minimum encoding size for uNum. Usually 0.
- @param[in] uNum      One of CBOR_SIMPLEV_FALSE through _UNDEF or other.
+ @param[in] pCtx   The encoding context to add the simple value to.
+ @param[in] uSize  Minimum encoding size for uNum. Usually 0.
+ @param[in] uNum   One of CBOR_SIMPLEV_FALSE through _UNDEF or other.
 
  This is used to add simple types like true and false.
 
- Call QCBOREncode_AddBool(), QCBOREncode_AddNULL(), QCBOREncode_AddUndef()
- instead of this.
+ Call QCBOREncode_AddBool(), QCBOREncode_AddNULL(),
+ QCBOREncode_AddUndef() instead of this.
 
- This function can add simple values that are not defined by CBOR yet. This expansion
- point in CBOR should not be used unless they are standardized.
+ This function can add simple values that are not defined by CBOR
+ yet. This expansion point in CBOR should not be used unless they are
+ standardized.
 
  Error handling is the same as QCBOREncode_AddInt64().
  */
@@ -2231,7 +2491,8 @@
 
 static inline void QCBOREncode_AddInt64ToMap(QCBOREncodeContext *pCtx, const char *szLabel, int64_t uNum)
 {
-   QCBOREncode_AddBuffer(pCtx, CBOR_MAJOR_TYPE_TEXT_STRING, UsefulBuf_FromSZ(szLabel)); // AddSZString not defined yet
+   // Use _AddBuffer() because _AddSZString() is defined below, not above
+   QCBOREncode_AddBuffer(pCtx, CBOR_MAJOR_TYPE_TEXT_STRING, UsefulBuf_FromSZ(szLabel));
    QCBOREncode_AddInt64(pCtx, uNum);
 }
 
@@ -2244,7 +2505,8 @@
 
 static inline void QCBOREncode_AddUInt64ToMap(QCBOREncodeContext *pCtx, const char *szLabel, uint64_t uNum)
 {
-   QCBOREncode_AddBuffer(pCtx, CBOR_MAJOR_TYPE_TEXT_STRING, UsefulBuf_FromSZ(szLabel)); // AddSZString not defined yet
+   // Use _AddBuffer() because _AddSZString() is defined below, not above
+   QCBOREncode_AddBuffer(pCtx, CBOR_MAJOR_TYPE_TEXT_STRING, UsefulBuf_FromSZ(szLabel));
    QCBOREncode_AddUInt64(pCtx, uNum);
 }
 
@@ -2262,7 +2524,8 @@
 
 static inline void QCBOREncode_AddTextToMap(QCBOREncodeContext *pCtx, const char *szLabel, UsefulBufC Text)
 {
-   QCBOREncode_AddText(pCtx, UsefulBuf_FromSZ(szLabel)); // AddSZString not defined yet
+   // Use _AddBuffer() because _AddSZString() is defined below, not above
+   QCBOREncode_AddText(pCtx, UsefulBuf_FromSZ(szLabel));
    QCBOREncode_AddText(pCtx, Text);
 }
 
diff --git a/src/qcbor_decode.c b/src/qcbor_decode.c
index fe384c0..8e485ab 100644
--- a/src/qcbor_decode.c
+++ b/src/qcbor_decode.c
@@ -565,7 +565,7 @@
       case CBOR_SIMPLEV_ONEBYTE: // 24
          if(uNumber <= CBOR_SIMPLE_BREAK) {
             // This takes out f8 00 ... f8 1f which should be encoded as e0 … f7
-            nReturn = QCBOR_ERR_INVALID_CBOR;
+            nReturn = QCBOR_ERR_BAD_TYPE_7;
             goto Done;
          }
          /* FALLTHROUGH */
diff --git a/test/qcbor_decode_tests.c b/test/qcbor_decode_tests.c
index e9d54fb..680c86b 100644
--- a/test/qcbor_decode_tests.c
+++ b/test/qcbor_decode_tests.c
@@ -1305,13 +1305,13 @@
    if(Item.uDataType != QCBOR_TYPE_UKNOWN_SIMPLE || Item.val.uSimple != 19)
       return -1;
 
-   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_INVALID_CBOR)
+   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_BAD_TYPE_7)
       return -1;
 
-   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_INVALID_CBOR)
+   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_BAD_TYPE_7)
       return -1;
 
-   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_INVALID_CBOR)
+   if(QCBORDecode_GetNext(&DCtx, &Item) != QCBOR_ERR_BAD_TYPE_7)
       return -1;
 
    if((nCBORError = QCBORDecode_GetNext(&DCtx, &Item)))
@@ -1352,8 +1352,8 @@
    { {(uint8_t[]){0x7c}, 1}, QCBOR_ERR_UNSUPPORTED }, // Reserved additional info = 28
    { {(uint8_t[]){0x7f}, 1}, QCBOR_ERR_UNSUPPORTED }, // Indefinite length UTF-8 string
    { {(uint8_t[]){0xff}, 1}, QCBOR_ERR_UNSUPPORTED } , // break
-   { {(uint8_t[]){0xf8, 0x00}, 2}, QCBOR_ERR_INVALID_CBOR }, // An invalid encoding of a simple type
-   { {(uint8_t[]){0xf8, 0x1f}, 2}, QCBOR_ERR_INVALID_CBOR },  // An invalid encoding of a simple type
+   { {(uint8_t[]){0xf8, 0x00}, 2}, QCBOR_ERR_BAD_TYPE_7 }, // An invalid encoding of a simple type
+   { {(uint8_t[]){0xf8, 0x1f}, 2}, QCBOR_ERR_BAD_TYPE_7 },  // An invalid encoding of a simple type
    { {(uint8_t[]){0xc0, 0x00}, 2}, QCBOR_ERR_BAD_OPT_TAG },  // Text-based date, with an integer
    { {(uint8_t[]){0xc1, 0x41, 0x33}, 3}, QCBOR_ERR_BAD_OPT_TAG },   // Epoch date, with an byte string
    { {(uint8_t[]){0xc1, 0xc0, 0x00}, 3}, QCBOR_ERR_BAD_OPT_TAG },   // tagged as both epoch and string dates