/* * Copyright (c) 2003-2005 Sendmail, Inc. and its suppliers. * All rights reserved. * * By using this file, you agree to the terms and conditions set * forth in the LICENSE file which can be found at the top level of * the sendmail distribution. */ #include "sm/generic.h" SM_RCSID("@(#)$Id: strexpdig.c,v 1.9 2005/06/06 16:26:06 ca Exp $") #include "sm/assert.h" #include "sm/magic.h" #include "sm/ctype.h" #include "sm/str-int.h" #include "sm/strexp.h" /* ** SM_STR_EXPDIG -- Expand %digit in string with argv[digit] (%=meta) ** %[0-9] -> argv[0-9] ** %x -> x for anything else ** ** Parameters: ** src -- str to expand (read) ** dst -- str into which the expanded sequence is written (output) ** meta -- meta character ('%') ** argc -- number of valid elements in argv (0 - 10) ** argv -- array of strings to use for expansion ** ** Returns: ** >=0: number of replacements ** <0: usual sm_error code */ sm_ret_T sm_str_expdig(const sm_str_P src, sm_str_P dst, uchar meta, uint argc, sm_str_P *argv) { uint i, len, idx, n; uchar ch; sm_ret_T ret; SM_IS_BUF(dst); SM_IS_BUF(src); n = 0; if (meta == '\0') meta = '%'; len = sm_str_getlen(src); for (i = 0; i < len; i++) { ch = sm_str_rd_elem(src, i); if (ch == meta && i + 1 < len) { ++i; ch = sm_str_rd_elem(src, i); if (!ISDIGIT(ch)) { ret = sm_str_put(dst, ch); if (sm_is_err(ret)) goto error; continue; } idx = ch - '0'; /* ** Is there an argv[] element for this? ** If no: %n will be replaced by an empty string! */ if (idx >= argc || argv[idx] == NULL) continue; ret = sm_str_cat(dst, argv[idx]); if (sm_is_err(ret)) goto error; ++n; continue; } ret = sm_str_put(dst, ch); if (sm_is_err(ret)) goto error; } if (n > (uint)SM_RET_MAX) n = SM_RET_MAX; return (sm_ret_T) n; error: /* cleanup? */ return ret; }