1
0
mirror of https://gitlab.gnome.org/GNOME/libxml2.git synced 2025-10-21 14:53:44 +03:00

In preparation to use normalized values of facets during validation:

* xmlschemastypes.c xmlschemastypes.h: In preparation to use
  normalized values of facets during validation: changed the
  arguments of some string comparison functions; added a static
  xmlSchemaValidateFacetInternal() with more arguments to be
  more flexible. Prepared XML_SCHEMA_FACET_ENUMERATION validation
  to use the comparison functions. Fixed some assignments in
  xmlSchemaValAtomicType(): total digit count, lo, mi, hi.
This commit is contained in:
Kasimier T. Buchcik
2005-03-15 14:58:11 +00:00
parent 57c000e33d
commit 6c81d0ea8d
3 changed files with 396 additions and 226 deletions

View File

@@ -1,3 +1,13 @@
Tue Mar 15 15:43:27 CET 2005 Kasimier Buchcik <libxml2-cvs@cazic.net>
* xmlschemastypes.c xmlschemastypes.h: In preparation to use
normalized values of facets during validation: changed the
arguments of some string comparison functions; added a static
xmlSchemaValidateFacetInternal() with more arguments to be
more flexible. Prepared XML_SCHEMA_FACET_ENUMERATION validation
to use the comparison functions. Fixed some assignments in
xmlSchemaValAtomicType(): total digit count, lo, mi, hi.
Sun Mar 13 19:32:03 CET 2005 Daniel Veillard <daniel@veillard.com>
* NEWS configure.in testapi.c doc/*: preparing release of 2.6.18

View File

@@ -51,6 +51,15 @@ XMLPUBFUN int XMLCALL
xmlSchemaFacetPtr facet,
const xmlChar *value,
xmlSchemaValPtr val);
#if 0
XMLPUBFUN int XMLCALL
xmlSchemaValidateFacetWhtsp (xmlSchemaFacetPtr facet,
xmlSchemaWhitespaceValueType fws,
xmlSchemaValType valType,
xmlSchemaValPtr val,
const xmlChar *value,
xmlSchemaWhitespaceValueType ws);
#endif
XMLPUBFUN void XMLCALL
xmlSchemaFreeValue (xmlSchemaValPtr val);
XMLPUBFUN xmlSchemaFacetPtr XMLCALL

View File

@@ -1930,7 +1930,7 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
/*
* If a mixed decimal, get rid of trailing zeroes
*/
if (dec) {
if (dec != -1) {
while ((cptr > cval) && (*(cptr-1) == '0')) {
cptr--;
len--;
@@ -2065,6 +2065,11 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
if (type == xmlSchemaTypeFloatDef) {
v = xmlSchemaNewValue(XML_SCHEMAS_FLOAT);
if (v != NULL) {
/*
* TODO: sscanf seems not to give the correct
* value for extremely high/low values.
* E.g. "1E-149" results in zero.
*/
if (sscanf((const char *) value, "%f",
&(v->value.f)) == 1) {
*val = v;
@@ -2078,6 +2083,10 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
} else {
v = xmlSchemaNewValue(XML_SCHEMAS_DOUBLE);
if (v != NULL) {
/*
* TODO: sscanf seems not to give the correct
* value for extremely high/low values.
*/
if (sscanf((const char *) value, "%lf",
&(v->value.d)) == 1) {
*val = v;
@@ -2628,7 +2637,7 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
case XML_SCHEMAS_NNINTEGER:{
const xmlChar *cur = value;
unsigned long lo, mi, hi;
int sign = 0;
int sign = 0, total = 0;
if (cur == NULL)
goto return1;
@@ -2637,11 +2646,22 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
cur++;
} else if (*cur == '+')
cur++;
ret = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (ret == 0)
/* Skip leading zeroes. */
while ((*cur == '0') && ((*(cur + 1)) != 0))
cur++;
if (*cur != '0') {
total = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (total <= 0)
goto return1;
if (*cur != 0)
goto return1;
} else {
/* Tiny speedup for "0" */
total = 1;
lo = 0;
mi = 0;
hi = 0;
}
if (type->builtInType == XML_SCHEMAS_NPINTEGER) {
if ((sign == 0) &&
((hi != 0) || (mi != 0) || (lo != 0)))
@@ -2664,15 +2684,15 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
/*
* We can store a value only if no overflow occured
*/
if ((ret > 0) && (val != NULL)) {
if (val != NULL) {
v = xmlSchemaNewValue(type->builtInType);
if (v != NULL) {
v->value.decimal.lo = lo;
v->value.decimal.mi = lo;
v->value.decimal.hi = lo;
v->value.decimal.mi = mi;
v->value.decimal.hi = hi;
v->value.decimal.sign = sign;
v->value.decimal.frac = 0;
v->value.decimal.total = cur - value;
v->value.decimal.total = total;
*val = v;
}
}
@@ -2694,11 +2714,22 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
cur++;
} else if (*cur == '+')
cur++;
ret = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (ret <= 0)
/* Skip leading zeroes. */
while ((*cur == '0') && ((*(cur + 1)) != 0))
cur++;
if (*cur != '0') {
total = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (total <= 0)
goto return1;
if (*cur != 0)
goto return1;
} else {
/* Tiny speedup for "0" */
total = 1;
lo = 0;
mi = 0;
hi = 0;
}
if (type->builtInType == XML_SCHEMAS_LONG) {
if (hi >= 922) {
if (hi > 922)
@@ -2742,8 +2773,8 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
v = xmlSchemaNewValue(type->builtInType);
if (v != NULL) {
v->value.decimal.lo = lo;
v->value.decimal.mi = lo;
v->value.decimal.hi = lo;
v->value.decimal.mi = mi;
v->value.decimal.hi = hi;
v->value.decimal.sign = sign;
v->value.decimal.frac = 0;
v->value.decimal.total = total;
@@ -2762,11 +2793,23 @@ xmlSchemaValAtomicType(xmlSchemaTypePtr type, const xmlChar * value,
if (cur == NULL)
goto return1;
ret = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (ret <= 0)
/* Note that "+" is not allowed. */
/* Skip leading zeroes. */
while ((*cur == '0') && ((*(cur + 1)) != 0))
cur++;
if (*cur != '0') {
total = xmlSchemaParseUInt(&cur, &lo, &mi, &hi);
if (total <= 0)
goto return1;
if (*cur != 0)
goto return1;
} else {
/* Tiny speedup for "0" */
total = 1;
lo = 0;
mi = 0;
hi = 0;
}
if (type->builtInType == XML_SCHEMAS_ULONG) {
if (hi >= 1844) {
if (hi > 1844)
@@ -3684,8 +3727,8 @@ xmlSchemaCompareDates (xmlSchemaValPtr x, xmlSchemaValPtr y)
/**
* xmlSchemaComparePreserveReplaceStrings:
* @x: a first string value
* @y: a second string value
* @xv: a first string value
* @yv: a second string value
* @invert: inverts the result if x < y or x > y.
*
* Compare 2 string for their normalized values.
@@ -3697,22 +3740,16 @@ xmlSchemaCompareDates (xmlSchemaValPtr x, xmlSchemaValPtr y)
* case of error
*/
static int
xmlSchemaComparePreserveReplaceStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
xmlSchemaComparePreserveReplaceStrings(const xmlChar *xv,
const xmlChar *yv,
int invert)
{
const xmlChar *utf1;
const xmlChar *utf2;
int tmp;
if ((x == NULL) || (y == NULL))
return(-2);
utf1 = x->value.str;
utf2 = y->value.str;
while ((*utf1 != 0) && (*utf2 != 0)) {
if (IS_WSP_REPLACE_CH(*utf2)) {
if (! IS_WSP_SPACE_CH(*utf1)) {
if ((*utf1 - 0x20) < 0) {
while ((*xv != 0) && (*yv != 0)) {
if (IS_WSP_REPLACE_CH(*yv)) {
if (! IS_WSP_SPACE_CH(*xv)) {
if ((*xv - 0x20) < 0) {
if (invert)
return(1);
else
@@ -3725,7 +3762,7 @@ xmlSchemaComparePreserveReplaceStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
}
}
} else {
tmp = *utf1 - *utf2;
tmp = *xv - *yv;
if (tmp < 0) {
if (invert)
return(1);
@@ -3739,16 +3776,16 @@ xmlSchemaComparePreserveReplaceStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
return(1);
}
}
utf1++;
utf2++;
xv++;
yv++;
}
if (*utf1 != 0) {
if (*xv != 0) {
if (invert)
return(-1);
else
return(1);
}
if (*utf2 != 0) {
if (*yv != 0) {
if (invert)
return(1);
else
@@ -3771,31 +3808,25 @@ xmlSchemaComparePreserveReplaceStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
* case of error
*/
static int
xmlSchemaComparePreserveCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
xmlSchemaComparePreserveCollapseStrings(const xmlChar *xv,
const xmlChar *yv,
int invert)
{
const xmlChar *utf1;
const xmlChar *utf2;
int tmp;
if ((x == NULL) || (y == NULL))
return(-2);
utf1 = x->value.str;
utf2 = y->value.str;
/*
* Skip leading blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
while ((*utf1 != 0) && (*utf2 != 0)) {
if (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2)) {
if (! IS_WSP_SPACE_CH(*utf1)) {
while ((*xv != 0) && (*yv != 0)) {
if (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv)) {
if (! IS_WSP_SPACE_CH(*xv)) {
/*
* The utf2 character would have been replaced to 0x20.
*/
if ((*utf1 - 0x20) < 0) {
if ((*xv - 0x20) < 0) {
if (invert)
return(1);
else
@@ -3807,15 +3838,15 @@ xmlSchemaComparePreserveCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
return(1);
}
}
utf1++;
utf2++;
xv++;
yv++;
/*
* Skip contiguous blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
} else {
tmp = *utf1++ - *utf2++;
tmp = *xv++ - *yv++;
if (tmp < 0) {
if (invert)
return(1);
@@ -3830,19 +3861,19 @@ xmlSchemaComparePreserveCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
}
}
}
if (*utf1 != 0) {
if (*xv != 0) {
if (invert)
return(-1);
else
return(1);
}
if (*utf2 != 0) {
if (*yv != 0) {
/*
* Skip trailing blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
if (*utf2 != 0) {
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
if (*yv != 0) {
if (invert)
return(1);
else
@@ -3866,31 +3897,25 @@ xmlSchemaComparePreserveCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
* case of error
*/
static int
xmlSchemaCompareReplaceCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
xmlSchemaCompareReplaceCollapseStrings(const xmlChar *xv,
const xmlChar *yv,
int invert)
{
const xmlChar *utf1;
const xmlChar *utf2;
int tmp;
if ((x == NULL) || (y == NULL))
return(-2);
utf1 = x->value.str;
utf2 = y->value.str;
/*
* Skip leading blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
while ((*utf1 != 0) && (*utf2 != 0)) {
if (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2)) {
if (! (IS_WSP_SPACE_CH(*utf1) || IS_WSP_REPLACE_CH(*utf1))) {
while ((*xv != 0) && (*yv != 0)) {
if (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv)) {
if (! (IS_WSP_SPACE_CH(*xv) || IS_WSP_REPLACE_CH(*xv))) {
/*
* The utf2 character would have been replaced to 0x20.
*/
if ((*utf1 - 0x20) < 0) {
if ((*xv - 0x20) < 0) {
if (invert)
return(1);
else
@@ -3902,19 +3927,19 @@ xmlSchemaCompareReplaceCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
return(1);
}
}
utf1++;
utf2++;
xv++;
yv++;
/*
* Skip contiguous blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
} else {
if (IS_WSP_SPACE_CH(*utf1) || IS_WSP_REPLACE_CH(*utf1)) {
if (IS_WSP_SPACE_CH(*xv) || IS_WSP_REPLACE_CH(*xv)) {
/*
* The utf1 character would have been replaced to 0x20.
*/
if ((0x20 - *utf2) < 0) {
if ((0x20 - *yv) < 0) {
if (invert)
return(1);
else
@@ -3926,26 +3951,26 @@ xmlSchemaCompareReplaceCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
return(1);
}
}
tmp = *utf1++ - *utf2++;
tmp = *xv++ - *yv++;
if (tmp < 0)
return(-1);
if (tmp > 0)
return(1);
}
}
if (*utf1 != 0) {
if (*xv != 0) {
if (invert)
return(-1);
else
return(1);
}
if (*utf2 != 0) {
if (*yv != 0) {
/*
* Skip trailing blank chars of the collapsed string.
*/
while (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2))
utf2++;
if (*utf2 != 0) {
while (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv))
yv++;
if (*yv != 0) {
if (invert)
return(1);
else
@@ -3967,44 +3992,38 @@ xmlSchemaCompareReplaceCollapseStrings(xmlSchemaValPtr x, xmlSchemaValPtr y,
* case of error
*/
static int
xmlSchemaCompareReplacedStrings(xmlSchemaValPtr x, xmlSchemaValPtr y)
xmlSchemaCompareReplacedStrings(const xmlChar *xv,
const xmlChar *yv)
{
const xmlChar *utf1;
const xmlChar *utf2;
int tmp;
if ((x == NULL) || (y == NULL))
return(-2);
utf1 = x->value.str;
utf2 = y->value.str;
while ((*utf1 != 0) && (*utf2 != 0)) {
if (IS_WSP_SPACE_CH(*utf2) || IS_WSP_REPLACE_CH(*utf2)) {
if (! (IS_WSP_SPACE_CH(*utf1) || IS_WSP_REPLACE_CH(*utf1))) {
if ((*utf1 - 0x20) < 0)
while ((*xv != 0) && (*yv != 0)) {
if (IS_WSP_SPACE_CH(*yv) || IS_WSP_REPLACE_CH(*yv)) {
if (! (IS_WSP_SPACE_CH(*xv) || IS_WSP_REPLACE_CH(*xv))) {
if ((*xv - 0x20) < 0)
return(-1);
else
return(1);
}
} else {
if (IS_WSP_SPACE_CH(*utf1) || IS_WSP_REPLACE_CH(*utf1)) {
if ((0x20 - *utf2) < 0)
if (IS_WSP_SPACE_CH(*xv) || IS_WSP_REPLACE_CH(*xv)) {
if ((0x20 - *yv) < 0)
return(-1);
else
return(1);
}
tmp = *utf1 - *utf2;
tmp = *xv - *yv;
if (tmp < 0)
return(-1);
if (tmp > 0)
return(1);
}
utf1++;
utf2++;
xv++;
yv++;
}
if (*utf1 != 0)
if (*xv != 0)
return(1);
if (*utf2 != 0)
if (*yv != 0)
return(-1);
return(0);
}
@@ -4020,42 +4039,36 @@ xmlSchemaCompareReplacedStrings(xmlSchemaValPtr x, xmlSchemaValPtr y)
* case of error
*/
static int
xmlSchemaCompareNormStrings(xmlSchemaValPtr x, xmlSchemaValPtr y) {
const xmlChar *utf1;
const xmlChar *utf2;
xmlSchemaCompareNormStrings(const xmlChar *xv,
const xmlChar *yv) {
int tmp;
if ((x == NULL) || (y == NULL))
return(-2);
utf1 = x->value.str;
utf2 = y->value.str;
while (IS_BLANK_CH(*utf1)) utf1++;
while (IS_BLANK_CH(*utf2)) utf2++;
while ((*utf1 != 0) && (*utf2 != 0)) {
if (IS_BLANK_CH(*utf1)) {
if (!IS_BLANK_CH(*utf2)) {
tmp = *utf1 - *utf2;
while (IS_BLANK_CH(*xv)) xv++;
while (IS_BLANK_CH(*yv)) yv++;
while ((*xv != 0) && (*yv != 0)) {
if (IS_BLANK_CH(*xv)) {
if (!IS_BLANK_CH(*yv)) {
tmp = *xv - *yv;
return(tmp);
}
while (IS_BLANK_CH(*utf1)) utf1++;
while (IS_BLANK_CH(*utf2)) utf2++;
while (IS_BLANK_CH(*xv)) xv++;
while (IS_BLANK_CH(*yv)) yv++;
} else {
tmp = *utf1++ - *utf2++;
tmp = *xv++ - *yv++;
if (tmp < 0)
return(-1);
if (tmp > 0)
return(1);
}
}
if (*utf1 != 0) {
while (IS_BLANK_CH(*utf1)) utf1++;
if (*utf1 != 0)
if (*xv != 0) {
while (IS_BLANK_CH(*xv)) xv++;
if (*xv != 0)
return(1);
}
if (*utf2 != 0) {
while (IS_BLANK_CH(*utf2)) utf2++;
if (*utf2 != 0)
if (*yv != 0) {
while (IS_BLANK_CH(*yv)) yv++;
if (*yv != 0)
return(-1);
}
return(0);
@@ -4137,8 +4150,10 @@ xmlSchemaCompareFloats(xmlSchemaValPtr x, xmlSchemaValPtr y) {
/**
* xmlSchemaCompareValues:
* @x: a first value
* @xvalue: the first value as a string (optional)
* @xwtsp: the whitespace type
* @y: a second value
* @xvalue: the second value as a string (optional)
* @ywtsp: the whitespace type
*
* Compare 2 values
@@ -4147,14 +4162,18 @@ xmlSchemaCompareFloats(xmlSchemaValPtr x, xmlSchemaValPtr y) {
* case of error
*/
static int
xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
xmlSchemaCompareValuesInternal(xmlSchemaValType xtype,
xmlSchemaValPtr x,
const xmlChar *xvalue,
xmlSchemaWhitespaceValueType xws,
xmlSchemaValType ytype,
xmlSchemaValPtr y,
const xmlChar *yvalue,
xmlSchemaWhitespaceValueType yws) {
if ((x == NULL) || (y == NULL))
return(-2);
switch (x->type) {
switch (xtype) {
case XML_SCHEMAS_UNKNOWN:
case XML_SCHEMAS_ANYTYPE:
return(-2);
@@ -4172,25 +4191,29 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
case XML_SCHEMAS_BYTE:
case XML_SCHEMAS_UBYTE:
case XML_SCHEMAS_DECIMAL:
if (y->type == x->type)
if ((x == NULL) || (y == NULL))
return(-2);
if (ytype == xtype)
return(xmlSchemaCompareDecimals(x, y));
if ((y->type == XML_SCHEMAS_DECIMAL) ||
(y->type == XML_SCHEMAS_INTEGER) ||
(y->type == XML_SCHEMAS_NPINTEGER) ||
(y->type == XML_SCHEMAS_NINTEGER) ||
(y->type == XML_SCHEMAS_NNINTEGER) ||
(y->type == XML_SCHEMAS_PINTEGER) ||
(y->type == XML_SCHEMAS_INT) ||
(y->type == XML_SCHEMAS_UINT) ||
(y->type == XML_SCHEMAS_LONG) ||
(y->type == XML_SCHEMAS_ULONG) ||
(y->type == XML_SCHEMAS_SHORT) ||
(y->type == XML_SCHEMAS_USHORT) ||
(y->type == XML_SCHEMAS_BYTE) ||
(y->type == XML_SCHEMAS_UBYTE))
if ((ytype == XML_SCHEMAS_DECIMAL) ||
(ytype == XML_SCHEMAS_INTEGER) ||
(ytype == XML_SCHEMAS_NPINTEGER) ||
(ytype == XML_SCHEMAS_NINTEGER) ||
(ytype == XML_SCHEMAS_NNINTEGER) ||
(ytype == XML_SCHEMAS_PINTEGER) ||
(ytype == XML_SCHEMAS_INT) ||
(ytype == XML_SCHEMAS_UINT) ||
(ytype == XML_SCHEMAS_LONG) ||
(ytype == XML_SCHEMAS_ULONG) ||
(ytype == XML_SCHEMAS_SHORT) ||
(ytype == XML_SCHEMAS_USHORT) ||
(ytype == XML_SCHEMAS_BYTE) ||
(ytype == XML_SCHEMAS_UBYTE))
return(xmlSchemaCompareDecimals(x, y));
return(-2);
case XML_SCHEMAS_DURATION:
if ((x == NULL) || (y == NULL))
return(-2);
if (y->type == XML_SCHEMAS_DURATION)
return(xmlSchemaCompareDurations(x, y));
return(-2);
@@ -4202,14 +4225,16 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
case XML_SCHEMAS_GYEARMONTH:
case XML_SCHEMAS_DATE:
case XML_SCHEMAS_DATETIME:
if ((y->type == XML_SCHEMAS_DATETIME) ||
(y->type == XML_SCHEMAS_TIME) ||
(y->type == XML_SCHEMAS_GDAY) ||
(y->type == XML_SCHEMAS_GMONTH) ||
(y->type == XML_SCHEMAS_GMONTHDAY) ||
(y->type == XML_SCHEMAS_GYEAR) ||
(y->type == XML_SCHEMAS_DATE) ||
(y->type == XML_SCHEMAS_GYEARMONTH))
if ((x == NULL) || (y == NULL))
return(-2);
if ((ytype == XML_SCHEMAS_DATETIME) ||
(ytype == XML_SCHEMAS_TIME) ||
(ytype == XML_SCHEMAS_GDAY) ||
(ytype == XML_SCHEMAS_GMONTH) ||
(ytype == XML_SCHEMAS_GMONTHDAY) ||
(ytype == XML_SCHEMAS_GYEAR) ||
(ytype == XML_SCHEMAS_DATE) ||
(ytype == XML_SCHEMAS_GYEARMONTH))
return (xmlSchemaCompareDates(x, y));
return (-2);
/*
@@ -4229,64 +4254,80 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
case XML_SCHEMAS_ENTITY:
case XML_SCHEMAS_NOTATION:
case XML_SCHEMAS_ANYURI:
{
const xmlChar *xv, *yv;
if (x == NULL)
xv = xvalue;
else
xv = x->value.str;
if (y == NULL)
yv = yvalue;
else
yv = y->value.str;
/*
* TODO: Compare those against QName.
*/
if (y->type == XML_SCHEMAS_QNAME) {
if (ytype == XML_SCHEMAS_QNAME) {
TODO
if (y == NULL)
return(-2);
return (-2);
}
if ((y->type == XML_SCHEMAS_ANYSIMPLETYPE) ||
(y->type == XML_SCHEMAS_STRING) ||
(y->type == XML_SCHEMAS_NORMSTRING) ||
(y->type == XML_SCHEMAS_TOKEN) ||
(y->type == XML_SCHEMAS_LANGUAGE) ||
(y->type == XML_SCHEMAS_NMTOKEN) ||
(y->type == XML_SCHEMAS_NAME) ||
(y->type == XML_SCHEMAS_NCNAME) ||
(y->type == XML_SCHEMAS_ID) ||
(y->type == XML_SCHEMAS_IDREF) ||
(y->type == XML_SCHEMAS_ENTITY) ||
(y->type == XML_SCHEMAS_NOTATION) ||
(y->type == XML_SCHEMAS_ANYURI)) {
if ((ytype == XML_SCHEMAS_ANYSIMPLETYPE) ||
(ytype == XML_SCHEMAS_STRING) ||
(ytype == XML_SCHEMAS_NORMSTRING) ||
(ytype == XML_SCHEMAS_TOKEN) ||
(ytype == XML_SCHEMAS_LANGUAGE) ||
(ytype == XML_SCHEMAS_NMTOKEN) ||
(ytype == XML_SCHEMAS_NAME) ||
(ytype == XML_SCHEMAS_NCNAME) ||
(ytype == XML_SCHEMAS_ID) ||
(ytype == XML_SCHEMAS_IDREF) ||
(ytype == XML_SCHEMAS_ENTITY) ||
(ytype == XML_SCHEMAS_NOTATION) ||
(ytype == XML_SCHEMAS_ANYURI)) {
if (xws == XML_SCHEMA_WHITESPACE_PRESERVE) {
if (yws == XML_SCHEMA_WHITESPACE_PRESERVE) {
/* TODO: What about x < y or x > y. */
if (xmlStrEqual(x->value.str, y->value.str))
if (xmlStrEqual(xv, yv))
return (0);
else
return (2);
} else if (yws == XML_SCHEMA_WHITESPACE_REPLACE)
return (xmlSchemaComparePreserveReplaceStrings(x, y, 0));
return (xmlSchemaComparePreserveReplaceStrings(xv, yv, 0));
else if (yws == XML_SCHEMA_WHITESPACE_COLLAPSE)
return (xmlSchemaComparePreserveCollapseStrings(x, y, 0));
return (xmlSchemaComparePreserveCollapseStrings(xv, yv, 0));
} else if (xws == XML_SCHEMA_WHITESPACE_REPLACE) {
if (yws == XML_SCHEMA_WHITESPACE_PRESERVE)
return (xmlSchemaComparePreserveReplaceStrings(y, x, 1));
return (xmlSchemaComparePreserveReplaceStrings(yv, xv, 1));
if (yws == XML_SCHEMA_WHITESPACE_REPLACE)
return (xmlSchemaCompareReplacedStrings(x, y));
return (xmlSchemaCompareReplacedStrings(xv, yv));
if (yws == XML_SCHEMA_WHITESPACE_COLLAPSE)
return (xmlSchemaCompareReplaceCollapseStrings(x, y, 0));
return (xmlSchemaCompareReplaceCollapseStrings(xv, yv, 0));
} else if (xws == XML_SCHEMA_WHITESPACE_COLLAPSE) {
if (yws == XML_SCHEMA_WHITESPACE_PRESERVE)
return (xmlSchemaComparePreserveCollapseStrings(y, x, 1));
return (xmlSchemaComparePreserveCollapseStrings(yv, xv, 1));
if (yws == XML_SCHEMA_WHITESPACE_REPLACE)
return (xmlSchemaCompareReplaceCollapseStrings(y, x, 1));
return (xmlSchemaCompareReplaceCollapseStrings(yv, xv, 1));
if (yws == XML_SCHEMA_WHITESPACE_COLLAPSE)
return (xmlSchemaCompareNormStrings(x, y));
return (xmlSchemaCompareNormStrings(xv, yv));
} else
return (-2);
}
return (-2);
}
case XML_SCHEMAS_QNAME:
if (y->type == XML_SCHEMAS_QNAME) {
if ((x == NULL) || (y == NULL))
return(-2);
if (ytype == XML_SCHEMAS_QNAME) {
if ((xmlStrEqual(x->value.qname.name, y->value.qname.name)) &&
(xmlStrEqual(x->value.qname.uri, y->value.qname.uri)))
return(0);
@@ -4295,12 +4336,16 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
return (-2);
case XML_SCHEMAS_FLOAT:
case XML_SCHEMAS_DOUBLE:
if ((y->type == XML_SCHEMAS_FLOAT) ||
(y->type == XML_SCHEMAS_DOUBLE))
if ((x == NULL) || (y == NULL))
return(-2);
if ((ytype == XML_SCHEMAS_FLOAT) ||
(ytype == XML_SCHEMAS_DOUBLE))
return (xmlSchemaCompareFloats(x, y));
return (-2);
case XML_SCHEMAS_BOOLEAN:
if (y->type == XML_SCHEMAS_BOOLEAN) {
if ((x == NULL) || (y == NULL))
return(-2);
if (ytype == XML_SCHEMAS_BOOLEAN) {
if (x->value.b == y->value.b)
return(0);
if (x->value.b == 0)
@@ -4309,7 +4354,9 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
}
return (-2);
case XML_SCHEMAS_HEXBINARY:
if (y->type == XML_SCHEMAS_HEXBINARY) {
if ((x == NULL) || (y == NULL))
return(-2);
if (ytype == XML_SCHEMAS_HEXBINARY) {
if (x->value.hex.total == y->value.hex.total) {
int ret = xmlStrcmp(x->value.hex.str, y->value.hex.str);
if (ret > 0)
@@ -4324,7 +4371,9 @@ xmlSchemaCompareValuesInternal(xmlSchemaValPtr x,
}
return (-2);
case XML_SCHEMAS_BASE64BINARY:
if (y->type == XML_SCHEMAS_BASE64BINARY) {
if ((x == NULL) || (y == NULL))
return(-2);
if (ytype == XML_SCHEMAS_BASE64BINARY) {
if (x->value.base64.total == y->value.base64.total) {
int ret = xmlStrcmp(x->value.base64.str,
y->value.base64.str);
@@ -4378,7 +4427,8 @@ xmlSchemaCompareValues(xmlSchemaValPtr x, xmlSchemaValPtr y) {
else
yws = XML_SCHEMA_WHITESPACE_COLLAPSE;
return(xmlSchemaCompareValuesInternal(x, xws, y, yws));
return(xmlSchemaCompareValuesInternal(x->type, x, NULL, xws, y->type,
y, NULL, yws));
}
/**
@@ -4397,8 +4447,36 @@ int
xmlSchemaCompareValuesWhtsp(xmlSchemaValPtr x,
xmlSchemaWhitespaceValueType xws,
xmlSchemaValPtr y,
xmlSchemaWhitespaceValueType yws) {
return(xmlSchemaCompareValuesInternal(x, xws, y, yws));
xmlSchemaWhitespaceValueType yws)
{
return(xmlSchemaCompareValuesInternal(x->type, x, NULL, xws, y->type,
y, NULL, yws));
}
/**
* xmlSchemaCompareValuesWhtspExt:
* @x: a first value
* @xws: the whitespace value of x
* @y: a second value
* @yws: the whitespace value of y
*
* Compare 2 values
*
* Returns -1 if x < y, 0 if x == y, 1 if x > y, 2 if x <> y, and -2 in
* case of error
*/
static int
xmlSchemaCompareValuesWhtspExt(xmlSchemaValType xtype,
xmlSchemaValPtr x,
const xmlChar *xvalue,
xmlSchemaWhitespaceValueType xws,
xmlSchemaValType ytype,
xmlSchemaValPtr y,
const xmlChar *yvalue,
xmlSchemaWhitespaceValueType yws)
{
return(xmlSchemaCompareValuesInternal(xtype, x, xvalue, xws, ytype, y,
yvalue, yws));
}
/**
@@ -4599,7 +4677,7 @@ xmlSchemaValidateLengthFacet(xmlSchemaTypePtr type,
}
/**
* xmlSchemaValidateFacet:
* xmlSchemaValidateFacetInternal:
* @base: the base type
* @facet: the facet to check
* @value: the lexical repr of the value to validate
@@ -4610,63 +4688,60 @@ xmlSchemaValidateLengthFacet(xmlSchemaTypePtr type,
* Returns 0 if the element is schemas valid, a positive error code
* number otherwise and -1 in case of internal or API error.
*/
int
xmlSchemaValidateFacet(xmlSchemaTypePtr base ATTRIBUTE_UNUSED,
xmlSchemaFacetPtr facet,
const xmlChar *value, xmlSchemaValPtr val)
static int
xmlSchemaValidateFacetInternal(xmlSchemaFacetPtr facet,
xmlSchemaWhitespaceValueType fws,
xmlSchemaValType valType,
xmlSchemaValPtr val,
const xmlChar *value,
xmlSchemaWhitespaceValueType ws)
{
int ret;
if ((facet == NULL) || (value == NULL))
if (facet == NULL)
return(-1);
switch (facet->type) {
case XML_SCHEMA_FACET_PATTERN:
/*
* NOTE that for patterns, the @value needs to be the normalized
* value, *not* the lexical initial value or the canonical value.
*/
if (value == NULL)
return(-1);
ret = xmlRegexpExec(facet->regexp, value);
if (ret == 1)
return(0);
if (ret == 0) {
if (ret == 0)
return(XML_SCHEMAV_CVC_PATTERN_VALID);
}
return(ret);
case XML_SCHEMA_FACET_MAXEXCLUSIVE:
ret = xmlSchemaCompareValues(val, facet->val);
if (ret == -2) {
/* TODO error code */
if (ret == -2)
return(-1);
}
if (ret == -1)
return(0);
/* error code */
return(XML_SCHEMAV_CVC_MAXEXCLUSIVE_VALID);
case XML_SCHEMA_FACET_MAXINCLUSIVE:
ret = xmlSchemaCompareValues(val, facet->val);
if (ret == -2) {
/* TODO error code */
if (ret == -2)
return(-1);
}
if ((ret == -1) || (ret == 0))
return(0);
/* error code */
return(XML_SCHEMAV_CVC_MAXINCLUSIVE_VALID);
case XML_SCHEMA_FACET_MINEXCLUSIVE:
ret = xmlSchemaCompareValues(val, facet->val);
if (ret == -2) {
/* TODO error code */
if (ret == -2)
return(-1);
}
if (ret == 1)
return(0);
/* error code */
return(XML_SCHEMAV_CVC_MINEXCLUSIVE_VALID);
case XML_SCHEMA_FACET_MININCLUSIVE:
ret = xmlSchemaCompareValues(val, facet->val);
if (ret == -2) {
/* TODO error code */
if (ret == -2)
return(-1);
}
if ((ret == 1) || (ret == 0))
return(0);
/* error code */
return(XML_SCHEMAV_CVC_MININCLUSIVE_VALID);
case XML_SCHEMA_FACET_WHITESPACE:
/* TODO whitespaces */
@@ -4677,14 +4752,25 @@ xmlSchemaValidateFacet(xmlSchemaTypePtr base ATTRIBUTE_UNUSED,
*/
return(0);
case XML_SCHEMA_FACET_ENUMERATION:
if (fws == XML_SCHEMA_WHITESPACE_UNKNOWN) {
if ((facet->value != NULL) &&
(xmlStrEqual(facet->value, value)))
return(0);
} else {
ret = xmlSchemaCompareValuesWhtspExt(facet->val->type,
facet->val, facet->value, fws, valType, val,
value, ws);
if (ret == -2)
return(-1);
if (ret == 0)
return(0);
}
return(XML_SCHEMAV_CVC_ENUMERATION_VALID);
case XML_SCHEMA_FACET_LENGTH:
case XML_SCHEMA_FACET_MAXLENGTH:
case XML_SCHEMA_FACET_MINLENGTH: {
unsigned int len = 0;
/* TODO: Take the whitespace of the value into account. */
if ((facet->val == NULL) ||
((facet->val->type != XML_SCHEMAS_DECIMAL) &&
@@ -4697,7 +4783,7 @@ xmlSchemaValidateFacet(xmlSchemaTypePtr base ATTRIBUTE_UNUSED,
else if ((val != NULL) && (val->type == XML_SCHEMAS_BASE64BINARY))
len = val->value.base64.total;
else {
switch (base->builtInType) {
switch (valType) {
case XML_SCHEMAS_IDREF:
case XML_SCHEMAS_NORMSTRING:
case XML_SCHEMAS_TOKEN:
@@ -4774,6 +4860,71 @@ xmlSchemaValidateFacet(xmlSchemaTypePtr base ATTRIBUTE_UNUSED,
}
/**
* xmlSchemaValidateFacet:
* @base: the base type
* @facet: the facet to check
* @value: the lexical repr of the value to validate
* @val: the precomputed value
*
* Check a value against a facet condition
*
* Returns 0 if the element is schemas valid, a positive error code
* number otherwise and -1 in case of internal or API error.
*/
int
xmlSchemaValidateFacet(xmlSchemaTypePtr base ATTRIBUTE_UNUSED,
xmlSchemaFacetPtr facet,
const xmlChar *value,
xmlSchemaValPtr val)
{
/*
* This tries to ensure API compatibility regarding the old
* xmlSchemaValidateFacet() and the new xmlSchemaValidateFacetInternal() and
* xmlSchemaValidateFacetWhtsp().
*/
if (val != NULL)
return(xmlSchemaValidateFacetInternal(facet,
XML_SCHEMA_WHITESPACE_UNKNOWN, val->type, val, value,
XML_SCHEMA_WHITESPACE_UNKNOWN));
else {
return(xmlSchemaValidateFacetInternal(facet,
XML_SCHEMA_WHITESPACE_UNKNOWN, base->builtInType, val, value,
XML_SCHEMA_WHITESPACE_UNKNOWN));
}
}
/**
* xmlSchemaValidateFacetWhtsp:
* @facet: the facet to check
* @fws: the whitespace type of the facet's value
* @valType: the built-in type of the value
* @value: the lexical (or normalized for pattern) repr of the value to validate
* @val: the precomputed value
* @ws: the whitespace type of the value
*
* Check a value against a facet condition. This takes value normalization
* according to the specified whitespace types into account.
* Note that @value needs to be the *normalized* value if the facet
* is of type "pattern".
*
* Returns 0 if the element is schemas valid, a positive error code
* number otherwise and -1 in case of internal or API error.
*/
#if 0
int
xmlSchemaValidateFacetWhtsp(xmlSchemaFacetPtr facet,
xmlSchemaWhitespaceValueType fws,
xmlSchemaValType valType,
xmlSchemaValPtr val,
const xmlChar *value,
xmlSchemaWhitespaceValueType ws)
{
return(xmlSchemaValidateFacetInternal(facet, fws, valType,
val, value, ws));
}
#endif
/**
* xmlSchemaGetCanonValue:
* @val: the precomputed value