diff options
Diffstat (limited to 'libenv.h')
-rw-r--r-- | libenv.h | 563 |
1 files changed, 563 insertions, 0 deletions
diff --git a/libenv.h b/libenv.h new file mode 100644 index 0000000..a1ac96d --- /dev/null +++ b/libenv.h @@ -0,0 +1,563 @@ +/* See LICENSE file for copyright and license details. */ +#ifndef LIBENV_H +#define LIBENV_H + +#include <stdarg.h> +#include <stddef.h> +#include <stdint.h> + +#if defined(__GNUC__) +# define LIBENV_MALLOC__ __attribute__((__malloc__, __warn_unused_result__)) +# define LIBENV_RET_NONNULL__ __attribute__((__returns_nonnull__, __warn_unused_result__)) +#else +# define LIBENV_MALLOC__ +# define LIBENV_RET_NONNULL__ +#endif + + +/** + * Environment variable class + */ +enum libenv_class { + /** + * Used to mark the end of a class list in + * for a variadic function + */ + LIBENV_END = 0, + + /* Classes: */ + + /** + * Environment variables necessary for the + * graphical environment + */ + LIBENV_DISPLAY, + + /** + * Environment variables that configure + * the graphical environment + */ + LIBENV_DISPLAY_CONFIG, + + /** + * Environment variables that describe + * the desktop environment + */ + LIBENV_DESKTOP, + + /** + * Environment variables that describe + * the terminals capabilities + */ + LIBENV_TERMINAL_CAPS, + + /** + * Environment variables that describe + * the terminals but is only meaningful + * for the local host + */ + LIBENV_LOCAL_TERMINAL, + + /** + * Environment variables that configure + * the locale + */ + LIBENV_LOCALE, + + /** + * Environment variables that configure + * the timezone + */ + LIBENV_TIMEZONE, + + /** + * Environment variables that describe + * the current session + * + * This for example includes variables + * added by SSH to describe the remote + * connection + * + * This does not include display, desktop, + * or terminal information, nor does + * include information to identify the + * user + */ + LIBENV_SESSION, + + /** + * Environment variables that configure + * the user's theme + * + * This is excludes variables listed + * for LIBENV_THEME_PLUGIN except in the + * hypothetical scenario where it names + * a plugin and additional configurations + */ + LIBENV_THEME_CONFIG, + + /** + * Environment variables that describe + * the plugins the user's theme requires + */ + LIBENV_THEME_PLUGIN, + + /** + * Environment variables that configures + * the user's internet configurations, + * including mainly proxies + */ + LIBENV_INTERNET, + + /** + * Environment variables that configures + * the user's audio + */ + LIBENV_AUDIO, + + /** + * Environment variables that describe + * any information gathered about the + * user from passwd(5) or login parameters + */ + LIBENV_USER, + + /** + * Environment variables that default + * applications configured for the user + */ + LIBENV_APPLICATIONS, + + /** + * Environment variables that configure + * preferences, for the user, for various + * applications + */ + LIBENV_PREFERENCES, + + /** + * Environment variables that list directories + * configured system wide (but could be + * overwritten for the user) + * + * Environment variables with this classification + * has at least also LIBENV_PATH + */ + LIBENV_SYSTEM_PATHS, + + /** + * Environment variables that list directories + * configured for the user + * + * Environment variables with this classification + * has at least also LIBENV_PATH + */ + LIBENV_USER_PATHS, + + /** + * Environment variables that contain + * current and past working directories + * + * Environment variables with this classification + * has at least also LIBENV_PATH + */ + LIBENV_PWD, + + /** + * Environment variables that contain + * information about the executed utility + */ + LIBENV_EXEC, + + /** + * Environment variables that contain + * filesystem paths + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_PATH, + + /** + * Environment variables that should be removed + * when entering a remote session + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_REMOTE_UNSAFE, + + /** + * Environment variables that should be can + * safely be kepted when entering a remote + * session + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_REMOTE_SAFE, + + /** + * Environment variables that should be removed + * when entering a logging into a new user + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_LOGIN_UNSAFE, + + /** + * Environment variables that should be can + * safely be kepted when entering a logging + * into a new user + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_LOGIN_SAFE, + + /** + * Environment variables that should be removed + * when escalating privileges + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_SU_UNSAFE, + + /** + * Environment variables that should be can + * safely be kepted when escalating privileges + * + * Any environment variable with this + * classification has at least one other + * classification + */ + LIBENV_SU_SAFE /* = 26 */ +}; + +/** + * Environment variable name and classification + */ +struct libenv_variable { + /** + * The name of the environment variable + */ + const char *name; + + /** + * Bitset of `enum libenv_class`'s the variable + * is classified under + * + * For any value `c` in `enum libenv_class` except + * `LIBENV_END`, `(.classes[c / 64] >> (c % 64)) & 1` + * is 1 iff the variable belongs to the class; however + * the application must verify that `c / 64` is less + * than the value output by `libenv_get_complete_list` + * to its first argument + * + * For the sake of simplicity, the lowest-valued bit + * in the first `uint64_t` is always 0 + */ + const uint64_t *classes; +}; + + +/** + * Get the list of recognised environment variable, + * the list will container their names and classes + * + * This function does not read the current environment, + * and may return unset environemnt variables + * + * @param nclasswords_out Output parameter for the number of elements in each returned + * `struct libenv_variable`'s `.classes`, may be `NULL` + * @param count_out Output parameter for the number of elements in the returned list, + * sans a terminal `{NULL, NULL}` element, may be `NULL` + * @return Statically allocated list of all recognised environment variables + */ +LIBENV_RET_NONNULL__ const struct libenv_variable *libenv_get_complete_list(size_t *nclasswords_out, size_t *count_out); + +/** + * Get a list of environment variables names (which need not be set + * in the current environment) that fall into either of the specified + * variable classes + * + * @param classes_head,classes_tail List of variable classes, must end with `LIBENV_END` + * @return List of unique environment variable names, the caller should + * deallocate the returned list, when done with it, using the + * free(3) function, however the elements of the list are + * statically allocated and should not be deallocated or modified, + * `NULL` on failure + * + * @throws ENOMEM Not enought memory available to allocate the list + */ +LIBENV_MALLOC__ const char **libenv_vget_chosen_list(enum libenv_class, va_list); + +/** + * Get a list of environment variables names (which need not be set + * in the current environment) that fall into either of the specified + * variable classes + * + * @param classes_head... List of variable classes, must end with `LIBENV_END` + * @return List of unique environment variable names, the caller should + * deallocate the returned list, when done with it, using the + * free(3) function, however the elements of the list are + * statically allocated and should not be deallocated or modified, + * `NULL` on failure + * + * @throws ENOMEM Not enought memory available to allocate the list + */ +LIBENV_MALLOC__ const char **libenv_get_chosen_list(enum libenv_class, ... /*, LIBENV_END */); + +/** + * Given a list of environment variable names, remove the variables + * that belong to all of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vfilter_name_list(const char **, va_list); + +/** + * Given a list of environment variable names, remove the variables + * that belong to all of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_filter_name_list(const char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variables, with values, remove the variables + * that belong to all of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vfilter_variable_list(const char **, va_list); + +/** + * Given a list of environment variables, with values, remove the variables + * that belong to all of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_filter_variable_list(const char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variable names, remove any variable that + * does not belong to any of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vselect_name_list(const char **, va_list); + +/** + * Given a list of environment variable names, remove any variable that + * does not belong to any of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_select_name_list(const char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variables, with values, remove any variable + * that does not belong to any of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vselect_variable_list(const char **, va_list); + +/** + * Given a list of environment variables, with values, remove any variable + * that does not belong to any of the specified environment variable classes + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_select_variable_list(const char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variable names, remove the variables + * that belong to all of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vfilter_name_list_with_dealloc(char **, va_list); + +/** + * Given a list of environment variable names, remove the variables + * that belong to all of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_filter_name_list_with_dealloc(char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variables, with values, remove the variables + * that belong to all of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vfilter_variable_list_with_dealloc(char **, va_list); + +/** + * Given a list of environment variables, with values, remove the variables + * that belong to all of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_filter_variable_list_with_dealloc(char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variable names, remove any variable that + * does not belong to any of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vselect_name_list_with_dealloc(char **, va_list); + +/** + * Given a list of environment variable names, remove any variable that + * does not belong to any of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variable names; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_select_name_list_with_dealloc(char **, /* enum libenv_class */ ... /*, LIBENV_END */); + +/** + * Given a list of environment variables, with values, remove any variable + * that does not belong to any of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param classes The list of environment variable classes, must end with `LIBENV_END` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_vselect_variable_list_with_dealloc(char **, va_list); + +/** + * Given a list of environment variables, with values, remove any variable + * that does not belong to any of the specified environment variable classes + * + * Any element removed from `variables` will be deallocated using + * the free(3) function + * + * @param variables `NULL`-terminated list environemnt variables; may be `NULL`, + * which causes the function to return 0; unless `NULL` the list + * will be updated + * @param ... The list of environment variable classes, must end with `LIBENV_END`, + * each argument must have the type `enum libenv_class` + * @return The new number of elements in `variables`; `variables[return]` will + * be `NULL` provided that `variables` itself it not `NULL` + */ +size_t libenv_select_variable_list_with_dealloc(char **, /* enum libenv_class */ ... /*, LIBENV_END */); + + +#undef LIBENV_MALLOC__ +#undef LIBENV_RET_NONNULL__ + +#endif |