Re: Octstr support for converting to and from HTML 4 entities.
Rene Kluwen / Chimit Software Solutions <[email protected]>
| Newsgroups | gmane.comp.mobile.kannel.devel |
|---|---|
| Message-ID | <[email protected]> |
Hello Oded, In your html-entities.def I happened to notice that & was missing! I don't know if that is on purpose, but if not: now you know ;) Anyhow... I came up with a faster version. That depends on html-entities.def being sorted on entity-name. About being readable: the use of macro's and including an external file keeps being questionable to me as far as readability is concerned. But attached version is more efficient indeed. It uses the macro's in html-entities.def as well. But I tried to explain as much as possible in comments. Sunday, September 22, 2002, 8:09:01 PM, you wrote: OA> Hi list. OA> We needed the ability to encode data to XML/HTML with HTML 4 entities as defined by W3C, so I thought that adding it to the Octstr infrastructure would be nice - so that other people will be able OA> to use it. OA> So here it is for your review - don't spare the ammo. OA> Both conversions (to HTML entities and from) are using a .def file that is included into the code. the 'to' coversion is very straight forward and should be very easy. I'm afraid that the 'from' OA> conversion is rather processor intensive - I'm yet unsure as to how to make it more efficient and still keep it as readable. OA> -- OA> Oded Arbel OA> m-Wise mobile solutions OA> [email protected] OA> +972-9-9581711 (116) OA> +972-67-340014 OA> ::.. OA> Finagle's laws for existentialists - OA> 8.Everything takes longer than you think -- Best regards, Rene mailto:[email protected]
html_entities.patch
(application/octet-stream, 3.5 KB)
Index: gwlib/octstr.c
===================================================================
RCS file: /home/cvs/gateway/gwlib/octstr.c,v
retrieving revision 1.137
diff -u -r1.137 octstr.c
--- gwlib/octstr.c 4 Sep 2002 09:13:11 -0000 1.137
+++ gwlib/octstr.c 22 Sep 2002 23:28:22 -0000
@@ -1220,7 +1220,7 @@
octstr_grow(ostr, ostr->len + 1);
if (ostr->len > pos)
- memmove(ostr->data + 1, ostr->data + pos, ostr->len - pos);
+ memmove(ostr->data + pos + 1, ostr->data + pos, ostr->len - pos);
memcpy(ostr->data + pos, &c, 1);
ostr->len += 1;
ostr->data[ostr->len] = '\0';
@@ -2182,3 +2182,94 @@
return resultcode;
}
+
+/*
+ * This function is meant to find html entities in an octstr.
+ * The html-entities.def file must be sorted alphabetically for
+ * this function to work (according to C-Locale).
+ * It can be made even faster by implementing a binary search, though
+ * better boundary checking must be done in that case.
+*/
+static int octstr_find_entity(Octstr* input, int startpos, int endpos)
+{
+#define ENTITY(a,b) { a, b },
+ struct entity_struct {
+ int entity;
+ char *entity_str;
+ };
+ const struct entity_struct entities[] = {
+#include "html-entities.def"
+ { -1, "" } /* pivot */
+ };
+#undef ENTITY
+
+ int loop = 0; /* position of current entity in entity table */
+ int pos = startpos; /* current position to check in input string */
+ char ch, /* current character in entity-table */
+ current; /* current character in input string */
+
+ current = octstr_get_char(input, pos);
+ while (1) {
+ ch = entities[loop].entity_str[pos - startpos];
+ if (ch == current) {
+ pos++;
+ if (pos > endpos) {
+ /* we reached the end of the entity in the input string */
+ return -1; /* not found */
+ }
+ current = octstr_get_char(input, pos);
+ continue;
+ }
+ if (ch == '\0') {
+ if (pos == endpos) {
+ /* it seems this is the entity that we are looking for */
+ return entities[loop].entity;
+ }
+ /* We are still looking for more entries, in case multiple entries in
+ * the entity table exist where one entry is equal to the prefix of
+ * the next (Special case) */
+ }
+ else if (current < ch) {
+ /* the string in the sorted list is already greater than the string
+ * that we are looking for. No use to look any further. */
+ return -1; /* not found */
+ }
+ /* go to next entry in entity table */
+ loop++;
+ if (entities[loop].entity == -1) {
+ /* Pivot found: we are at the end of the table */
+ return -1; /* not found */
+ }
+ if (octstr_len(octstr_imm((entities[loop].entity_str))) <= pos - startpos) {
+ /* Check this in case we encouter the Special case mentioned above */
+ return -1; /* not found */
+ }
+ }
+ /* never reached */
+}
+
+/*
+ * function octstr_convert_from_html_entities()
+ * convert HTML safe data back to binary data by replacing HTML entities with their
+ * respective character values
+ * Input: data to be inserted in HTML
+ **/
+void octstr_convert_from_html_entities(Octstr* input)
+{
+ int startpos = 0, endpos;
+ int entity;
+
+
+ while ((startpos = octstr_search_char(input, '&', startpos)) != -1) {
+ endpos = octstr_search_char(input, ';', startpos + 1);
+ if (endpos >= 0) {
+ entity = octstr_find_entity(input, startpos + 1, endpos);
+ if (entity >= 0) {
+ octstr_delete(input, startpos, endpos - startpos + 1);
+ octstr_insert_char(input, startpos, entity);
+ }
+ }
+ startpos++;
+ }
+}
+
html-entities.def
(application/octet-stream, 2 KB) - not displayed