diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/artifactory.c | 15 | ||||
| -rw-r--r-- | src/docker.c | 4 | ||||
| -rw-r--r-- | src/ini.c | 2 | ||||
| -rw-r--r-- | src/str.c | 154 | ||||
| -rw-r--r-- | src/strlist.c | 239 | ||||
| -rw-r--r-- | src/system.c | 54 | ||||
| -rw-r--r-- | src/template.c | 54 | ||||
| -rw-r--r-- | src/utils.c | 38 | 
8 files changed, 362 insertions, 198 deletions
| diff --git a/src/artifactory.c b/src/artifactory.c index 4772602..5678d64 100644 --- a/src/artifactory.c +++ b/src/artifactory.c @@ -229,16 +229,15 @@ int jfrog_cli(struct JFRT_Auth *auth, char *args) {      }      const char *redactable[] = { -            "--access-token=", -            "--ssh-key-path=", -            "--ssh-passphrase=", -            "--client-cert-key-path=", -            "--client-cert-path=", -            "--password=", -            NULL, +            auth->access_token, +            auth->ssh_key_path, +            auth->ssh_passphrase, +            auth->client_cert_key_path, +            auth->client_cert_path, +            auth->password,      };      snprintf(cmd, sizeof(cmd) - 1, "jf %s %s", args, auth_args); -    redact_sensitive(redactable, cmd, cmd_redacted, sizeof(cmd_redacted) - 1); +    redact_sensitive(redactable, sizeof(redactable) / sizeof (*redactable), cmd, cmd_redacted, sizeof(cmd_redacted) - 1);      guard_free(auth_args);      guard_strlist_free(&arg_map); diff --git a/src/docker.c b/src/docker.c index f8c9c11..308fbc7 100644 --- a/src/docker.c +++ b/src/docker.c @@ -28,7 +28,7 @@ int docker_script(const char *image, char *data, unsigned flags) {      char buffer[OMC_BUFSIZ];      memset(cmd, 0, sizeof(cmd)); -    snprintf(cmd, sizeof(cmd) - 1, "docker run --rm -i %s /bin/bash -", image); +    snprintf(cmd, sizeof(cmd) - 1, "docker run --rm -i %s /bin/sh -", image);      outfile = popen(cmd, "w");      if (!outfile) { @@ -103,7 +103,7 @@ static int docker_exists() {      return false;  } -char *docker_ident() { +static char *docker_ident() {      FILE *fp = NULL;      char *tempfile = NULL;      char line[PATH_MAX]; @@ -16,7 +16,7 @@ void ini_section_init(struct INIFILE **ini) {      (*ini)->section = calloc((*ini)->section_count + 1, sizeof(**(*ini)->section));  } -struct INISection *ini_section_search(struct INIFILE **ini, unsigned mode, char *value) { +struct INISection *ini_section_search(struct INIFILE **ini, unsigned mode, const char *value) {      struct INISection *result = NULL;      for (size_t i = 0; i < (*ini)->section_count; i++) {          if ((*ini)->section[i]->key != NULL) { @@ -16,7 +16,7 @@ int num_chars(const char *sptr, int ch) {  int startswith(const char *sptr, const char *pattern) {      if (!sptr || !pattern) { -        return -1; +        return 0;      }      for (size_t i = 0; i < strlen(pattern); i++) {          if (sptr[i] != pattern[i]) { @@ -26,10 +26,9 @@ int startswith(const char *sptr, const char *pattern) {      return 1;  } -  int endswith(const char *sptr, const char *pattern) {      if (!sptr || !pattern) { -        return -1; +        return 0;      }      ssize_t sptr_size = (ssize_t) strlen(sptr);      ssize_t pattern_size = (ssize_t) strlen(pattern); @@ -61,64 +60,10 @@ void strchrdel(char *sptr, const char *chars) {          return;      } -    while (*sptr != '\0') { -        for (int i = 0; chars[i] != '\0'; i++) { -            if (*sptr == chars[i]) { -                memmove(sptr, sptr + 1, strlen(sptr)); -            } -        } -        sptr++; -    } -} - - -long int strchroff(const char *sptr, int ch) { -    char *orig = strdup(sptr); -    char *tmp = orig; -    long int result = 0; - -    int found = 0; -    size_t i = 0; - -    while (*tmp != '\0') { -        if (*tmp == ch) { -            found = 1; -            break; -        } -        tmp++; -        i++; -    } - -    if (found == 0 && i == strlen(sptr)) { -        return -1; -    } - -    result = tmp - orig; -    guard_free(orig); - -    return result; -} - -void strdelsuffix(char *sptr, const char *suffix) { -    if (!sptr || !suffix) { -        return; -    } -    size_t sptr_len = strlen(sptr); -    size_t suffix_len = strlen(suffix); -    intptr_t target_offset = sptr_len - suffix_len; - -    // Prevent access to memory below input string -    if (target_offset < 0) { -        return; -    } - -    // Create a pointer to -    char *target = sptr + target_offset; -    if (!strcmp(target, suffix)) { -        // Purge the suffix -        memset(target, '\0', suffix_len); -        // Recursive call continues removing suffix until it is gone -        strip(sptr); +    for (size_t i = 0; i < strlen(chars); i++) { +        char ch[2] = {0}; +        strncpy(ch, &chars[i], 1); +        replace_text(sptr, ch, "", 0);      }  } @@ -141,7 +86,7 @@ char** split(char *_sptr, const char* delim, size_t max)          if (max && i > max) {              break;          } -        split_alloc = num_chars(sptr, delim[i]); +        split_alloc += num_chars(sptr, delim[i]);      }      // Preallocate enough records based on the number of delimiters @@ -158,27 +103,35 @@ char** split(char *_sptr, const char* delim, size_t max)      }      // Separate the string into individual parts and store them in the result array -    int i = 0; -    size_t x = max;      char *token = NULL;      char *sptr_tmp = sptr; -    while((token = strsep(&sptr_tmp, delim)) != NULL) { -        result[i] = calloc(OMC_BUFSIZ, sizeof(char)); -        if (x < max) { -            strcat(result[i], strstr(orig, delim) + 1); +    size_t pos = 0; +    size_t i; +    for (i = 0; (token = strsep(&sptr_tmp, delim)) != NULL; i++) { +        // When max is zero, record all tokens +        if (max > 0 && i == max) { +            // Maximum number of splits occurred. +            // Record position in string +            pos = token - sptr;              break; -        } else { -            if (!result[i]) { -                return NULL; -            } -            strcpy(result[i], token);          } -        i++; -        if (x > 0) { -            --x; +        result[i] = calloc(OMC_BUFSIZ, sizeof(char)); +        if (!result[i]) { +            return NULL;          } -        //memcpy(result[i], token, strlen(token) + 1);   // copy the string contents into the record +        strcpy(result[i], token);      } + +    // pos is non-zero when maximum split is reached +    if (pos) { +        // append the remaining string contents to array +        result[i] = calloc(OMC_BUFSIZ, sizeof(char)); +        if (!result[i]) { +            return NULL; +        } +        strcpy(result[i], &orig[pos]); +    } +      guard_free(sptr);      return result;  } @@ -244,8 +197,9 @@ char *join_ex(char *separator, ...) {          if (tmp == NULL) {              perror("join_ex realloc failed");              return NULL; +        } else if (tmp != argv) { +            argv = tmp;          } -        argv = tmp;          size += strlen(current) + separator_len;          argv[argc] = strdup(current);      } @@ -275,43 +229,37 @@ char *substring_between(char *sptr, const char *delims) {      // Ensure we have enough delimiters to continue      size_t delim_count = strlen(delims); -    if (delim_count != 2) { +    if (delim_count < 2 || delim_count % 2) {          return NULL;      } +    char delim_open[255] = {0}; +    strncpy(delim_open, delims, delim_count / 2); + +    char delim_close[255] = {0}; +    strcpy(delim_close, &delims[delim_count / 2]); +      // Create pointers to the delimiters -    char *start = strchr(sptr, delims[0]); +    char *start = strstr(sptr, delim_open);      if (start == NULL || strlen(start) == 0) {          return NULL;      } -    char *end = strchr(start + 1, delims[1]); +    char *end = strstr(start + 1, delim_close);      if (end == NULL) {          return NULL;      } -    start++;    // ignore leading delimiter +    start += delim_count / 2;    // ignore leading delimiter      // Get length of the substring -    size_t length = strlen(start); +    size_t length = strlen(start) - strlen(end);      if (!length) {          return NULL;      } -    char *result = (char *)calloc(length + 1, sizeof(char)); -    if (!result) { -        return NULL; -    } - -    // Copy the contents of the substring to the result -    char *tmp = result; -    while (start != end) { -        *tmp = *start; -        tmp++; -        start++; -    } - -    return result; +    // Return the contents of the substring +    return strndup(start, length);  }  /* @@ -476,19 +424,16 @@ char *strip(char *sptr) {      size_t len = strlen(sptr);      if (len == 0) {          return sptr; -    } -    else if (len == 1 && (isblank(*sptr) || isspace(*sptr))) { +    } else if (len == 1 && (isblank(*sptr) || isspace(*sptr))) {          *sptr = '\0';          return sptr; -    } -    for (size_t i = len; i != 0; --i) { +    } for (size_t i = len; i != 0; --i) {          if (sptr[i] == '\0') {              continue;          }          if (isspace(sptr[i]) || isblank(sptr[i])) {              sptr[i] = '\0'; -        } -        else { +        } else {              break;          }      } @@ -665,6 +610,9 @@ int strcmp_array(const char **a, const char **b) {  }  int isdigit_s(const char *s) { +    if (!s || !strlen(s)) { +        return 0;   // nothing to do, fail +    }      for (size_t i = 0; s[i] != '\0'; i++) {          if (isdigit(s[i]) == 0) {              return 0;   // non-digit found, fail diff --git a/src/strlist.c b/src/strlist.c index d54ed06..bdacb5a 100644 --- a/src/strlist.c +++ b/src/strlist.c @@ -3,7 +3,6 @@   * @file strlist.c   */  #include "strlist.h" -//#include "url.h"  #include "utils.h"  /** @@ -71,6 +70,7 @@ int strlist_append_file(struct StrList *pStrList, char *_path, ReaderFn *readerF      char *path = NULL;      char *filename = NULL;      char **data = NULL; +    int is_url = strstr(_path, "://") != NULL;      if (readerFn == NULL) {          readerFn = reader_strlist_append_file; @@ -78,17 +78,31 @@ int strlist_append_file(struct StrList *pStrList, char *_path, ReaderFn *readerF      path = strdup(_path);      if (path == NULL) { -          retval = -1;          goto fatal;      } -    filename = expandpath(path); - -    if (filename == NULL) { - -        retval = -1; -        goto fatal; +    if (is_url) { +        int fd; +        char tempfile[PATH_MAX] = {0}; +        strcpy(tempfile, "/tmp/.remote_file.XXXXXX"); +        if ((fd = mkstemp(tempfile)) < 0) { +            retval = -1; +            goto fatal; +        } +        close(fd); +        filename = strdup(tempfile); +        long http_code = download(path, filename, NULL); +        if (HTTP_ERROR(http_code)) { +            retval = -1; +            goto fatal; +        } +    } else { +        filename = expandpath(path); +        if (filename == NULL) { +            retval = -1; +            goto fatal; +        }      }      data = file_readlines(filename, 0, 0, readerFn); @@ -96,17 +110,18 @@ int strlist_append_file(struct StrList *pStrList, char *_path, ReaderFn *readerF          retval = 1;          goto fatal;      } -      for (size_t record = 0; data[record] != NULL; record++) {          strlist_append(&pStrList, data[record]);          guard_free(data[record]);      } +    if (is_url) { +        // remove temporary data +        remove(filename); +    }      guard_free(data);  fatal: -    if (filename != NULL) { -        guard_free(filename); -    } +    guard_free(filename);      if (path != NULL) {          guard_free(path);      } @@ -115,7 +130,7 @@ fatal:  }  /** - * Append the contents of a `StrList` to another `StrList` + * Append the contents of `pStrList2` to `pStrList1`   * @param pStrList1 `StrList`   * @param pStrList2 `StrList`   */ @@ -200,16 +215,14 @@ void strlist_remove(struct StrList *pStrList, size_t index) {      if (count == 0) {          return;      } - -    for (size_t i = index; i < count; i++) { -        char *next = pStrList->data[i + 1]; -        pStrList->data[i] = next; -        if (next == NULL) { -            break; +    if (pStrList->data[index] != NULL) { +        for (size_t i = index; i < count; i++) { +            pStrList->data[i] = pStrList->data[i + 1]; +        } +        if (pStrList->num_inuse) { +            pStrList->num_inuse--;          }      } - -    pStrList->num_inuse--;  }  /** @@ -227,13 +240,10 @@ int strlist_cmp(struct StrList *a, struct StrList *b) {          return -2;      } -    if (a->num_alloc != b->num_alloc) { +    if (a->num_alloc != b->num_alloc || a->num_inuse != b->num_inuse) {          return 1;      } -    if (a->num_inuse != b->num_inuse) { -        return 1; -    }      for (size_t i = 0; i < strlist_count(a); i++) {          if (strcmp(strlist_item(a, i), strlist_item(b, i)) != 0) { @@ -321,6 +331,29 @@ void strlist_set(struct StrList **pStrList, size_t index, char *value) {      }  } +const char *strlist_error_msgs[] = { +        "success", +        "index out of range", +        "invalid value for type", +        "unknown error", +}; +int strlist_errno = 0; + +void strlist_set_error(int flag) { +    strlist_errno = flag; +} + +const char *strlist_get_error(int flag) { +    if (flag < STRLIST_E_SUCCESS || flag > STRLIST_E_UNKNOWN) { +        return strlist_error_msgs[STRLIST_E_UNKNOWN]; +    } +    return strlist_error_msgs[flag]; +} + +void strlist_clear_error() { +    strlist_errno = STRLIST_E_SUCCESS; +} +  /**   * Retrieve data from a `StrList`   * @param pStrList @@ -351,7 +384,17 @@ char *strlist_item_as_str(struct StrList *pStrList, size_t index) {   * @return `char`   */  char strlist_item_as_char(struct StrList *pStrList, size_t index) { -    return (char) strtol(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    char result; + +    strlist_clear_error(); +    result = (char) strtol(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -361,7 +404,17 @@ char strlist_item_as_char(struct StrList *pStrList, size_t index) {   * @return `unsigned char`   */  unsigned char strlist_item_as_uchar(struct StrList *pStrList, size_t index) { -    return (unsigned char) strtol(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    unsigned char result; + +    strlist_clear_error(); +    result = (unsigned char) strtoul(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -371,7 +424,17 @@ unsigned char strlist_item_as_uchar(struct StrList *pStrList, size_t index) {   * @return `short`   */  short strlist_item_as_short(struct StrList *pStrList, size_t index) { -    return (short)strtol(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    short result; + +    strlist_clear_error(); +    result = (short) strtol(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -381,7 +444,17 @@ short strlist_item_as_short(struct StrList *pStrList, size_t index) {   * @return `unsigned short`   */  unsigned short strlist_item_as_ushort(struct StrList *pStrList, size_t index) { -    return (unsigned short)strtoul(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    unsigned short result; + +    strlist_clear_error(); +    result = (unsigned short) strtoul(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -391,7 +464,17 @@ unsigned short strlist_item_as_ushort(struct StrList *pStrList, size_t index) {   * @return `int`   */  int strlist_item_as_int(struct StrList *pStrList, size_t index) { -    return (int)strtol(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    int result; + +    strlist_clear_error(); +    result = (int) strtol(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -401,7 +484,17 @@ int strlist_item_as_int(struct StrList *pStrList, size_t index) {   * @return `unsigned int`   */  unsigned int strlist_item_as_uint(struct StrList *pStrList, size_t index) { -    return (unsigned int)strtoul(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    unsigned int result; + +    strlist_clear_error(); +    result = (unsigned int) strtoul(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -411,7 +504,17 @@ unsigned int strlist_item_as_uint(struct StrList *pStrList, size_t index) {   * @return `long`   */  long strlist_item_as_long(struct StrList *pStrList, size_t index) { -    return strtol(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    long result; + +    strlist_clear_error(); +    result = (long) strtol(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -421,7 +524,17 @@ long strlist_item_as_long(struct StrList *pStrList, size_t index) {   * @return `unsigned long`   */  unsigned long strlist_item_as_ulong(struct StrList *pStrList, size_t index) { -    return strtoul(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    unsigned long result; + +    strlist_clear_error(); +    result = (unsigned long) strtoul(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -431,7 +544,17 @@ unsigned long strlist_item_as_ulong(struct StrList *pStrList, size_t index) {   * @return `long long`   */  long long strlist_item_as_long_long(struct StrList *pStrList, size_t index) { -    return strtoll(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    long long result; + +    strlist_clear_error(); +    result = (long long) strtoll(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -441,7 +564,17 @@ long long strlist_item_as_long_long(struct StrList *pStrList, size_t index) {   * @return `unsigned long long`   */  unsigned long long strlist_item_as_ulong_long(struct StrList *pStrList, size_t index) { -    return strtoull(strlist_item(pStrList, index), NULL, 10); +    char *error_p; +    unsigned long long result; + +    strlist_clear_error(); +    result = (unsigned long long) strtol(strlist_item(pStrList, index), &error_p, 10); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -451,7 +584,17 @@ unsigned long long strlist_item_as_ulong_long(struct StrList *pStrList, size_t i   * @return `float`   */  float strlist_item_as_float(struct StrList *pStrList, size_t index) { -    return (float)atof(strlist_item(pStrList, index)); +    char *error_p; +    float result; + +    strlist_clear_error(); +    result = (float) strtof(strlist_item(pStrList, index), &error_p); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -461,7 +604,17 @@ float strlist_item_as_float(struct StrList *pStrList, size_t index) {   * @return `double`   */  double strlist_item_as_double(struct StrList *pStrList, size_t index) { -    return atof(strlist_item(pStrList, index)); +    char *error_p; +    double result; + +    strlist_clear_error(); +    result = (double) strtod(strlist_item(pStrList, index), &error_p); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** @@ -471,7 +624,17 @@ double strlist_item_as_double(struct StrList *pStrList, size_t index) {   * @return `long double`   */  long double strlist_item_as_long_double(struct StrList *pStrList, size_t index) { -    return (long double)atof(strlist_item(pStrList, index)); +    char *error_p; +    long double result; + +    strlist_clear_error(); +    result = (long double) strtold(strlist_item(pStrList, index), &error_p); +    if (!result && error_p && *error_p != 0) { +        strlist_set_error(STRLIST_E_INVALID_VALUE); +        return 0; +    } +    error_p = NULL; +    return result;  }  /** diff --git a/src/system.c b/src/system.c index ca2da97..d5e77ce 100644 --- a/src/system.c +++ b/src/system.c @@ -1,11 +1,8 @@ -// -// Created by jhunk on 10/4/23. -// -  #include "system.h"  #include "omc.h"  int shell(struct Process *proc, char *args) { +    struct Process selfproc;      FILE *fp_out = NULL;      FILE *fp_err = NULL;      pid_t pid; @@ -13,6 +10,18 @@ int shell(struct Process *proc, char *args) {      status = 0;      errno = 0; +    if (!proc) { +        // provide our own proc structure +        // albeit not accessible to the user +        memset(&selfproc, 0, sizeof(selfproc)); +        proc = &selfproc; +    } + +    if (!args) { +        proc->returncode = -1; +        return -1; +    } +      FILE *tp = NULL;      char *t_name;      t_name = xmkstemp(&tp, "w"); @@ -31,22 +40,20 @@ int shell(struct Process *proc, char *args) {          exit(1);      } else if (pid == 0) {          int retval; -        if (proc != NULL) { -            if (strlen(proc->f_stdout)) { -                fp_out = freopen(proc->f_stdout, "w+", stdout); -            } +        if (strlen(proc->f_stdout)) { +            fp_out = freopen(proc->f_stdout, "w+", stdout); +        } -            if (strlen(proc->f_stderr)) { -                fp_err = freopen(proc->f_stderr, "w+", stderr); -            } +        if (strlen(proc->f_stderr)) { +            fp_err = freopen(proc->f_stderr, "w+", stderr); +        } -            if (proc->redirect_stderr) { -                if (fp_err) { -                    fclose(fp_err); -                    fclose(stderr); -                } -                dup2(fileno(stdout), fileno(stderr)); +        if (proc->redirect_stderr) { +            if (fp_err) { +                fclose(fp_err); +                fclose(stderr);              } +            dup2(fileno(stdout), fileno(stderr));          }          retval = execl("/bin/bash", "bash", "-c", t_name, (char *) NULL); @@ -54,7 +61,7 @@ int shell(struct Process *proc, char *args) {              remove(t_name);          } -        if (proc != NULL && strlen(proc->f_stdout)) { +        if (strlen(proc->f_stdout)) {              if (fp_out != NULL) {                  fflush(fp_out);                  fclose(fp_out); @@ -62,7 +69,7 @@ int shell(struct Process *proc, char *args) {              fflush(stdout);              fclose(stdout);          } -        if (proc != NULL && strlen(proc->f_stderr)) { +        if (strlen(proc->f_stderr)) {              if (fp_err) {                  fflush(fp_err);                  fclose(fp_err); @@ -89,10 +96,7 @@ int shell(struct Process *proc, char *args) {          remove(t_name);      } -    if (proc != NULL) { -        proc->returncode = status; -    } - +    proc->returncode = status;      guard_free(t_name);      return WEXITSTATUS(status);  } @@ -102,7 +106,7 @@ int shell_safe(struct Process *proc, char *args) {      char buf[1024] = {0};      int result; -    char *invalid_ch = strpbrk(args, ";&|()"); +    char *invalid_ch = strpbrk(args, OMC_SHELL_SAFE_RESTRICT);      if (invalid_ch) {          args = NULL;      } @@ -168,6 +172,6 @@ char *shell_output(const char *command, int *status) {          strcat(result, line);          memset(line, 0, sizeof(line));      } -    pclose(pp); +    *status = pclose(pp);      return result;  }
\ No newline at end of file diff --git a/src/template.c b/src/template.c index 6101338..0a57232 100644 --- a/src/template.c +++ b/src/template.c @@ -16,9 +16,14 @@ struct tpl_item {  };  struct tpl_item *tpl_pool[1024] = {0};  unsigned tpl_pool_used = 0; +struct tplfunc_frame *tpl_pool_func[1024] = {0};  unsigned tpl_pool_func_used = 0; -struct tplfunc_frame *tpl_pool_func[1024] = {0}; +extern void tpl_reset() { +    tpl_free(); +    tpl_pool_used = 0; +    tpl_pool_func_used = 0; +}  void tpl_register_func(char *key, struct tplfunc_frame *frame) {      (void) key;  // TODO: placeholder @@ -86,6 +91,10 @@ void tpl_free() {          }          guard_free(item);      } +    for (unsigned i = 0; i < tpl_pool_func_used; i++) { +        struct tplfunc_frame *item = tpl_pool_func[i]; +        guard_free(item); +    }  }  char *tpl_getval(char *key) { @@ -167,7 +176,9 @@ char *tpl_render(char *str) {              size_t key_len = 0;              while (isalnum(pos[off]) || pos[off] != '}') {                  if (isspace(pos[off]) || isblank(pos[off])) { -                    break; +                    // skip whitespace in key +                    off++; +                    continue;                  }                  key[key_len] = pos[off];                  key_len++; @@ -205,7 +216,44 @@ char *tpl_render(char *str) {                  char *env_val = getenv(key);                  value = strdup(env_val ? env_val : "");              } else if (do_func) { // {{ func:NAME(a, ...) }} -                // TODO +                char func_name_temp[OMC_NAME_MAX] = {0}; +                strcpy(func_name_temp, type_stop + 1); +                char *param_begin = strchr(func_name_temp, '('); +                if (!param_begin) { +                    fprintf(stderr, "offset %zu: function name must be followed by a '('\n", off); +                    guard_free(output); +                    return NULL; +                } +                *param_begin = 0; +                param_begin++; +                char *param_end = strrchr(param_begin, ')'); +                if (!param_end) { +                    fprintf(stderr, "offset %zu: function arguments must be closed with a ')'\n", off); +                    guard_free(output); +                    return NULL; +                } +                *param_end = 0; +                char *k = func_name_temp; +                char **params = split(param_begin, ",", 0); +                int params_count; +                for (params_count = 0; params[params_count] != NULL; params_count++); + +                struct tplfunc_frame *frame = tpl_getfunc(k); +                if (params_count > frame->argc) { +                    fprintf(stderr, "offset %zu: Too many arguments for function: %s()\n", off, frame->key); +                    value = strdup(""); +                } else { +                    for (size_t p = 0; p < sizeof(frame->argv) / sizeof(*frame->argv) && params[p] != NULL; p++) { +                        lstrip(params[p]); +                        strip(params[p]); +                        frame->argv[p].t_char_ptr = params[p]; +                    } +                    char func_result[100]; +                    char *fres = func_result; +                    frame->func(frame, fres); +                    value = strdup(fres); +                } +                GENERIC_ARRAY_FREE(params);              } else {                  // Read replacement value                  value = strdup(tpl_getval(key) ? tpl_getval(key) : ""); diff --git a/src/utils.c b/src/utils.c index 7cc3e6e..86622ad 100644 --- a/src/utils.c +++ b/src/utils.c @@ -6,9 +6,15 @@ const ssize_t dirstack_max = sizeof(dirstack) / sizeof(dirstack[0]);  ssize_t dirstack_len = 0;  int pushd(const char *path) { +    if (access(path, F_OK)) { +        // the requested path doesn't exist. +        return -1; +    }      if (dirstack_len + 1 > dirstack_max) { +        // the stack is full          return -1;      } +      dirstack[dirstack_len] = realpath(".", NULL);      dirstack_len++;      return chdir(path); @@ -151,7 +157,7 @@ char *path_dirname(char *path) {      if (!pos) {          return ".";      } -    *path = '\0'; +    *pos = '\0';      return path;  } @@ -701,30 +707,26 @@ char *collapse_whitespace(char **s) {   * @param maxlen maximum length of dest string   * @return 0 on success, -1 on error   */ -int redact_sensitive(const char **to_redact, char *src, char *dest, size_t maxlen) { -    char **parts = split(src, " ", 0); -    if (!parts) { -        fprintf(stderr, "Unable to split source string\n"); +int redact_sensitive(const char **to_redact, size_t to_redact_size, char *src, char *dest, size_t maxlen) { +    const char *redacted = "***REDACTED***"; + +    char *tmp = calloc(strlen(redacted) + strlen(src) + 1, sizeof(*tmp)); +    if (!tmp) {          return -1;      } +    strcpy(tmp, src); -    for (size_t i = 0; to_redact[i] != NULL; i++) { -        for (size_t p = 0; parts[p] != NULL; p++) { -            if (strstr(parts[p], to_redact[i])) { -                replace_text(parts[p], to_redact[i], "***REDACTED***", REPLACE_TRUNCATE_AFTER_MATCH); -            } +    for (size_t i = 0; i < to_redact_size; i++) { +        if (to_redact[i] && strstr(tmp, to_redact[i])) { +            replace_text(tmp, to_redact[i], redacted, 0); +            break;          }      } -    char *dest_tmp = join(parts, " "); -    if (!dest_tmp) { -        fprintf(stderr, "Unable to join message array\n"); -        return -1; -    } -    strncpy(dest, dest_tmp, maxlen); +    memset(dest, 0, maxlen); +    strncpy(dest, tmp, maxlen - 1); +    guard_free(tmp); -    GENERIC_ARRAY_FREE(parts); -    guard_free(dest_tmp);      return 0;  } | 
