Initial Revision
This commit is contained in:
parent
16e9434927
commit
1197596d3b
7
expat/xmltok/dllmain.c
Executable file
7
expat/xmltok/dllmain.c
Executable file
@ -0,0 +1,7 @@
|
||||
#include <windows.h>
|
||||
|
||||
BOOL WINAPI DllMain(HANDLE hInst, ULONG ul_reason_for_call, LPVOID lpReserved)
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
158
expat/xmlwf/wfcheck.c
Executable file
158
expat/xmlwf/wfcheck.c
Executable file
@ -0,0 +1,158 @@
|
||||
#include <stdlib.h>
|
||||
#include "wfcheck.h"
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define XMLTOKAPI __declspec(dllimport)
|
||||
#endif
|
||||
|
||||
#include "xmltok.h"
|
||||
|
||||
static
|
||||
int skipProlog(const char **s, const char *end, const char **nextTokP,
|
||||
const ENCODING **enc);
|
||||
|
||||
enum WfCheckResult
|
||||
wfCheck(const char *s, size_t n, const char **badPtr)
|
||||
{
|
||||
unsigned nElements = 0;
|
||||
unsigned nAtts = 0;
|
||||
const char *start = s;
|
||||
const char *end = s + n;
|
||||
const char *next;
|
||||
const ENCODING *enc;
|
||||
size_t stackSize = 1024;
|
||||
size_t level = 0;
|
||||
int tok;
|
||||
const char **startName = malloc(stackSize * sizeof(char *));
|
||||
int attsSize = 1024;
|
||||
const char **atts = malloc(attsSize * sizeof(char *));
|
||||
#define RETURN_CLEANUP(n) return (free((void *)startName), free((void *)atts), (n))
|
||||
if (!startName)
|
||||
return noMemory;
|
||||
tok = skipProlog(&s, end, &next, &enc);
|
||||
for (;;) {
|
||||
switch (tok) {
|
||||
case XML_TOK_NONE:
|
||||
*badPtr = s;
|
||||
RETURN_CLEANUP(noElements);
|
||||
case XML_TOK_INVALID:
|
||||
*badPtr = next;
|
||||
RETURN_CLEANUP(invalidToken);
|
||||
case XML_TOK_PARTIAL:
|
||||
*badPtr = s;
|
||||
RETURN_CLEANUP(unclosedToken);
|
||||
case XML_TOK_PARTIAL_CHAR:
|
||||
*badPtr = s;
|
||||
RETURN_CLEANUP(partialChar);
|
||||
case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
|
||||
nElements++;
|
||||
break;
|
||||
case XML_TOK_START_TAG_NO_ATTS:
|
||||
nElements++;
|
||||
if (level == stackSize) {
|
||||
startName = realloc((void *)startName, (stackSize *= 2) * sizeof(char *));
|
||||
if (!startName) {
|
||||
free((void *)atts);
|
||||
return noMemory;
|
||||
}
|
||||
}
|
||||
startName[level++] = s + enc->minBytesPerChar;
|
||||
break;
|
||||
case XML_TOK_START_TAG_WITH_ATTS:
|
||||
if (level == stackSize) {
|
||||
startName = realloc((void *)startName, (stackSize *= 2) * sizeof(char *));
|
||||
if (!startName) {
|
||||
free((void *)atts);
|
||||
return noMemory;
|
||||
}
|
||||
}
|
||||
startName[level++] = s + enc->minBytesPerChar;
|
||||
/* fall through */
|
||||
case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
|
||||
nElements++;
|
||||
{
|
||||
int i;
|
||||
int n = XmlGetAttributes(enc, s, attsSize, atts);
|
||||
nAtts += n;
|
||||
if (n > attsSize) {
|
||||
attsSize = 2*n;
|
||||
atts = realloc((void *)atts, attsSize * sizeof(char *));
|
||||
if (!atts) {
|
||||
free((void *)startName);
|
||||
return noMemory;
|
||||
}
|
||||
XmlGetAttributes(enc, s, n, atts);
|
||||
}
|
||||
for (i = 1; i < n; i++) {
|
||||
int j;
|
||||
for (j = 0; j < i; j++) {
|
||||
if (XmlSameName(enc, atts[i], atts[j])) {
|
||||
*badPtr = atts[i];
|
||||
RETURN_CLEANUP(duplicateAttribute);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case XML_TOK_END_TAG:
|
||||
--level;
|
||||
if (!XmlSameName(enc, startName[level], s + enc->minBytesPerChar * 2)) {
|
||||
*badPtr = s;
|
||||
RETURN_CLEANUP(tagMismatch);
|
||||
}
|
||||
break;
|
||||
}
|
||||
s = next;
|
||||
if (level == 0) {
|
||||
do {
|
||||
tok = XmlPrologTok(enc, s, end, &next);
|
||||
switch (tok) {
|
||||
case XML_TOK_NONE:
|
||||
RETURN_CLEANUP(wellFormed);
|
||||
case XML_TOK_PROLOG_S:
|
||||
case XML_TOK_COMMENT:
|
||||
case XML_TOK_PI:
|
||||
s = next;
|
||||
break;
|
||||
default:
|
||||
if (tok > 0) {
|
||||
*badPtr = s;
|
||||
RETURN_CLEANUP(junkAfterDocElement);
|
||||
}
|
||||
break;
|
||||
}
|
||||
} while (tok > 0);
|
||||
}
|
||||
else
|
||||
tok = XmlContentTok(enc, s, end, &next);
|
||||
}
|
||||
/* not reached */
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
int skipProlog(const char **startp, const char *end,
|
||||
const char **nextTokP, const ENCODING **enc)
|
||||
{
|
||||
const char *s = *startp;
|
||||
INIT_ENCODING initEnc;
|
||||
XmlInitEncoding(&initEnc, enc);
|
||||
for (;;) {
|
||||
int tok = XmlPrologTok(*enc, s, end, nextTokP);
|
||||
switch (tok) {
|
||||
case XML_TOK_START_TAG_WITH_ATTS:
|
||||
case XML_TOK_START_TAG_NO_ATTS:
|
||||
case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
|
||||
case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
|
||||
case XML_TOK_INVALID:
|
||||
case XML_TOK_NONE:
|
||||
case XML_TOK_PARTIAL:
|
||||
*startp = s;
|
||||
return tok;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
s = *nextTokP;
|
||||
}
|
||||
/* not reached */
|
||||
}
|
17
expat/xmlwf/wfcheck.h
Executable file
17
expat/xmlwf/wfcheck.h
Executable file
@ -0,0 +1,17 @@
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
enum WfCheckResult {
|
||||
wellFormed,
|
||||
noMemory,
|
||||
noElements,
|
||||
invalidToken,
|
||||
unclosedToken,
|
||||
partialChar,
|
||||
tagMismatch,
|
||||
duplicateAttribute,
|
||||
junkAfterDocElement
|
||||
};
|
||||
|
||||
enum WfCheckResult wfCheck(const char *s, size_t n, const char **badPtr);
|
||||
|
78
expat/xmlwf/xmlwf.c
Executable file
78
expat/xmlwf/xmlwf.c
Executable file
@ -0,0 +1,78 @@
|
||||
#define STRICT 1
|
||||
#include <windows.h>
|
||||
#include <stddef.h>
|
||||
#include <stdio.h>
|
||||
#include "wfcheck.h"
|
||||
|
||||
static
|
||||
int doFile(const char *name)
|
||||
{
|
||||
HANDLE f;
|
||||
HANDLE m;
|
||||
DWORD size;
|
||||
const char *p;
|
||||
const char *bad = 0;
|
||||
int ret;
|
||||
enum WfCheckResult result;
|
||||
|
||||
f = CreateFile(name, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING,
|
||||
FILE_FLAG_SEQUENTIAL_SCAN, NULL);
|
||||
if (f == INVALID_HANDLE_VALUE) {
|
||||
fprintf(stderr, "%s: CreateFile failed\n", name);
|
||||
return 0;
|
||||
}
|
||||
size = GetFileSize(f, NULL);
|
||||
m = CreateFileMapping(f, NULL, PAGE_READONLY, 0, 0, NULL);
|
||||
if (m == NULL) {
|
||||
fprintf(stderr, "%s: CreateFileMapping failed\n", name);
|
||||
CloseHandle(f);
|
||||
return 0;
|
||||
}
|
||||
p = (const char *)MapViewOfFile(m, FILE_MAP_READ, 0, 0, 0);
|
||||
if (p == NULL) {
|
||||
CloseHandle(m);
|
||||
CloseHandle(f);
|
||||
fprintf(stderr, "%s: MapViewOfFile failed\n", name);
|
||||
return 0;
|
||||
}
|
||||
result = wfCheck(p, size, &bad);
|
||||
if (result) {
|
||||
static const char *message[] = {
|
||||
0,
|
||||
"out of memory",
|
||||
"no element found",
|
||||
"invalid token after %lu bytes",
|
||||
"unclosed token started after %lu bytes",
|
||||
"unclosed token started after %lu bytes",
|
||||
"mismatched tag after %lu bytes",
|
||||
"duplicate attribute after %lu bytes",
|
||||
"junk after document element after %lu bytes",
|
||||
};
|
||||
fprintf(stderr, "%s: ", name);
|
||||
fprintf(stderr, message[result], (unsigned long)(bad - p));
|
||||
putc('\n', stderr);
|
||||
ret = 1;
|
||||
}
|
||||
else
|
||||
ret = 0;
|
||||
UnmapViewOfFile(p);
|
||||
CloseHandle(m);
|
||||
CloseHandle(f);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
int i;
|
||||
int ret = 0;
|
||||
if (argc == 1) {
|
||||
fprintf(stderr, "usage: %s filename ...\n", argv[0]);
|
||||
return 1;
|
||||
}
|
||||
for (i = 1; i < argc; i++) {
|
||||
int n = doFile(argv[i]);
|
||||
if (n > ret)
|
||||
ret = n;
|
||||
}
|
||||
return ret;
|
||||
}
|
Loading…
Reference in New Issue
Block a user