aboutsummaryrefslogtreecommitdiff
path: root/src/pack.h
diff options
context:
space:
mode:
authorDavid Timber <mieabby@gmail.com>2021-12-06 15:21:52 +0800
committerDavid Timber <mieabby@gmail.com>2021-12-06 15:21:52 +0800
commit15ba357fa1b309171b4a6def367b7f82724f2e55 (patch)
treeab2856478a9e5c8764c002bac46194e4e38de4f3 /src/pack.h
parentf5d9956c3e2343455a3025b9d38c539b680da8f5 (diff)
Documentation progress, bug fix, interface change
* Update vscode settings for Doxygen * Fix mem leak in prne_index_bin_archive() * Fix bug where errno is not set in prne_htbt_parse_args() * Change names of parameter to prne_htbt_cp_hover() * Add template for Doxygen comment blocks
Diffstat (limited to 'src/pack.h')
-rw-r--r--src/pack.h196
1 files changed, 180 insertions, 16 deletions
diff --git a/src/pack.h b/src/pack.h
index c487b00..aa7f64c 100644
--- a/src/pack.h
+++ b/src/pack.h
@@ -1,3 +1,6 @@
+/** \file
+ * \brief Executable packing facility.
+ */
/*
* Copyright (c) 2019-2021 David Timber <mieabby@gmail.com>
*
@@ -28,46 +31,62 @@
#include <zlib.h>
+/* Alias declarations */
typedef struct prne_bin_host prne_bin_host_t;
typedef struct prne_bin_tuple prne_bin_tuple_t;
typedef struct prne_bin_archive prne_bin_archive_t;
typedef struct prne_bin_rcb_ctx prne_bin_rcb_ctx_t;
typedef struct prne_rcb_param prne_rcb_param_t;
+// The pack function result codes
typedef enum {
- PRNE_PACK_RC_OK,
- PRNE_PACK_RC_EOF,
- PRNE_PACK_RC_INVAL,
- PRNE_PACK_RC_FMT_ERR,
- PRNE_PACK_RC_ERRNO,
- PRNE_PACK_RC_Z_ERR,
- PRNE_PACK_RC_NO_ARCH,
- PRNE_PACK_RC_UNIMPL_REV,
-
- NB_PRNE_PACK_RC
+ PRNE_PACK_RC_OK, // Successful
+ PRNE_PACK_RC_EOF, // End of file reached
+ PRNE_PACK_RC_INVAL, // Invalid data
+ PRNE_PACK_RC_FMT_ERR, // Format error
+ PRNE_PACK_RC_ERRNO, // Syscall error, errno set
+ PRNE_PACK_RC_Z_ERR, // zlib function error
+ PRNE_PACK_RC_NO_ARCH, // Arch not found
+ PRNE_PACK_RC_UNIMPL_REV, // Unimplemented revision number
+
+ NB_PRNE_PACK_RC // Meta: the number of result codes
} prne_pack_rc_t;
+// The executable host info record
struct prne_bin_host {
prne_os_t os;
prne_arch_t arch;
};
+// The executable host info record - executable size pair
struct prne_bin_tuple {
size_t size;
prne_bin_host_t host;
};
+// The indexed binary archive object
struct prne_bin_archive {
- const uint8_t *data;
- size_t data_size;
- size_t nb_bin;
- prne_bin_tuple_t *bin;
+ const uint8_t *data; // The pointer to the start of the binary archive
+ size_t data_size; // The byte length of the binary archive
+ size_t nb_bin; // The number of the tuples
+ prne_bin_tuple_t *bin; // The array of the tuples
};
-// Recombination Context
+// The recombination context object
struct prne_bin_rcb_ctx {
- void *o_ctx;
+ void *o_ctx; // The opaque context
+ /**
+ * \brief The function used to free the opaque context. Not to be used
+ * directly.
+ * \note Use \c prne_free_bin_rcb_ctx() to free the object!
+ * \see \c prne_free_bin_rcb_ctx()
+ */
void (*ctx_free_f)(void*);
+ /**
+ * \brief The adaptive read callback function. Not to be used directly.
+ * \note Use \c prne_bin_rcb_read()
+ * \see \c prne_bin_rcb_read()
+ */
ssize_t(*read_f)(
prne_bin_rcb_ctx_t *ctx,
uint8_t *buf,
@@ -76,6 +95,13 @@ struct prne_bin_rcb_ctx {
int *err);
};
+/**
+ * \brief The recombination parameter object for initiating binary
+ * recombination. The members are the parameters to \c prne_start_bin_rcb()
+ * call excluding the target info. An instance of this object is set up on
+ * program initialisation and shared globally.
+ * \see \c prne_start_bin_rcb()
+ */
struct prne_rcb_param {
const uint8_t *m_self;
size_t self_len;
@@ -86,20 +112,96 @@ struct prne_rcb_param {
const prne_bin_host_t *self;
};
+/**
+ * \brief The binary archive identity magic "pr-ba"
+ * \see /doc/fmts.md
+ */
static const char PRNE_PACK_BA_IDEN_DATA[] = { 'p', 'r', '-', 'b', 'a' };
+/**
+ * \brief The nybin file format identity magic "nybin"
+ * \see /doc/fmts.md
+ */
static const char PRNE_PACK_NYBIN_IDEN_DATA[] = { 'n', 'y', 'b', 'i', 'n' };
+/**
+ * \brief The equality operator of the executable host info record
+ * \retval true if the contents of the records are equal.
+ * \retval false otherwise.
+ */
bool prne_eq_bin_host (const prne_bin_host_t *a, const prne_bin_host_t *b);
+/**
+ * \brief The in-range operator of the executable host info record. Check both
+ * enums are in range(ie, recognised by the current implementation).
+ * \retval true if the enums are in range.
+ * \retval false otherwise.
+ */
bool prne_bin_host_inrange (const prne_bin_host_t *x);
+/**
+ * \brief Initialise the indexed binary archive object.
+ * \note \p a can be freed using \c prne_free_bin_archive() once initialised.
+ * \see \c prne_free_bin_archive()
+ */
void prne_init_bin_archive (prne_bin_archive_t *a);
+/**
+ * \brief Free resources allocated for the indexed binary archive object.
+ * \see \c prne_init_bin_archive()
+ */
void prne_free_bin_archive (prne_bin_archive_t *a);
+/**
+ * \brief Index the binary archive from the binary.
+ * \param data The binary data, usually the address obtained using \c mmap() on
+ * the executable.
+ * \param len The byte length of the binary data.
+ * \param[out] out The pointer to the binary archive object for index info.
+ * \retval PRNE_PACK_RC_OK The binary archive has been successfully index and
+ * \p out is ready to use.
+ * \retval PRNE_PACK_RC_FMT_ERR The binary could not be parsed due to a format
+ * error.
+ * \retval PRNE_PACK_RC_UNIMPL_REV An unimplemented revision number encountered.
+ * \retval PRNE_PACK_RC_ERRNO A memory allocation error has occurred. \c errno
+ * is set to \c ENOMEM
+ * \note Any resource allocated previously for \p out is freed using
+ * \c prne_free_bin_archive() if the operation is successful.
+ */
prne_pack_rc_t prne_index_bin_archive (
const uint8_t *data,
size_t len,
prne_bin_archive_t *out);
+/**
+ * \brief Initialise the recombination context object.
+ * \see \c prne_free_bin_rcb_ctx()
+ */
void prne_init_bin_rcb_ctx (prne_bin_rcb_ctx_t *ctx);
+/**
+ * \brief Free resources allocated for the recombination context object.
+ * \see \c prne_init_bin_rcb_ctx()
+ */
void prne_free_bin_rcb_ctx (prne_bin_rcb_ctx_t *ctx);
+/**
+ * \brief Initiate binary recombination. Get the recombination context object
+ * ready for \c prne_bin_rcb_read()
+ * \param ctx The recombination context object.
+ * \param target The recombination target host info.
+ * \param self The executable host info record of the running executable.
+ * \param m_self The pointer to the start of the running executable (the image
+ * of the current process). Usually the address obtained using \c mmap()
+ * \param self_len The total byte length of the running executable(the size of
+ * the file).
+ * \param exec_len The byte length of the ELF part of the running executable.
+ * \param m_dvault The pointer to the start of the data vault binary.
+ * \param dvault_len The byte length of the data vault binary.
+ * \param ba The indexed binary archive object.
+ * \retval PRNE_PACK_RC_OK if the initiation was successful.
+ * \retval PRNE_PACK_RC_INVAL if \p ba is NULL, or \p target or \p self is not
+ * in range.
+ * \retval PRNE_PACK_RC_ERRNO if a memory allocation error has occurred and
+ * \c errno is set to \c ENOMEM
+ * \retval PRNE_PACK_RC_NO_ARCH if \p ba does not contain the executable for
+ * \p target
+ * \retval PRNE_PACK_RC_Z_ERR if a zlib function returned an error. Probably
+ * allocation error or an incompatible zlib variant.
+ */
prne_pack_rc_t prne_start_bin_rcb (
prne_bin_rcb_ctx_t *ctx,
const prne_bin_host_t target,
@@ -110,6 +212,14 @@ prne_pack_rc_t prne_start_bin_rcb (
const uint8_t *m_dvault,
const size_t dvault_len,
const prne_bin_archive_t *ba);
+/**
+ * \brief A variant of \c prne_start_bin_rcb() that try to initiate for a
+ * compatible arch target on \c PRNE_PACK_RC_NO_ARCH
+ * \param[out] actual The pointer to the executable host info record for
+ * returning the actual target initiated (optional)
+ * \see \c prne_start_bin_rcb()
+ * \see \c prne_compat_arch()
+ */
prne_pack_rc_t prne_start_bin_rcb_compat (
prne_bin_rcb_ctx_t *ctx,
const prne_bin_host_t target,
@@ -121,6 +231,26 @@ prne_pack_rc_t prne_start_bin_rcb_compat (
const size_t dvault_len,
const prne_bin_archive_t *ba,
prne_bin_host_t *actual);
+/**
+ * \brief Read the recombined binary.
+ * \param ctx The initiated recombination context object.
+ * \param buf The output buffer.
+ * \param len The number of bytes available in \p buf
+ * \param[out] prc The pointer to a pack function result code variable(optional)
+ * \param[out] err The pointer to an int for library function return values
+ * (optional)
+ * \return The number of bytes written to \p buf
+ * \retval 0 with \p prc PRNE_PACK_RC_OK means no data could be produced in a
+ * reasonable amount of CPU time and the function had to return for other
+ * threads. This is not an error and the function may be called again with the
+ * same arguments after yielding to other threads.
+ * \retval 0 with \p prc PRNE_PACK_RC_EOF means all the data for the target
+ * has been produced and the output file can be closed. The subsequent calls
+ * will result in the same return values.
+ * \retval -1 on error. \p ctx cannot be used for read and must be freed or
+ * reinitialised. \p prc is set to either \c PRNE_PACK_RC_ERRNO or
+ * \c PRNE_PACK_RC_Z_ERR
+ */
ssize_t prne_bin_rcb_read (
prne_bin_rcb_ctx_t *ctx,
uint8_t *buf,
@@ -128,6 +258,20 @@ ssize_t prne_bin_rcb_read (
prne_pack_rc_t *prc,
int *err);
+/**
+ * \brief Index the NYBIN file. The file must be mmaped first.
+ * \param[in] m_nybin The pointer to the start of the contents of the NYBIN file.
+ * \param[in] nybin_len The byte length of the contents of the NYBIN file.
+ * \param[out] m_dv The start of the data vault.
+ * \param[out] dv_len The byte length of the data vault.
+ * \param[out] m_ba The start of the binary archive.
+ * \param[out] ba_len The byte length of the binary archive.
+ * \retval true if the parsing was successful and the output parameters are all
+ * set.
+ * \retval false with \c errno set to \c EPROTO on invalid format.
+ * \retval false with \c errno set to \c ENOSYS if the revision of the file is
+ * unrecognised.
+ */
bool prne_index_nybin (
const uint8_t *m_nybin,
const size_t nybin_len,
@@ -136,9 +280,29 @@ bool prne_index_nybin (
const uint8_t **m_ba,
size_t *ba_len);
+/**
+ * \brief Initialise the recombination parameter object. Reserved for any
+ * dynamically allocated members in the future.
+ */
void prne_init_rcb_param (prne_rcb_param_t *rp);
+/**
+ * \brief Free resources allocated for the recombination parameter object.
+ * Reserved for any dynamically allocated members in the future.
+ */
void prne_free_rcb_param (prne_rcb_param_t *rp);
+/**
+ * \brief Get the array of the compatible arches for \p arch
+ * \retval NULL if there's no known compatible arch for \p arch
+ * \return The pointer to an internal array, terminated by \c PRNE_ARCH_NONE
+ * \see \c prne_start_bin_rcb_compat()
+ * \note This function can be used to examine the "compat tree" of the arches.
+ */
const prne_arch_t *prne_compat_arch (const prne_arch_t arch);
+/**
+ * \brief Get the descriptive string for the enum value.
+ * \retval NULL if \p prc is not in range.
+ * \return The pointer to the internal string describing the enum value.
+ */
const char *prne_pack_rc_tostr (const prne_pack_rc_t prc);