fsautoproc
Basic file transformation automation management utility
Loading...
Searching...
No Matches
lcmd.c File Reference

File-specific system command execution mapping implementation. More...

#include "lcmd.h"
#include <assert.h>
#include <errno.h>
#include <regex.h>
#include <stdatomic.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/wait.h>
#include <sysexits.h>
#include <unistd.h>
#include "cJSON/cJSON.h"
#include "jemalloc/jemalloc.h"
#include "fd.h"
#include "je.h"
#include "log.h"
#include "tm.h"
Include dependency graph for lcmd.c:

Functions

static void str_free (str_set_inner_item *str)
 Frees a dynamically allocated string.
 
static void lcmdfree (struct lcmdset_s *cmd)
 Frees the memory allocated for a single command set entry struct.
 
void lcmdfree_r (lcmdset_set *cs)
 Iterates and frees all memory allocated by the command set array.
 
static char * fsreadstr (const char *fp)
 Reads the contents of the file described by filepath fp into a dynamically allocated buffer returned by the function.
 
static str_set * lcmdcopycmds (const cJSON *arr)
 Duplicates a cJSON array of strings into a str_set. Non-string entries will print an error message and cause the entry to be NULL.
 
static int lcmdparseflags (const cJSON *item)
 Parses a cJSON array of strings into a set of file event bit flags. Non-string entries are ignored. Unrecognized string entries will log an error message. Accepted strings are "new", "mod", and "del" which map to LCTRIG_NEW, LCTRIG_MOD, and LCTRIG_DEL respectively.
 
static int lcmdparseone (const cJSON *obj, struct lcmdset_s *cmd, const int id)
 Populates a single command struct by parsing the fields of the provided cJSON object.
 
lcmdset_set * lcmdparse (const char *fp)
 Parses the provided file path and populates an array of command sets. The file must be a valid JSON file containing an array of objects. Each object must contain the following keys:
 
static bool lcmdmatch (regex_set *fpatterns, const char *fp)
 Checks if the provided filepath matches any of the compiled regex patterns in the provided array.
 
bool lcmdmatchany (lcmdset_set *cs, const char *fp)
 Checks if the provided file path matches any of the file patterns in the command set.
 
static int lcmdfailed (const char *src, const int st)
 Checks if the waitpid(2)-style int described by the wait status st failed due to an exit code or signal termination. If so, an appropriate log message is printed using the source description src.
 
static int lcmdinvoke (const char *cmd, const char *fp, struct fdset_s fds, const int flags, _Atomic uint64_t *msspent)
 Invokes a string cmd as a system command using system(3) in a forked/child process. The file path of node is set as an environment variable for use in the command. File descriptor set fds is used to optionally redirect stdout and stderr of the child command processes.
 
int lcmdexec (lcmdset_set *cs, const char *fp, const struct fdset_s fds, int flags)
 Sequentially iterates the command set and executes the configured system commands on the provided file node if the trigger flags and file patterns match.
 

Detailed Description

File-specific system command execution mapping implementation.

Function Documentation

◆ fsreadstr()

static char * fsreadstr ( const char *  fp)
static

Reads the contents of the file described by filepath fp into a dynamically allocated buffer returned by the function.

Parameters
fpThe filepath to read
Returns
If successful, a pointer to a dynamically allocated buffer of the file's null terminated contents. The caller is responsible for freeing the buffer.
Here is the caller graph for this function:

◆ lcmdcopycmds()

static str_set * lcmdcopycmds ( const cJSON *  arr)
static

Duplicates a cJSON array of strings into a str_set. Non-string entries will print an error message and cause the entry to be NULL.

Parameters
arrcJSON array of strings
Returns
NULL if a string could not be duplicated, or the set could not be allocated. Otherwise, a str_set is returned containing the duplicated strings.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdexec()

int lcmdexec ( lcmdset_set *  cs,
const char *  fp,
struct fdset_s  fds,
int  flags 
)

Sequentially iterates the command set and executes the configured system commands on the provided file node if the trigger flags and file patterns match.

Parameters
csThe command set array to filter and execute
fpThe file path to match against the command set
fdsThe file descriptor set to use for stdout/stderr redirection
flagsThe trigger flags to match, see LCTRIG_*. If LCTOPT_VERBOSE is set, the commands will be printed to stdout before execution. If LCTOPT_TRACE is set, the true/false match result for each command set will be printed to stdout.
Returns
0 if successful, otherwise the first non-zero return value from system(3) is returned.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdfailed()

static int lcmdfailed ( const char *  src,
const int  st 
)
static

Checks if the waitpid(2)-style int described by the wait status st failed due to an exit code or signal termination. If so, an appropriate log message is printed using the source description src.

Parameters
srcThe source description of the child process
stThe wait status of the child process
Returns
1 if the value exited or was signaled, otherwise 0.
Here is the caller graph for this function:

◆ lcmdfree()

static void lcmdfree ( struct lcmdset_s cmd)
static

Frees the memory allocated for a single command set entry struct.

Parameters
cmdCommand set entry to free
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdfree_r()

void lcmdfree_r ( lcmdset_set *  cs)

Iterates and frees all memory allocated by the command set array.

Parameters
csThe command set array to free
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdinvoke()

static int lcmdinvoke ( const char *  cmd,
const char *  fp,
struct fdset_s  fds,
const int  flags,
_Atomic uint64_t *  msspent 
)
static

Invokes a string cmd as a system command using system(3) in a forked/child process. The file path of node is set as an environment variable for use in the command. File descriptor set fds is used to optionally redirect stdout and stderr of the child command processes.

Parameters
cmdThe command string to execute
fpThe file path to assign to the FILEPATH environment variable
fdsThe file descriptor set to use for stdout/stderr redirection
flagsBit flags for controlling command execution. If the LCTOPT_VERBOSE flag is set, the command will be printed to stdout before execution. If the LCTOPT_TRACE flag is set, debug information regarding the eligibility of any encountered file path will be printed to stdout.
msspentOptional pointer to a uint64_t value to which the time spent executing the command (in milliseconds) will be added.
Returns
0 if successful, otherwise -1 to indicate an error.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdmatch()

static bool lcmdmatch ( regex_set *  fpatterns,
const char *  fp 
)
static

Checks if the provided filepath matches any of the compiled regex patterns in the provided array.

Parameters
fpatternsArray of compiled regex patterns
fpFilepath to match
Returns
True if the filepath matches any of the patterns, otherwise false.
Here is the caller graph for this function:

◆ lcmdmatchany()

bool lcmdmatchany ( lcmdset_set *  cs,
const char *  fp 
)

Checks if the provided file path matches any of the file patterns in the command set.

Parameters
csThe command set array to filter
fpThe file path to match
Returns
true if the file path matches any file pattern, otherwise false
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdparse()

lcmdset_set * lcmdparse ( const char *  fp)

Parses the provided file path and populates an array of command sets. The file must be a valid JSON file containing an array of objects. Each object must contain the following keys:

  • on: An array of trigger flags to match
  • patterns: An array of file patterns to match
  • commands: An array of system commands to execute The on array must contain one or more of the following strings:
  • new: Trigger on new files
  • mod: Trigger on modified files
  • del: Trigger on deleted files The patterns array must contain one or more strings that are used to match the file path. The commands array must contain one or more strings that are passed to system(3) for execution.
    Parameters
    fpThe file path to parse
    Returns
    An array of command sets if successful, otherwise NULL.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ lcmdparseflags()

static int lcmdparseflags ( const cJSON *  item)
static

Parses a cJSON array of strings into a set of file event bit flags. Non-string entries are ignored. Unrecognized string entries will log an error message. Accepted strings are "new", "mod", and "del" which map to LCTRIG_NEW, LCTRIG_MOD, and LCTRIG_DEL respectively.

Parameters
itemcJSON array of strings
Returns
Bit flags representing the file event types, or 0 if no flags were correctly parsed.
Here is the caller graph for this function:

◆ lcmdparseone()

static int lcmdparseone ( const cJSON *  obj,
struct lcmdset_s cmd,
const int  id 
)
static

Populates a single command struct by parsing the fields of the provided cJSON object.

Parameters
objcJSON object containing the command data
cmdStruct to populate with parsed command data
idCommand set index for naming purposes
Returns
0 if successful, otherwise non-zero to indicate an error.
Here is the call graph for this function:
Here is the caller graph for this function:

◆ str_free()

static void str_free ( str_set_inner_item *  str)
static

Frees a dynamically allocated string.

Parameters
strPointer to the string to free
Note
This function is intended for use with str_set_for_each, which requires a function that takes a pointer to the inner item type.
Here is the caller graph for this function: