mirror of
https://github.com/michaelrsweet/mxml.git
synced 2025-02-19 17:05:30 +00:00
Dynamically allocate element name, attribute name, and attribute value
buffers. Bump version number to 1.0.1.
This commit is contained in:
parent
208408cf01
commit
243f70768f
9
CHANGES
9
CHANGES
@ -1,6 +1,13 @@
|
||||
README - 06/14/2003
|
||||
README - 06/15/2003
|
||||
-------------------
|
||||
|
||||
CHANGES IN Mini-XML 1.0.1
|
||||
|
||||
- The mxmlLoadFile() function now uses dynamically
|
||||
allocated string buffers for element names, attribute
|
||||
names, and attribute values. Previously they were
|
||||
capped at 16383, 255, and 255 bytes, respectively.
|
||||
|
||||
|
||||
CHANGES IN Mini-XML 1.0
|
||||
|
||||
|
3
README
3
README
@ -4,7 +4,8 @@ README - 06/14/2003
|
||||
|
||||
INTRODUCTION
|
||||
|
||||
This README file describes the Mini-XML library version 1.0.
|
||||
This README file describes the Mini-XML library version
|
||||
1.0.1.
|
||||
|
||||
Mini-XML is a small XML parsing library that you can use to
|
||||
read XML and XML-like data files in your application without
|
||||
|
12
TODO
12
TODO
@ -1,11 +1,5 @@
|
||||
TODO - 06/05/2003
|
||||
TODO - 06/15/2003
|
||||
-----------------
|
||||
|
||||
- Finish up documentation generator, specifically:
|
||||
|
||||
- Structure/class/enumeration/typedef support.
|
||||
- Support for argument names with type info,
|
||||
e.g. "int (*cb)(mxml_node_t *)"
|
||||
- Links at top to jump to specific sections?
|
||||
|
||||
- Code documentation cleanup to take advantage of mxmldoc...
|
||||
- Dynamically allocate memory for attribute values.
|
||||
- Add C++ class.
|
||||
|
@ -16,11 +16,11 @@ href="../index.html">Back to Home Page</a> ]</p>
|
||||
|
||||
<h1 class="title" align="center">Mini-XML Home Page</h1>
|
||||
|
||||
<p class="title" align="center">Current Release: v1.0, June 14, 2003<br/>
|
||||
<p class="title" align="center">Current Release: v1.0.1, June 15, 2003<br/>
|
||||
[ <a
|
||||
href="mxml-1.0.tar.gz">Download Source (.tar.gz 64k)</a>
|
||||
href="mxml-1.0.1.tar.gz">Download Source (.tar.gz 64k)</a>
|
||||
| <a
|
||||
href="mxml-1.0-1.i386.rpm">Download Linux RPM (.i386.rpm 42k)</a>
|
||||
href="mxml-1.0.1-1.i386.rpm">Download Linux RPM (.i386.rpm 42k)</a>
|
||||
| <a href="CHANGES">Change Log</a> | <a
|
||||
href="documentation.html">Documentation</a> | <a
|
||||
href="http://freshmeat.net/projects/mxml">Rate/Make Comments</A> ]</p>
|
||||
|
239
mxml-file.c
239
mxml-file.c
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* "$Id: mxml-file.c,v 1.10 2003/06/14 23:56:47 mike Exp $"
|
||||
* "$Id: mxml-file.c,v 1.11 2003/06/15 21:31:45 mike Exp $"
|
||||
*
|
||||
* File loading code for mini-XML, a small XML-like file parsing library.
|
||||
*
|
||||
@ -36,6 +36,7 @@
|
||||
* Local functions...
|
||||
*/
|
||||
|
||||
static int mxml_add_char(int ch, char **ptr, char **buffer, int *bufsize);
|
||||
static int mxml_parse_element(mxml_node_t *node, FILE *fp);
|
||||
static int mxml_write_node(mxml_node_t *node, FILE *fp,
|
||||
int (*cb)(mxml_node_t *, int), int col);
|
||||
@ -65,8 +66,9 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
*parent; /* Current parent node */
|
||||
int ch, /* Character from file */
|
||||
whitespace; /* Non-zero if whitespace seen */
|
||||
char buffer[16384], /* String buffer */
|
||||
char *buffer, /* String buffer */
|
||||
*bufptr; /* Pointer into buffer */
|
||||
int bufsize; /* Size of buffer */
|
||||
mxml_type_t type; /* Current node type */
|
||||
|
||||
|
||||
@ -74,6 +76,13 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
* Read elements and other nodes from the file...
|
||||
*/
|
||||
|
||||
if ((buffer = malloc(64)) == NULL)
|
||||
{
|
||||
fputs("Unable to allocate string buffer!\n", stderr);
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
bufsize = 64;
|
||||
bufptr = buffer;
|
||||
parent = top;
|
||||
whitespace = 0;
|
||||
@ -180,13 +189,13 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
while ((ch = getc(fp)) != EOF)
|
||||
if (isspace(ch) || ch == '>' || (ch == '/' && bufptr > buffer))
|
||||
break;
|
||||
else if (bufptr < (buffer + sizeof(buffer) - 1))
|
||||
else if (mxml_add_char(ch, &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
*bufptr++ = ch;
|
||||
|
||||
if ((bufptr - buffer) == 3 && !strncmp(buffer, "!--", 3))
|
||||
break;
|
||||
}
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
else if ((bufptr - buffer) == 3 && !strncmp(buffer, "!--", 3))
|
||||
break;
|
||||
|
||||
*bufptr = '\0';
|
||||
|
||||
@ -201,13 +210,10 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
if (ch == '>' && bufptr > (buffer + 4) &&
|
||||
!strncmp(bufptr - 2, "--", 2))
|
||||
break;
|
||||
else if (bufptr < (buffer + sizeof(buffer) - 1))
|
||||
*bufptr++ = ch;
|
||||
else
|
||||
else if (mxml_add_char(ch, &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
fprintf(stderr, "Comment too long in file under parent <%s>!\n",
|
||||
parent ? parent->value.element.name : "null");
|
||||
break;
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
|
||||
@ -245,13 +251,10 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
{
|
||||
if (ch == '>')
|
||||
break;
|
||||
else if (bufptr < (buffer + sizeof(buffer) - 1))
|
||||
*bufptr++ = ch;
|
||||
else
|
||||
else if (mxml_add_char(ch, &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
fprintf(stderr, "Declaration too long in file under parent <%s>!\n",
|
||||
parent ? parent->value.element.name : "null");
|
||||
break;
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
while ((ch = getc(fp)) != EOF);
|
||||
@ -439,13 +442,10 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
* Plain ASCII doesn't need special encoding...
|
||||
*/
|
||||
|
||||
if (bufptr < (buffer + sizeof(buffer) - 1))
|
||||
*bufptr++ = ch;
|
||||
else
|
||||
if (mxml_add_char(ch, &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
fprintf(stderr, "String too long in file under parent <%s>!\n",
|
||||
parent ? parent->value.element.name : "null");
|
||||
break;
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -454,32 +454,59 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
* Use UTF-8 encoding for the Unicode char...
|
||||
*/
|
||||
|
||||
if (bufptr < (buffer + sizeof(buffer) - 5))
|
||||
if (ch < 2048)
|
||||
{
|
||||
if (ch < 2048)
|
||||
if (mxml_add_char(0xc0 | (ch >> 6), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
*bufptr++ = 0xc0 | (ch >> 6);
|
||||
*bufptr++ = 0x80 | (ch & 63);
|
||||
}
|
||||
else if (ch < 65536)
|
||||
{
|
||||
*bufptr++ = 0xe0 | (ch >> 12);
|
||||
*bufptr++ = 0x80 | ((ch >> 6) & 63);
|
||||
*bufptr++ = 0x80 | (ch & 63);
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
else
|
||||
if (mxml_add_char(0x80 | (ch & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
*bufptr++ = 0xf0 | (ch >> 18);
|
||||
*bufptr++ = 0x80 | ((ch >> 12) & 63);
|
||||
*bufptr++ = 0x80 | ((ch >> 6) & 63);
|
||||
*bufptr++ = 0x80 | (ch & 63);
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
else if (ch < 65536)
|
||||
{
|
||||
if (mxml_add_char(0xe0 | (ch >> 12), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
if (mxml_add_char(0x80 | ((ch >> 6) & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
if (mxml_add_char(0x80 | (ch & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
fprintf(stderr, "String too long in file under parent <%s>!\n",
|
||||
parent ? parent->value.element.name : "null");
|
||||
break;
|
||||
if (mxml_add_char(0xf0 | (ch >> 18), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
if (mxml_add_char(0x80 | ((ch >> 12) & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
if (mxml_add_char(0x80 | ((ch >> 6) & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
if (mxml_add_char(0x80 | (ch & 63), &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -489,17 +516,20 @@ mxmlLoadFile(mxml_node_t *top, /* I - Top node */
|
||||
* Add character to current buffer...
|
||||
*/
|
||||
|
||||
if (bufptr < (buffer + sizeof(buffer) - 1))
|
||||
*bufptr++ = ch;
|
||||
else
|
||||
if (mxml_add_char(ch, &bufptr, &buffer, &bufsize))
|
||||
{
|
||||
fprintf(stderr, "String too long in file under parent <%s>!\n",
|
||||
parent ? parent->value.element.name : "null");
|
||||
break;
|
||||
free(buffer);
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Free the string buffer - we don't need it anymore...
|
||||
*/
|
||||
|
||||
free(buffer);
|
||||
|
||||
/*
|
||||
* Find the top element and return it...
|
||||
*/
|
||||
@ -552,6 +582,49 @@ mxmlSaveFile(mxml_node_t *node, /* I - Node to write */
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* 'mxml_add_char()' - Add a character to a buffer, expanding as needed.
|
||||
*/
|
||||
|
||||
static int /* O - 0 on success, -1 on error */
|
||||
mxml_add_char(int ch, /* I - Character to add */
|
||||
char **bufptr, /* IO - Current position in buffer */
|
||||
char **buffer, /* IO - Current buffer */
|
||||
int *bufsize) /* IO - Current buffer size */
|
||||
{
|
||||
char *newbuffer; /* New buffer value */
|
||||
|
||||
|
||||
if (*bufptr >= (*buffer + *bufsize - 1))
|
||||
{
|
||||
/*
|
||||
* Increase the size of the buffer...
|
||||
*/
|
||||
|
||||
if (*bufsize < 1024)
|
||||
(*bufsize) *= 2;
|
||||
else
|
||||
(*bufsize) += 1024;
|
||||
|
||||
if ((newbuffer = realloc(*buffer, *bufsize)) == NULL)
|
||||
{
|
||||
free(*buffer);
|
||||
|
||||
fprintf(stderr, "Unable to expand string buffer to %d bytes!\n",
|
||||
*bufsize);
|
||||
|
||||
return (-1);
|
||||
}
|
||||
|
||||
*bufptr = newbuffer + (*bufptr - *buffer);
|
||||
}
|
||||
|
||||
*(*bufptr)++ = ch;
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* 'mxml_parse_element()' - Parse an element for any attributes...
|
||||
*/
|
||||
@ -562,11 +635,34 @@ mxml_parse_element(mxml_node_t *node, /* I - Element node */
|
||||
{
|
||||
int ch, /* Current character in file */
|
||||
quote; /* Quoting character */
|
||||
char name[256], /* Attribute name */
|
||||
value[256], /* Attribute value */
|
||||
char *name, /* Attribute name */
|
||||
*value, /* Attribute value */
|
||||
*ptr; /* Pointer into name/value */
|
||||
int namesize, /* Size of name string */
|
||||
valsize; /* Size of value string */
|
||||
|
||||
|
||||
/*
|
||||
* Initialize the name and value buffers...
|
||||
*/
|
||||
|
||||
if ((name = malloc(64)) == NULL)
|
||||
{
|
||||
fputs("Unable to allocate memory for name!\n", stderr);
|
||||
return (EOF);
|
||||
}
|
||||
|
||||
namesize = 64;
|
||||
|
||||
if ((value = malloc(64)) == NULL)
|
||||
{
|
||||
free(name);
|
||||
fputs("Unable to allocate memory for value!\n", stderr);
|
||||
return (EOF);
|
||||
}
|
||||
|
||||
valsize = 64;
|
||||
|
||||
/*
|
||||
* Loop until we hit a >, /, ?, or EOF...
|
||||
*/
|
||||
@ -614,13 +710,11 @@ mxml_parse_element(mxml_node_t *node, /* I - Element node */
|
||||
while ((ch = getc(fp)) != EOF)
|
||||
if (isspace(ch) || ch == '=' || ch == '/' || ch == '>' || ch == '?')
|
||||
break;
|
||||
else if (ptr < (name + sizeof(name) - 1))
|
||||
*ptr++ = ch;
|
||||
else
|
||||
else if (mxml_add_char(ch, &ptr, &name, &namesize))
|
||||
{
|
||||
fprintf(stderr, "Attribute name too long for element %s!\n",
|
||||
node->value.element.name);
|
||||
return (EOF);
|
||||
free(name);
|
||||
free(value);
|
||||
return (EOF);
|
||||
}
|
||||
|
||||
*ptr = '\0';
|
||||
@ -650,13 +744,11 @@ mxml_parse_element(mxml_node_t *node, /* I - Element node */
|
||||
while ((ch = getc(fp)) != EOF)
|
||||
if (ch == quote)
|
||||
break;
|
||||
else if (ptr < (value + sizeof(value) - 1))
|
||||
*ptr++ = ch;
|
||||
else
|
||||
else if (mxml_add_char(ch, &ptr, &value, &valsize))
|
||||
{
|
||||
fprintf(stderr, "Attribute value too long for attribute '%s' in element %s!\n",
|
||||
name, node->value.element.name);
|
||||
return (EOF);
|
||||
free(name);
|
||||
free(value);
|
||||
return (EOF);
|
||||
}
|
||||
|
||||
*ptr = '\0';
|
||||
@ -673,13 +765,11 @@ mxml_parse_element(mxml_node_t *node, /* I - Element node */
|
||||
while ((ch = getc(fp)) != EOF)
|
||||
if (isspace(ch) || ch == '=' || ch == '/' || ch == '>')
|
||||
break;
|
||||
else if (ptr < (value + sizeof(value) - 1))
|
||||
*ptr++ = ch;
|
||||
else
|
||||
else if (mxml_add_char(ch, &ptr, &value, &valsize))
|
||||
{
|
||||
fprintf(stderr, "Attribute value too long for attribute '%s' in element %s!\n",
|
||||
name, node->value.element.name);
|
||||
return (EOF);
|
||||
free(name);
|
||||
free(value);
|
||||
return (EOF);
|
||||
}
|
||||
|
||||
*ptr = '\0';
|
||||
@ -702,6 +792,13 @@ mxml_parse_element(mxml_node_t *node, /* I - Element node */
|
||||
mxmlElementSetAttr(node, name, value);
|
||||
}
|
||||
|
||||
/*
|
||||
* Free the name and value buffers and return...
|
||||
*/
|
||||
|
||||
free(name);
|
||||
free(value);
|
||||
|
||||
return (ch);
|
||||
}
|
||||
|
||||
@ -1012,5 +1109,5 @@ mxml_write_ws(mxml_node_t *node, /* I - Current node */
|
||||
|
||||
|
||||
/*
|
||||
* End of "$Id: mxml-file.c,v 1.10 2003/06/14 23:56:47 mike Exp $".
|
||||
* End of "$Id: mxml-file.c,v 1.11 2003/06/15 21:31:45 mike Exp $".
|
||||
*/
|
||||
|
@ -1,5 +1,5 @@
|
||||
#
|
||||
# "$Id: mxml.list.in,v 1.3 2003/06/15 01:29:02 mike Exp $"
|
||||
# "$Id: mxml.list.in,v 1.4 2003/06/15 21:31:45 mike Exp $"
|
||||
#
|
||||
# EPM software list file for mini-XML, a small XML-like file parsing library.
|
||||
#
|
||||
@ -32,7 +32,7 @@ $srcdir=@srcdir@
|
||||
%vendor Michael Sweet
|
||||
%license ${srcdir}/COPYING
|
||||
%readme ${srcdir}/README
|
||||
%version 1.0
|
||||
%version 1.0.1
|
||||
|
||||
%description <<EOF
|
||||
Mini-XML is a small XML parsing library that you can use to read
|
||||
@ -88,5 +88,5 @@ f 0444 root sys ${mandir}/cat3/mxml.$CAT3EXT $srcdir/mxml.$CAT3EXT
|
||||
f 0444 root sys ${mandir}/man3/mxml.$MAN3EXT $srcdir/mxml.man
|
||||
|
||||
#
|
||||
# End of "$Id: mxml.list.in,v 1.3 2003/06/15 01:29:02 mike Exp $".
|
||||
# End of "$Id: mxml.list.in,v 1.4 2003/06/15 21:31:45 mike Exp $".
|
||||
#
|
||||
|
@ -1,5 +1,5 @@
|
||||
#
|
||||
# "$Id: mxml.spec,v 1.2 2003/06/15 01:22:37 mike Exp $"
|
||||
# "$Id: mxml.spec,v 1.3 2003/06/15 21:31:45 mike Exp $"
|
||||
#
|
||||
# RPM "spec" file for mini-XML, a small XML-like file parsing library.
|
||||
#
|
||||
@ -18,7 +18,7 @@
|
||||
|
||||
Summary: Miniature XML development library
|
||||
Name: mxml
|
||||
Version: 1.0
|
||||
Version: 1.0.1
|
||||
Release: 1
|
||||
Copyright: GPL
|
||||
Group: Development/Libraries
|
||||
@ -94,5 +94,5 @@ rm -rf $RPM_BUILD_ROOT
|
||||
/usr/share/man/man3/*
|
||||
|
||||
#
|
||||
# End of "$Id: mxml.spec,v 1.2 2003/06/15 01:22:37 mike Exp $".
|
||||
# End of "$Id: mxml.spec,v 1.3 2003/06/15 21:31:45 mike Exp $".
|
||||
#
|
||||
|
Loading…
Reference in New Issue
Block a user