Introduce a small msgbuf abstraction

Tidy up how we extract data from wire-format buffers.

The API achieves the following:

1. Abstracts the buffer tracking to improve clarity in the calling code

2. Prevents buffer overflows during data extraction

3. Handles type conversions while avoiding undefined behaviour

4. Handles alignment concerns with packed data and removes the need for
   `__attribute__((packed))` structs in the public ABI

5. Handles the endianness conversions required by the PLDM
   specification(s)

6. Batches error checks such that you mostly only have to do `return
   pldm_msgbuf_destroy();` at the end of the decode_* function for error
   handling, no error handling required on every `pldm_msgbuf_extract()`
   call

7. pldm_msgbuf_extract() is generic over the type of the data pointer
   (automatically calls the correct extractor for the type of the
   pointer)

8. Generates optimal code (where the optimiser can prove the accesses
   are in-bounds we generate straight-line load/store pairs and no
   function calls)

Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
Change-Id: I7e727cbd26c43aae2815ababe0e6ca4c8e629766
Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
diff --git a/tests/meson.build b/tests/meson.build
index 1955487..aba89bc 100644
--- a/tests/meson.build
+++ b/tests/meson.build
@@ -21,7 +21,8 @@
   'libpldm_fru_test',
   'libpldm_utils_test',
   'libpldm_pdr_test',
-  'libpldm_firmware_update_test'
+  'libpldm_firmware_update_test',
+  'msgbuf',
 ]
 
 if get_option('oem-ibm').enabled()
@@ -31,9 +32,12 @@
   ]
 endif
 
+src_includes = include_directories('..' / 'src', '..' / 'include' / 'libpldm')
+
 foreach t : tests
   test(t, executable(t.underscorify(), t + '.cpp',
                      implicit_include_directories: false,
+                     include_directories: src_includes,
                      dependencies: [
                          libpldm_dep,
                          gtest_dep,
@@ -41,3 +45,7 @@
        workdir: meson.current_source_dir())
 endforeach
 
+test('msgbuf_generic', executable('msgbuf_generic',
+                                  'msgbuf_generic.c',
+                                  implicit_include_directories: false,
+                                  include_directories: src_includes))