Comments on the example
diff --git a/example.c b/example.c
index 45f729e..a12c148 100644
--- a/example.c
+++ b/example.c
@@ -18,38 +18,48 @@
 
 #define MAX_CYLINDERS 16
 
+
+/**
+ The data structure representing a car engine that is encoded and decoded in this examples.
+ */
 typedef struct
 {
     UsefulBufC Manufacturer;
-    int64_t uNumCylinders;
     int64_t uDisplacement;
     int64_t uHorsePower;
     double dDesignedCompresion;
+    int64_t uNumCylinders;
     struct {
         double uMeasuredCompression;
     } cylinders[MAX_CYLINDERS];
     bool bTurboCharged;
-} Engine;
+} CarEngine;
 
 
-void EngineInit(Engine *pE)
+/**
+ Initialize the Engine data structure with some values to encode/decode.
+ */
+void EngineInit(CarEngine *pE)
 {
-    pE->uNumCylinders = 6;
-    pE->bTurboCharged = false;
     pE->Manufacturer = UsefulBuf_FROM_SZ_LITERAL("Porsche");
     pE->uDisplacement = 3296;
     pE->uHorsePower = 210;
     pE->dDesignedCompresion = 9.1;
+    pE->uNumCylinders = 6;
     pE->cylinders[0].uMeasuredCompression = 9.0;
     pE->cylinders[1].uMeasuredCompression = 9.2;
     pE->cylinders[2].uMeasuredCompression = 8.9;
     pE->cylinders[3].uMeasuredCompression = 8.9;
     pE->cylinders[4].uMeasuredCompression = 9.1;
     pE->cylinders[5].uMeasuredCompression = 9.0;
+    pE->bTurboCharged = false;
 }
 
 
-bool EngineCompare(Engine *pE1, Engine *pE2)
+/**
+ Return @c true if the two Engined data structures are exactly the same.
+ */
+bool EngineCompare(CarEngine *pE1, CarEngine *pE2)
 {
     if(pE1->uNumCylinders != pE2->uNumCylinders) {
         return false;
@@ -81,7 +91,21 @@
 }
 
 
-UsefulBufC EncodeEngine(const Engine *pEngine, UsefulBuf Buffer)
+/**
+ @brief Encode an initialized Engine data structure in CBOR.
+
+ @param[in] pEngine  The data structure to encode.
+ @param[in] Buffer    Pointer and length of buffer to output to.
+
+ @return The pointer and length of the encoded CBOR or @ref NULLUsefulBufC on error.
+
+ @c Buffer must be big enough to hold the output. If it is not @ref NULLUsefulBufC
+ will be returned. @ref @ref NULLUsefulBufC will be returned for any other encoding
+ errors.
+
+ This encoding will use definite CBOR lengths.
+ */
+UsefulBufC EncodeEngine(const CarEngine *pEngine, UsefulBuf Buffer)
 {
     /* Initialize th encoder with the buffer big enough to hold the expected output.
      If it is too small, QCBOREncode_Finish() will return an error. */
@@ -101,7 +125,7 @@
         QCBOREncode_AddDouble(&EncodeCtx, pEngine->cylinders[i].uMeasuredCompression);
     }
     QCBOREncode_CloseArray(&EncodeCtx);
-    QCBOREncode_AddBoolToMap(&EncodeCtx, "turbo", pEngine->bTurboCharged);
+    QCBOREncode_AddBoolToMap(&EncodeCtx, "Turbo", pEngine->bTurboCharged);
     QCBOREncode_CloseMap(&EncodeCtx);
 
     /* Get the pointer and length of the encoded output. If there was
@@ -117,7 +141,22 @@
 }
 
 
-UsefulBufC EncodeEngineIndefinteLen(const Engine *pEngine, UsefulBuf Buffer)
+/**
+ @brief Encode an initialized Engine data structure in CBOR using indefinite lengths..
+
+ @param[in] pEngine  The data structure to encode.
+ @param[in] Buffer    Pointer and length of buffer to output to.
+
+ @return The pointer and length of the encoded CBOR or @ref NULLUsefulBufC on error.
+
+ This is virtually the same as EncodeEngine(). The encoded CBOR is slightly different as the
+  map and array use indefinite lengths, rather than definite lengths.
+
+ There is little practical use for this function as definite lengths are generally preferred for
+ CBOR and QCBOR always easily encodes definite lengths. (The advantage of indefinite
+ lengths are that they are simpler to encode, but that doesn't come into effect here).
+ */
+UsefulBufC EncodeEngineIndefinteLen(const CarEngine *pEngine, UsefulBuf Buffer)
 {
     QCBOREncodeContext EncodeCtx;
 
@@ -133,7 +172,7 @@
         QCBOREncode_AddDouble(&EncodeCtx, pEngine->cylinders[i].uMeasuredCompression);
     }
     QCBOREncode_CloseArrayIndefiniteLength(&EncodeCtx);
-    QCBOREncode_AddBoolToMap(&EncodeCtx, "turbo", pEngine->bTurboCharged);
+    QCBOREncode_AddBoolToMap(&EncodeCtx, "Turbo", pEngine->bTurboCharged);
     QCBOREncode_CloseMapIndefiniteLength(&EncodeCtx);
 
     UsefulBufC EncodedCBOR;
@@ -147,7 +186,9 @@
 }
 
 
-
+/**
+ Error results when decoding an Engine data structure.
+ */
 typedef enum  {
     EngineSuccess,
     CBORNotWellFormed,
@@ -157,6 +198,9 @@
 } EngineDecodeErrors;
 
 
+/**
+ Convert \ref QCBORError to \ref EngineDecodeErrors.
+ */
 EngineDecodeErrors ConvertError(QCBORError uErr)
 {
     EngineDecodeErrors uReturn;
@@ -180,12 +224,31 @@
 }
 
 
-/*
- Decode using the advanced decode features. This pulls in more
- code from the QCBOR library, but is much simpler and
- roughly mirrors the encoding implementation.
+/**
+ @brief Simplest engine decode using advanced decoe features.
+
+ @param[in] EncodedEngine  Pointer and length of CBOR-encoded engine.
+ @param[out] pE  The structure filled in from the decoding.
+
+ @return The decode error or success.
+
+ This verssion of the decoder has the simplest implementation, but
+ pulls in more code from the QCBOR library.  This version uses
+ the most CPU because it scanns the all the CBOR each time
+ a data item is decoded. The CPU used for a data structure as small
+ as this is probably insignificant. CPU use for this style of decode is
+ probably only a factor on slow CPUs with big CBOR inputs.
+
+ Code size is yet to be measured, but this is probably the smallest total
+ code size if multiple protocols are being decoded in one application because
+ the complex parsing of a map and array is done be shared code from the
+ CBOR library rather than by individual protocol-specific chunks of code.
+ Similarly, this may be the smallest for  complex CBOR with multiple
+ maps that need to be processed..
+
+ See also DecodeEngineAdvancedFaster() and DecodeEngineBasic().
  */
-EngineDecodeErrors DecodeEngine(UsefulBufC EncodedEngine, Engine *pE)
+EngineDecodeErrors DecodeEngineAdvanced(UsefulBufC EncodedEngine, CarEngine *pE)
 {
     QCBORError uErr;
     QCBORDecodeContext DecodeCtx;
@@ -196,7 +259,7 @@
     QCBORDecode_GetInt64InMapSZ(&DecodeCtx, "Displacement", &(pE->uDisplacement));
     QCBORDecode_GetInt64InMapSZ(&DecodeCtx, "Horsepower", &(pE->uHorsePower));
     QCBORDecode_GetDoubleInMapSZ(&DecodeCtx, "DesignedCompression", &(pE->dDesignedCompresion));
-    QCBORDecode_GetBoolInMapSZ(&DecodeCtx, "turbo", &(pE->bTurboCharged));
+    QCBORDecode_GetBoolInMapSZ(&DecodeCtx, "Turbo", &(pE->bTurboCharged));
 
     QCBORDecode_GetInt64InMapSZ(&DecodeCtx, "NumCylinders", &(pE->uNumCylinders));
 
@@ -226,8 +289,23 @@
 }
 
 
+/**
+ @brief Simplest engine decode using advanced decoe features.
 
-EngineDecodeErrors DecodeEngineXX(UsefulBufC EncodedEngine, Engine *pE)
+ @param[in] EncodedEngine  Pointer and length of CBOR-encoded engine.
+ @param[out] pE  The structure filled in from the decoding.
+
+ @return The decode error or success.
+
+This verssion of the decoder is still fairly simple and uses the
+ advanced decode features like DecodeEngine(), but is faster
+ and pulls in less library code. It is faster because all the items
+ except the array are pulled out of the map in one pass, rather
+ than multiple passes.
+
+ See also DecodeEngineAdvanced() and DecodeEngineBasic().
+*/
+EngineDecodeErrors DecodeEngineAdvancedFaster(UsefulBufC EncodedEngine, CarEngine *pE)
 {
     QCBORError uErr;
     QCBORDecodeContext DecodeCtx;
@@ -235,47 +313,47 @@
     QCBORDecode_Init(&DecodeCtx, EncodedEngine, QCBOR_DECODE_MODE_NORMAL);
     QCBORDecode_EnterMap(&DecodeCtx);
 
-    QCBORItem XX[7];
-    XX[0].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[0].label.string = UsefulBuf_FROM_SZ_LITERAL("Manufacturer");
-    XX[0].uDataType = QCBOR_TYPE_TEXT_STRING;
+    QCBORItem EngineItems[7];
+    EngineItems[0].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[0].label.string = UsefulBuf_FROM_SZ_LITERAL("Manufacturer");
+    EngineItems[0].uDataType = QCBOR_TYPE_TEXT_STRING;
 
-    XX[1].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[1].label.string = UsefulBuf_FROM_SZ_LITERAL("Displacement");
-    XX[1].uDataType = QCBOR_TYPE_INT64;
+    EngineItems[1].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[1].label.string = UsefulBuf_FROM_SZ_LITERAL("Displacement");
+    EngineItems[1].uDataType = QCBOR_TYPE_INT64;
 
-    XX[2].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[2].label.string = UsefulBuf_FROM_SZ_LITERAL("Horsepower");
-    XX[2].uDataType = QCBOR_TYPE_INT64;
+    EngineItems[2].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[2].label.string = UsefulBuf_FROM_SZ_LITERAL("Horsepower");
+    EngineItems[2].uDataType = QCBOR_TYPE_INT64;
 
-    XX[3].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[3].label.string = UsefulBuf_FROM_SZ_LITERAL("DesignedCompression");
-    XX[3].uDataType = QCBOR_TYPE_DOUBLE;
+    EngineItems[3].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[3].label.string = UsefulBuf_FROM_SZ_LITERAL("DesignedCompression");
+    EngineItems[3].uDataType = QCBOR_TYPE_DOUBLE;
 
-    XX[4].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[4].label.string = UsefulBuf_FROM_SZ_LITERAL("turbo");
-    XX[4].uDataType = QCBOR_TYPE_ANY;
+    EngineItems[4].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[4].label.string = UsefulBuf_FROM_SZ_LITERAL("Turbo");
+    EngineItems[4].uDataType = QCBOR_TYPE_ANY;
 
-    XX[5].uLabelType = QCBOR_TYPE_TEXT_STRING;
-    XX[5].label.string = UsefulBuf_FROM_SZ_LITERAL("NumCylinders");
-    XX[5].uDataType = QCBOR_TYPE_INT64;
+    EngineItems[5].uLabelType = QCBOR_TYPE_TEXT_STRING;
+    EngineItems[5].label.string = UsefulBuf_FROM_SZ_LITERAL("NumCylinders");
+    EngineItems[5].uDataType = QCBOR_TYPE_INT64;
 
-    XX[6].uLabelType = QCBOR_TYPE_NONE;
+    EngineItems[6].uLabelType = QCBOR_TYPE_NONE;
 
-    uErr = QCBORDecode_GetItemsInMap(&DecodeCtx, XX);
+    uErr = QCBORDecode_GetItemsInMap(&DecodeCtx, EngineItems);
     if(uErr != QCBOR_SUCCESS) {
         goto Done;
     }
 
-    pE->Manufacturer = XX[0].val.string;
-    pE->uDisplacement = XX[1].val.int64;
-    pE->uHorsePower = XX[2].val.int64;
-    pE->dDesignedCompresion = XX[3].val.dfnum;
-    pE->uNumCylinders = XX[5].val.int64;
+    pE->Manufacturer = EngineItems[0].val.string;
+    pE->uDisplacement = EngineItems[1].val.int64;
+    pE->uHorsePower = EngineItems[2].val.int64;
+    pE->dDesignedCompresion = EngineItems[3].val.dfnum;
+    pE->uNumCylinders = EngineItems[5].val.int64;
 
-    if(XX[4].uDataType == QCBOR_TYPE_TRUE) {
+    if(EngineItems[4].uDataType == QCBOR_TYPE_TRUE) {
         pE->bTurboCharged = true;
-    } else if(XX[4].uDataType == QCBOR_TYPE_FALSE) {
+    } else if(EngineItems[4].uDataType == QCBOR_TYPE_FALSE) {
         pE->bTurboCharged = false;
     } else {
         return EngineProtocolerror;
@@ -340,7 +418,7 @@
 
 
 EngineDecodeErrors DecodeCylinders(QCBORDecodeContext *pDecodeCtx,
-                                   Engine *pE,
+                                   CarEngine *pE,
                                    const QCBORItem *pItem)
 {
     int i = 0;
@@ -373,8 +451,26 @@
 }
 
 
+/**
+@brief Engine decode without advanced decode features.
 
-EngineDecodeErrors DecodeEngineBasic(UsefulBufC EncodedEngine, Engine *pE)
+@param[in] EncodedEngine  Pointer and length of CBOR-encoded engine.
+@param[out] pE  The structure filled in from the decoding.
+
+@return The decode error or success.
+
+This version of the deocde is the most complex, but uses
+ significantly less code from the QCBOR library.  It is also
+ the most CPU-efficient since it does only one pass
+ through the CBOR.
+
+  Code size is yet to be measured, but this is probably the smallest total
+ code size of all three, if just one CBOR protocol is being decoded. If
+ multiple protocols are being decoded the other options.
+
+ See also DecodeEngineAdvanced() and DecodeEngineAdvancedFaster().
+*/
+EngineDecodeErrors DecodeEngineBasic(UsefulBufC EncodedEngine, CarEngine *pE)
 {
     QCBORDecodeContext DecodeCtx;
 
@@ -416,7 +512,6 @@
         } /* continue on and try for another match */
 
 
-
         uErr = CheckLabelAndType("NumCylinders", QCBOR_TYPE_INT64, &Item);
         if(uErr == QCBOR_SUCCESS) {
             if(Item.val.int64 > MAX_CYLINDERS) {
@@ -462,7 +557,7 @@
             return EngineProtocolerror;
         }
 
-        uErr = CheckLabelAndType("turbo", QCBOR_TYPE_ANY, &Item);
+        uErr = CheckLabelAndType("Turbo", QCBOR_TYPE_ANY, &Item);
            if(uErr == QCBOR_SUCCESS) {
                if(Item.uDataType == QCBOR_TYPE_TRUE) {
                    pE->bTurboCharged = true;
@@ -494,7 +589,7 @@
 
 void RunQCborExample()
 {
-    Engine                  E, DecodedEngine;
+    CarEngine                  E, DecodedEngine;
     MakeUsefulBufOnStack(   EngineBuffer, 300);
     UsefulBufC              EncodedEngine;
 
@@ -507,7 +602,7 @@
 
     printf("Engine Encoded in %zu bytes\n", EncodedEngine.len);
 
-    int x = (int)DecodeEngine(EncodedEngine, &DecodedEngine);
+    int x = (int)DecodeEngineAdvanced(EncodedEngine, &DecodedEngine);
     printf("Engine Decode Result: %d\n", x);
 
 
@@ -515,7 +610,7 @@
 
     printf("Indef Engine Encoded in %zu bytes\n", InDefEncodedEngine.len);
 
-    x = (int)DecodeEngine(InDefEncodedEngine, &DecodedEngine);
+    x = (int)DecodeEngineAdvanced(InDefEncodedEngine, &DecodedEngine);
     printf("Indef Engine Decode Result: %d\n", x);
 
     if(!EngineCompare(&E, &DecodedEngine)) {
@@ -538,7 +633,7 @@
         printf("indef decode comparison fail\n");
     }
 
-    x = (int)DecodeEngineXX(EncodedEngine, &DecodedEngine);
+    x = (int)DecodeEngineAdvancedFaster(EncodedEngine, &DecodedEngine);
     printf("Efficient Engine Basic Decode Result: %d\n", x);
 
     if(!EngineCompare(&E, &DecodedEngine)) {