Annotation of embedaddon/expat/xmlwf/xmlmime.c, revision 1.1
1.1 ! misho 1: #include <string.h>
! 2: #include "xmlmime.h"
! 3:
! 4: static const char *
! 5: getTok(const char **pp)
! 6: {
! 7: /* inComment means one level of nesting; inComment+1 means two levels etc */
! 8: enum { inAtom, inString, init, inComment };
! 9: int state = init;
! 10: const char *tokStart = 0;
! 11: for (;;) {
! 12: switch (**pp) {
! 13: case '\0':
! 14: if (state == inAtom)
! 15: return tokStart;
! 16: return 0;
! 17: case ' ':
! 18: case '\r':
! 19: case '\t':
! 20: case '\n':
! 21: if (state == inAtom)
! 22: return tokStart;
! 23: break;
! 24: case '(':
! 25: if (state == inAtom)
! 26: return tokStart;
! 27: if (state != inString)
! 28: state++;
! 29: break;
! 30: case ')':
! 31: if (state > init)
! 32: --state;
! 33: else if (state != inString)
! 34: return 0;
! 35: break;
! 36: case ';':
! 37: case '/':
! 38: case '=':
! 39: if (state == inAtom)
! 40: return tokStart;
! 41: if (state == init)
! 42: return (*pp)++;
! 43: break;
! 44: case '\\':
! 45: ++*pp;
! 46: if (**pp == '\0')
! 47: return 0;
! 48: break;
! 49: case '"':
! 50: switch (state) {
! 51: case inString:
! 52: ++*pp;
! 53: return tokStart;
! 54: case inAtom:
! 55: return tokStart;
! 56: case init:
! 57: tokStart = *pp;
! 58: state = inString;
! 59: break;
! 60: }
! 61: break;
! 62: default:
! 63: if (state == init) {
! 64: tokStart = *pp;
! 65: state = inAtom;
! 66: }
! 67: break;
! 68: }
! 69: ++*pp;
! 70: }
! 71: /* not reached */
! 72: }
! 73:
! 74: /* key must be lowercase ASCII */
! 75:
! 76: static int
! 77: matchkey(const char *start, const char *end, const char *key)
! 78: {
! 79: if (!start)
! 80: return 0;
! 81: for (; start != end; start++, key++)
! 82: if (*start != *key && *start != 'A' + (*key - 'a'))
! 83: return 0;
! 84: return *key == '\0';
! 85: }
! 86:
! 87: void
! 88: getXMLCharset(const char *buf, char *charset)
! 89: {
! 90: const char *next, *p;
! 91:
! 92: charset[0] = '\0';
! 93: next = buf;
! 94: p = getTok(&next);
! 95: if (matchkey(p, next, "text"))
! 96: strcpy(charset, "us-ascii");
! 97: else if (!matchkey(p, next, "application"))
! 98: return;
! 99: p = getTok(&next);
! 100: if (!p || *p != '/')
! 101: return;
! 102: p = getTok(&next);
! 103: #if 0
! 104: if (!matchkey(p, next, "xml") && charset[0] == '\0')
! 105: return;
! 106: #endif
! 107: p = getTok(&next);
! 108: while (p) {
! 109: if (*p == ';') {
! 110: p = getTok(&next);
! 111: if (matchkey(p, next, "charset")) {
! 112: p = getTok(&next);
! 113: if (p && *p == '=') {
! 114: p = getTok(&next);
! 115: if (p) {
! 116: char *s = charset;
! 117: if (*p == '"') {
! 118: while (++p != next - 1) {
! 119: if (*p == '\\')
! 120: ++p;
! 121: if (s == charset + CHARSET_MAX - 1) {
! 122: charset[0] = '\0';
! 123: break;
! 124: }
! 125: *s++ = *p;
! 126: }
! 127: *s++ = '\0';
! 128: }
! 129: else {
! 130: if (next - p > CHARSET_MAX - 1)
! 131: break;
! 132: while (p != next)
! 133: *s++ = *p++;
! 134: *s = 0;
! 135: break;
! 136: }
! 137: }
! 138: }
! 139: break;
! 140: }
! 141: }
! 142: else
! 143: p = getTok(&next);
! 144: }
! 145: }
! 146:
! 147: #ifdef TEST
! 148:
! 149: #include <stdio.h>
! 150:
! 151: int
! 152: main(int argc, char *argv[])
! 153: {
! 154: char buf[CHARSET_MAX];
! 155: if (argc <= 1)
! 156: return 1;
! 157: printf("%s\n", argv[1]);
! 158: getXMLCharset(argv[1], buf);
! 159: printf("charset=\"%s\"\n", buf);
! 160: return 0;
! 161: }
! 162:
! 163: #endif /* TEST */
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>