#include #include #include #define HTML_ESCAPE_TABLE_TERMINATOR { '\0', NULL } static struct html_escape_table html_escape_space[] = { /* {{{ */ { ' ', " " }, HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table html_escape_special_chars[] = { /* {{{ */ { '\x3C', "<" }, { '\x3E', ">" }, { '\x26', "&" }, HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table html_escape_quotes[] = { /* {{{ */ { '\"', """ }, { '\'', "'" }, HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table html_escape_iso8859_1[] = { /* {{{ */ HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table html_escape_iso8859_2[] = { /* {{{ */ HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table html_escape_iso8859_15[] = { /* {{{ */ { '\xE4', "ä" }, { '\xC4', "Ä" }, { '\xF6', "ö" }, { '\xD6', "Ö" }, { '\xFC', "ü" }, { '\xDC', "Ü" }, { '\xDF', "ß" }, { '\xA4', "€" }, HTML_ESCAPE_TABLE_TERMINATOR }; /* }}} */ static struct html_escape_table *html_escape_tables[] = { /* {{{ */ html_escape_space, html_escape_special_chars, html_escape_quotes, html_escape_iso8859_1, html_escape_iso8859_2, html_escape_iso8859_15, NULL }; /* }}} */ char * PLATON_FUNC(html_escape)(str, types) const char *str; const int types; { /* {{{ */ register int i, ii, j, len = 1; struct html_escape_table *current_table; char *html; if ((html = (char *) malloc(1 * sizeof(char))) == NULL) return NULL; /* Loop through every character of str */ for (*html = '\0'; *str != '\0'; str++) { /* Loop through every HTML escape table */ for (i = 0, ii = 1; ; i++, ii *= 2) { /* ii == 2^i */ if ((current_table = html_escape_tables[i]) == NULL) break; /* Check if table is selected */ if (! types & ii) continue; /* Loop though every entity of HTML escape table */ for (j = 0; current_table[j].html != NULL; j++) { /* If character to escape was found */ if (*str != current_table[j].code) continue; /* Substitute character with appropriate entity */ len += strlen(current_table[j].html); if ((html = (char *) realloc(html, len)) == NULL) return NULL; strcat(html, current_table[j].html); break; } if (current_table[j].html != NULL) break; } /* If character was substitued */ if (current_table != NULL) continue; /* Just copy character */ len++; if ((html = (char *) realloc(html, len)) == NULL) return NULL; html[len - 2] = *str; html[len - 1] = '\0'; } return html; } /* }}} */ char * PLATON_FUNC(html_unescape)(html, types) const char *html; const int types; { /* {{{ */ register int i, ii, j, len; struct html_escape_table *current_table; char *str, *ptr; /* String duplication */ if ((str = strdup(html)) == NULL) return NULL; /* Loop through every HTML escape table */ for (i = 0, ii = 1; ; i++, ii *= 2) { /* ii == 2^i */ if ((current_table = html_escape_tables[i]) == NULL) break; /* Check if table is selected */ if (! types & ii) continue; /* Loop though every entity of HTML escape table */ for (j = 0; current_table[j].html != NULL; j++) { while ((ptr = strstr(str, current_table[j].html)) != NULL) { len = strlen(current_table[j].html); if (len <= 0) break; *ptr = current_table[j].code; memmove((void *) (ptr + 1), (void *) (ptr + len), strlen(ptr + len) + 1); } } } return str; } /* }}} */ #if defined(SELF) || defined(SELFTEST) || defined(SELF_HTML_ESCAPE) /* {{{ */ #include #define TEST_STRING "<<--'//'-->>" int main(argc, argv) int argc; char **argv; { register char *s1, *s2; s1 = htmlspecialchars(TEST_STRING); printf("htmlspecialchars(\"%s\") = \"%s\"\n", TEST_STRING, s1); s2 = html_unescape(s1, HTML_ESCAPE_HTMLSPECIALCHARS); printf("html_unescape(\"%s\", HTML_ESCAPE_HTMLSPECIALCHARS) = \"%s\"\n", s1, s2); free(s2); free(s1); s1 = htmlentities(TEST_STRING); printf("htmlentities(\"%s\") = \"%s\"\n", TEST_STRING, s1); s2 = html_unescape(s1, HTML_ESCAPE_HTMLENTITIES); printf("html_unescape(\"%s\", HTML_ESCAPE_HTMLENTITIES) = \"%s\"\n", s1, s2); free(s2); free(s1); return 0; } #endif /* #if defined(SELF) || defined(SELFTEST) || defined(SELF_STRCGI) */ /* }}} */ /* Modeline for ViM {{{ * vim: set ts=4: * vim600: fdm=marker fdl=0 fdc=0: * }}} */