mime.c
上传用户:ladybrid91
上传日期:2007-01-04
资源大小:287k
文件大小:4k
源码类别:

Web服务器

开发平台:

Unix_Linux

  1. /*
  2. ** mime.c
  3. **
  4. ** Copyright (c) 1994-1995 Peter Eriksson <pen@signum.se>
  5. **
  6. ** This program is free software; you can redistribute it and/or modify
  7. ** it under the terms of the GNU General Public License as published by
  8. ** the Free Software Foundation; either version 2 of the License, or
  9. ** (at your option) any later version.
  10. **
  11. ** This program is distributed in the hope that it will be useful,
  12. ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. ** GNU General Public License for more details.
  15. ** You should have received a copy of the GNU General Public License
  16. ** along with this program; if not, write to the Free Software
  17. ** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  18. */
  19.    
  20. #include <stdio.h>
  21. #include <string.h>
  22. #include <time.h>
  23. #include <limits.h>
  24. #include <stdlib.h>
  25. #include <syslog.h>
  26. #include "phttpd.h"
  27. int mime_getline(char *buf, int size, int fd)
  28. {
  29.     int c, i;
  30.     
  31.     c = EOF;
  32.     for (i = 0; i < size-1 && (c = fd_getc(fd)) != EOF; i++)
  33.     {
  34. buf[i] = c;
  35. if (c == 'n')
  36. {
  37.     if (i == 0)
  38.     {
  39. buf[i] = '';
  40. return 0;
  41.     }
  42.     
  43.     c = fd_getc(fd);
  44.     if (c == EOF)
  45. break;
  46.     
  47.     if (c == 'n' || !s_isspace(c))
  48.     {
  49. fd_ungetc(c, fd);
  50. break;
  51.     }
  52. }
  53.     }
  54.     buf[i] = '';
  55.     
  56.     if (c == EOF)
  57. return -1;
  58.     return i;
  59. }
  60. struct mimeinfo *mime_getheaders(int fd)
  61. {
  62.     struct mimeinfo *mip;
  63.     hashentry_t *hep;
  64.     char buf[2048];
  65.     char *cp, *cp2;
  66.     int i, status;
  67.     NEW(mip);
  68.     mip->version = 2;
  69.     mip->headerbytes = 0;
  70.     
  71.     ht_init(&mip->table, 0, NULL);
  72.     
  73.     while ((status = mime_getline(buf, sizeof(buf), fd)) > 0)
  74.     {
  75. i = strlen(buf) - 1;
  76. mip->headerbytes = mip->headerbytes + i + 1;
  77. while (i >= 0 && s_isspace(buf[i]))
  78.     i--;
  79. buf[i+1] = '';
  80. for (cp = buf; *cp && s_isspace(*cp); cp++)
  81.     ;
  82. if (*cp == '')
  83.     break;
  84. cp2 = cp;
  85. while (*cp2 && *cp2 != ':')
  86. {
  87.     *cp2 = s_toupper(*cp2);
  88.     ++cp2;
  89. }
  90. if (*cp2 == 0)
  91.     continue;
  92. *cp2++ = '';
  93. while (*cp2 && s_isspace(*cp2))
  94.     ++cp2;
  95. if (debug > 4)
  96.     fprintf(stderr, "mime_getheaders(): got key=%s, value=%sn",
  97.     cp, cp2);
  98. /*
  99. ** Some special handling of certain flags
  100. */
  101. if (strcmp(cp, "CONNECTION") == 0)
  102. {
  103.     if (strcasecmp(cp2, "KEEP-ALIVE") == 0)
  104. mip->connection_flags |= MCF_KEEPALIVE;
  105. }
  106. else if (strcmp(cp, "PRAGMA") == 0)
  107. {
  108.     if (strcasecmp(cp2, "NO-CACHE") == 0)
  109. mip->pragma_flags |= MPF_NOCACHE;
  110. }
  111. hep = ht_lookup(&mip->table, cp, 0);
  112. if (hep == NULL)
  113. {
  114.       hep = ht_insert(&mip->table, cp, 0, s_strdup(cp2),
  115.     0, s_free);
  116. }
  117. else
  118. {
  119.     char *new_str;
  120.     int nlen;
  121.     
  122.     /* This code could be optimized :-) */
  123.     nlen = (strlen(hep->data) + strlen(cp2) + 3);
  124.     
  125.     new_str = s_malloc(nlen);
  126.     s_strcpy(new_str, nlen, hep->data);
  127.     s_strcat(new_str, nlen, "n");
  128.     s_strcat(new_str, nlen, cp2);
  129.     
  130.     s_free(hep->data);
  131.     hep->data = new_str;
  132. }
  133. ht_release(hep);
  134.     }
  135.     return mip;
  136. }
  137. void mime_freeheaders(struct mimeinfo *mip)
  138. {
  139.     if (debug > 3)
  140. fprintf(stderr, "mime_freeheaders(): Startn");
  141.     
  142.     ht_destroy(&mip->table);
  143.     s_free(mip);
  144.     
  145.     if (debug > 3)
  146. fprintf(stderr, "mime_freeheaders(): Stopn");
  147. }
  148. static int mwr_header(hashentry_t *hep, void *misc)
  149. {
  150.     int fd = * (int *) misc;
  151.     char *start, *end;
  152.     
  153.     if (debug > 4)
  154. fprintf(stderr, "mwr_header: key="%s", value="%s"n",
  155. (char *) hep->key, (char *) hep->data);
  156.     start = hep->data;
  157.     while ((end = strchr(start, 'n')) != NULL)
  158.     {
  159. if (end == start)
  160. {
  161.     /* Ignore empty lines */
  162.     start = end+1;
  163.     continue;
  164. }
  165. fd_puts(hep->key, fd);
  166. fd_puts(": ", fd);
  167. fd_write(fd, start, end-start+1);
  168. start = end+1;
  169.     }
  170.     if (*start)
  171.     {
  172. fd_puts(hep->key, fd);
  173. fd_puts(": ", fd);
  174. fd_puts(start, fd);
  175. fd_putc('n', fd);
  176.     }
  177.     return 0;
  178. }
  179. void mime_writeheaders(int fd, struct mimeinfo *mip)
  180. {
  181.     if (mip == NULL)
  182. return;
  183.     ht_foreach(&mip->table, mwr_header, &fd);
  184.     return;
  185. }
  186. void *mime_getheader(struct mimeinfo *mip,
  187.      const char *header,
  188.      int str_flag)
  189. {
  190.     hashentry_t *hep;
  191.     char *str;
  192.     
  193.     if (debug > 3)
  194. fprintf(stderr, "mime_getheader("%s")n", header);
  195.     if (mip == NULL)
  196. return NULL;
  197.     
  198.     hep = ht_lookup(&mip->table, header, 0);
  199.     if (hep == NULL)
  200. return NULL;
  201.     if (debug > 4)
  202. fprintf(stderr, "tuse=%dn", hep->use);
  203.     str = hep->data;
  204.     ht_release(hep);
  205.     return str;
  206. }