/*- * Copyright 2003 John-Mark Gurney. * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * $Id: mimemisc.c,v 1.2 2003/09/15 23:37:19 jmg Exp $ * */ #include #include #include #include struct attrib * attrib_create(void) { struct attrib *ret; ret = malloc(sizeof *ret); ret->a_n = 0; ret->a_alloc = 0; ret->a_name = NULL; ret->a_value = NULL; return ret; } void attrib_add(struct attrib *a, const char *name, const char *value) { attrib_addnodup(a, strdup(name), strdup(value)); } void attrib_addnodup(struct attrib *a, char *name, char *value) { if (a->a_n + 1 >= a->a_alloc) { a->a_alloc = 2 * (a->a_alloc == 0 ? 4 : a->a_alloc); a->a_name = realloc(a->a_name, a->a_alloc * sizeof *a->a_name); a->a_value = realloc(a->a_value, a->a_alloc * sizeof *a->a_value); } a->a_name[a->a_n] = name; a->a_value[a->a_n] = value; a->a_n++; } const char * attrib_get(struct attrib *a, const char *name, int *cnt) { int i; for (i = cnt == NULL ? 0 : *cnt; i < a->a_n; i++) if (strcasecmp(name, a->a_name[i]) == 0) { if (cnt != NULL) *cnt = i; return a->a_value[i]; } return NULL; } void attrib_free(struct attrib *a) { int i; for (i = 0; i < a->a_n; i++) { free(a->a_name[i]); free(a->a_value[i]); } free(a->a_name); free(a->a_value); free(a); } char * bd_makenorm(const char *bd, const char *crlfpair) { char *ret; ret = malloc(strlen(bd) + strlen(crlfpair) * 2 + 3); strcpy(ret, crlfpair); strcat(ret, "--"); strcat(ret, bd); strcat(ret, crlfpair); return ret; } char * bd_maketail(const char *bd, const char *crlfpair) { char *ret; ret = malloc(strlen(bd) + strlen(crlfpair) * 2 + 5); strcpy(ret, crlfpair); strcat(ret, "--"); strcat(ret, bd); strcat(ret, "--"); strcat(ret, crlfpair); return ret; } static char * getquotedstring(const char *qstr, const char **end) { int n; char *spc; int len; int alloc; if (*qstr != '"') { n = strspn(qstr, "!#$%&'*+-.0123456789?ABCDEFGHIJKLMNOPQRSTUVWXYZ^_`abcdefghijklmnopqrstuvwxyz{|}~"); spc = malloc(sizeof *spc * (n + 1)); strncpy(spc, qstr, n); spc[n] = '\0'; *end = qstr + n; return spc; } spc = malloc((alloc = 64)); len = 0; spc[0] = '\0'; qstr++; for (;;) { if (*qstr == '\\') { spc[len++] = *++qstr; qstr++; } else if (*qstr == '\n') { spc[len++] = *++qstr; qstr++; } else if (*qstr == '"') break; else spc[len++] = *qstr++; if (len >= alloc) spc = realloc(spc, (alloc *= 2)); } spc[len] = '\0'; *end = ++qstr; return spc; } static int addparameter(struct attrib *a, const char **ctr) { const char *ct; char *eq; char *name; char *value; ct = *ctr; if ((ct = strchr(ct, ';')) == NULL) return 0; ct++; while (isspace(*ct)) ct++; if ((eq = strchr(ct, '=')) == NULL) return 0; name = malloc(sizeof *name * (eq - ct + 1)); strncpy(name, ct, eq - ct); name[eq - ct] = '\0'; ct = eq + 1; value = getquotedstring(ct, &ct); attrib_addnodup(a, name, value); *ctr = ct; return 1; } struct attrib * mime_getattrib(const char *ct) { struct attrib *ret; ret = attrib_create(); while (addparameter(ret, &ct)); return ret; }