Changeset e2ea8d7e in mainline for uspace/app/bdsh/util.c


Ignore:
Timestamp:
2008-08-27T05:36:12Z (16 years ago)
Author:
Tim Post <echo@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
1b4b7b6
Parents:
b510d52
Message:

Housekeeping list, complete lingering things before they get forgotten:

  • cli_*() now sets a global cli_errno, error functions cleaned up
  • Finish internal cli_*() functions in util.c
  • Don't expose cli_init() or cli_finit()
  • Get rid of unused globals
  • Don't set globals in commands themselves
  • Update README files
  • Fix stale comments
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/app/bdsh/util.c

    rb510d52 re2ea8d7e  
    5353#include "util.h"
    5454
     55extern volatile int cli_errno;
     56
    5557/* some platforms do not have strdup, implement it here.
    5658 * Returns a pointer to an allocated string or NULL on failure */
     
    6062        void *ret = malloc(len);
    6163
    62         if (ret == NULL)
     64        if (ret == NULL) {
     65                cli_errno = CL_ENOMEM;
    6366                return (char *) NULL;
    64 
     67        }
     68
     69        cli_errno = CL_EOK;
    6570        return (char *) memcpy(ret, s1, len);
    6671}
     
    8085        *s1 = realloc(*s1, len);
    8186
    82         if (*s1 == NULL)
    83                 return -1;
     87        if (*s1 == NULL) {
     88                cli_errno = CL_ENOMEM;
     89                return -1;
     90        }
    8491
    8592        memset(*s1, 0, sizeof(*s1));
    8693        memcpy(*s1, s2, len);
     94        cli_errno = CL_EOK;
    8795        return (int) len;
    8896}
    8997
    90 /* An asprintf() for concantenating paths. Allocates the system PATH_MAX value,
    91  * expands the formatted string and re-sizes the block s1 points to accordingly.
    92  *
    93  * Returns the length of the new s1 on success, -1 on failure. On failure, an
    94  * attempt is made to return s1 unmodified for sanity, in this case 0 is returned.
    95  * to indicate that s1 was not modified.
    96  *
    97  * FIXME: ugly hack to get around asprintf(), if you use this, CHECK ITS VALUE! */
     98/* An asprintf() for formatting paths, similar to asprintf() but ensures
     99 * the returned allocated string is <= PATH_MAX. On failure, an attempt
     100 * is made to return the original string (if not null) unmodified.
     101 *
     102 * Returns: Length of the new string on success, 0 if the string was handed
     103 * back unmodified, -1 on failure. On failure, cli_errno is set.
     104 *
     105 * We do not use POSIX_PATH_MAX, as it is typically much smaller than the
     106 * PATH_MAX defined by the kernel.
     107 *
     108 * Use this like:
     109 * if (1 > cli_psprintf(&char, "%s/%s", foo, bar)) {
     110 *   cli_error(cli_errno, "Failed to format path");
     111 *   stop_what_your_doing_as_your_out_of_memory();
     112 * }
     113 */
     114
    98115int cli_psprintf(char **s1, const char *fmt, ...)
    99116{
    100117        va_list ap;
    101118        size_t needed, base = PATH_MAX + 1;
     119        int skipped = 0;
     120        char *orig = NULL;
    102121        char *tmp = (char *) malloc(base);
    103122
    104         if (NULL == tmp)
    105                 return -1;
    106 
    107         char *orig = *s1;
    108 
     123        /* Don't even touch s1, not enough memory */
     124        if (NULL == tmp) {
     125                cli_errno = CL_ENOMEM;
     126                return -1;
     127        }
     128
     129        /* If re-allocating s1, save a copy in case we fail */
     130        if (NULL != *s1)
     131                orig = cli_strdup(*s1);
     132
     133        /* Print the string to tmp so we can determine the size that
     134         * we actually need */
    109135        memset(tmp, 0, sizeof(tmp));
    110136        va_start(ap, fmt);
    111         vsnprintf(tmp, base, fmt, ap);
     137        /* vsnprintf will return the # of bytes not written */
     138        skipped = vsnprintf(tmp, base, fmt, ap);
    112139        va_end(ap);
     140
     141        /* realloc/alloc s1 to be just the size that we need */
    113142        needed = strlen(tmp) + 1;
    114143        *s1 = realloc(*s1, needed);
     144
    115145        if (NULL == *s1) {
     146                /* No string lived here previously, or we failed to
     147                 * make a copy of it, either way there's nothing we
     148                 * can do. */
     149                if (NULL == *orig) {
     150                        cli_errno = CL_ENOMEM;
     151                        return -1;
     152                }
     153                /* We can't even allocate enough size to restore the
     154                 * saved copy, just give up */
    116155                *s1 = realloc(*s1, strlen(orig) + 1);
    117156                if (NULL == *s1) {
    118157                        free(tmp);
     158                        free(orig);
     159                        cli_errno = CL_ENOMEM;
    119160                        return -1;
    120161                }
     162                /* Give the string back as we found it */
    121163                memset(*s1, 0, sizeof(*s1));
    122164                memcpy(*s1, orig, strlen(orig) + 1);
    123165                free(tmp);
     166                free(orig);
     167                cli_errno = CL_ENOMEM;
    124168                return 0;
    125169        }
     170
     171        /* Ok, great, we have enough room */
    126172        memset(*s1, 0, sizeof(*s1));
    127173        memcpy(*s1, tmp, needed);
    128174        free(tmp);
    129175
     176        /* Free tmp only if s1 was reallocated instead of allocated */
     177        if (NULL != orig)
     178                free(orig);
     179
     180        if (skipped) {
     181                /* s1 was bigger than PATH_MAX when expanded, however part
     182                 * of the string was printed. Tell the caller not to use it */
     183                cli_errno = CL_ETOOBIG;
     184                return -1;
     185        }
     186
     187        /* Success! */
     188        cli_errno = CL_EOK;
    130189        return (int) needed;
    131190}
     
    137196        int c, sc;
    138197
    139         if (s == NULL && (s = *last) == NULL)
     198        if (s == NULL && (s = *last) == NULL) {
     199                cli_errno = CL_EFAIL;
    140200                return (NULL);
     201        }
    141202
    142203cont:
Note: See TracChangeset for help on using the changeset viewer.