zorba-coders team mailing list archive
-
zorba-coders team
-
Mailing list archive
-
Message #00054
[Merge] lp:~danielturcanu/zorba/mytrunk into lp:zorba
Daniel Turcanu has proposed merging lp:~danielturcanu/zorba/mytrunk into lp:zorba.
Requested reviews:
Zorba Coders (zorba-coders)
For more details, see:
https://code.launchpad.net/~danielturcanu/zorba/mytrunk/+merge/76556
Some fixes, especially for Windows.
--
https://code.launchpad.net/~danielturcanu/zorba/mytrunk/+merge/76556
Your team Zorba Coders is requested to review the proposed merge of lp:~danielturcanu/zorba/mytrunk into lp:zorba.
=== modified file 'src/diagnostics/dict_XX_cpp.xq'
--- src/diagnostics/dict_XX_cpp.xq 2011-08-05 02:21:55 +0000
+++ src/diagnostics/dict_XX_cpp.xq 2011-09-22 11:09:58 +0000
@@ -1,91 +1,92 @@
-(:
- : Copyright 2006-2009 The FLWOR Foundation.
- :
- : Licensed under the Apache License, Version 2.0 (the "License");
- : you may not use this file except in compliance with the License.
- : You may obtain a copy of the License at
- :
- : http://www.apache.org/licenses/LICENSE-2.0
- :
- : Unless required by applicable law or agreed to in writing, software
- : distributed under the License is distributed on an "AS IS" BASIS,
- : WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- : See the License for the specific language governing permissions and
- : limitations under the License.
-:)
-
-import module namespace util = "http://www.zorba-xquery.com/diagnostic/util" at "diagnostic_util.xq";
-
-declare function local:make-dict( $doc ) as xs:string*
-{
- for $entry in ( $doc//diagnostic, $doc//entry )
- let $key :=
- typeswitch ( $entry )
- case element(diagnostic)
- return $entry/@code
- case $e as element(entry)
- return
- (
- (: raise an error if sub-message contains $1 as parameter :)
- if ( contains ( $e/value, "$1" ) )
- then
- error(
- fn:QName("http://www.zorba-xquery.com/error", "submessage"),
- concat(
- "sub-entry must not contain parameter named $1: ", $e/value
- )
- )
- else
- (),
- if ( $e/parent::diagnostic )
- then concat( "~", $e/parent::diagnostic/@code, "_", $entry/@key )
- else concat( "~", $entry/@key )
- )
- default
- return error()
- let $value := replace( $entry/value, '"', '\\"' )
- let $if := $entry/@if
- order by $key
- return (
- if ( $if )
- then concat( "#if ", $if )
- else (),
- concat( ' { "', $key, '", "', $value, '" },' ),
- if ( $if )
- then "#endif"
- else ()
- )
-};
-
-
-declare variable $input external;
-
-let $lang := $input/diagnostic-list/@lang
-return string-join(
- ( util:copyright(),
- '#include "stdafx.h"',
- '#include "diagnostics/dict_impl.h"',
- '',
- 'namespace zorba {',
- 'namespace diagnostic {',
- 'namespace dict {',
- '',
- concat( 'extern entry const dict_', $lang, '[] = {' ),
- local:make-dict( $input ),
- '};',
- concat( 'DEF_DICT_END(', $lang, ');' ),
- '',
- '} // namespace dict',
- '} // namespace diagnostic',
- '} // namespace zorba',
- '/*',
- ' * Local variables:',
- ' * mode: c++',
- ' * End:',
- ' */'
- ),
- $util:newline
-),
-$util:newline
-
-(: vim:set syntax=xquery et sw=2 ts=2: :)
+(:
+ : Copyright 2006-2009 The FLWOR Foundation.
+ :
+ : Licensed under the Apache License, Version 2.0 (the "License");
+ : you may not use this file except in compliance with the License.
+ : You may obtain a copy of the License at
+ :
+ : http://www.apache.org/licenses/LICENSE-2.0
+ :
+ : Unless required by applicable law or agreed to in writing, software
+ : distributed under the License is distributed on an "AS IS" BASIS,
+ : WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ : See the License for the specific language governing permissions and
+ : limitations under the License.
+:)
+
+import module namespace util = "http://www.zorba-xquery.com/diagnostic/util" at "diagnostic_util.xq";
+
+declare function local:make-dict( $doc ) as xs:string*
+{
+ for $entry in ( $doc//diagnostic, $doc//entry )
+ let $key :=
+ typeswitch ( $entry )
+ case element(diagnostic)
+ return $entry/@code
+ case $e as element(entry)
+ return
+ (
+ (: raise an error if sub-message contains $1 as parameter :)
+ if ( contains ( $e/value, "$1" ) )
+ then
+ error(
+ fn:QName("http://www.zorba-xquery.com/error", "submessage"),
+ concat(
+ "sub-entry must not contain parameter named $1: ", $e/value
+ )
+ )
+ else
+ (),
+ if ( $e/parent::diagnostic )
+ then concat( "~", $e/parent::diagnostic/@code, "_", $entry/@key )
+ else concat( "~", $entry/@key )
+ )
+ default
+ return error()
+ let $value := replace( $entry/value, '"', '\\"' )
+ let $if := $entry/@if
+ order by $key
+ return (
+ if ( $if )
+ then concat( "#if ", $if )
+ else (),
+ concat( ' { "', $key, '", "', $value, '" },' ),
+ if ( $if )
+ then "#endif"
+ else ()
+ )
+};
+
+
+declare variable $input external;
+
+let $lang := $input/diagnostic-list/@lang
+return string-join(
+ ( util:copyright(),
+ '#include "stdafx.h"',
+ '#include "zorba/config.h"',
+ '#include "diagnostics/dict_impl.h"',
+ '',
+ 'namespace zorba {',
+ 'namespace diagnostic {',
+ 'namespace dict {',
+ '',
+ concat( 'extern entry const dict_', $lang, '[] = {' ),
+ local:make-dict( $input ),
+ '};',
+ concat( 'DEF_DICT_END(', $lang, ');' ),
+ '',
+ '} // namespace dict',
+ '} // namespace diagnostic',
+ '} // namespace zorba',
+ '/*',
+ ' * Local variables:',
+ ' * mode: c++',
+ ' * End:',
+ ' */'
+ ),
+ $util:newline
+),
+$util:newline
+
+(: vim:set syntax=xquery et sw=2 ts=2: :)
=== modified file 'src/diagnostics/pregenerated/dict_en.cpp'
--- src/diagnostics/pregenerated/dict_en.cpp 2011-09-16 21:58:20 +0000
+++ src/diagnostics/pregenerated/dict_en.cpp 2011-09-22 11:09:58 +0000
@@ -1,725 +1,726 @@
-/**
- * Copyright 2006-2011 The FLWOR Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
- /*
- * THIS FILE IS GENERATED.
- * PLEASE DO NOT EDIT.
- */
-
-#include "stdafx.h"
-#include "diagnostics/dict_impl.h"
-
-namespace zorba {
-namespace diagnostic {
-namespace dict {
-
-extern entry const dict_en[] = {
- { "FOAR0001", "division by zero" },
- { "FOAR0002", "numeric operation overflow/underflow${: 1}" },
- { "FOCA0001", "\"$1\": value too large for decimal" },
- { "FOCA0002", "\"$1\": invalid lexical value${: 2}" },
- { "FOCA0003", "\"$1\": value too large for integer" },
- { "FOCA0005", "NaN supplied as float/double value" },
- { "FOCA0006", "\"$1\": string to be cast to decimal has too many digits of precision" },
- { "FOCH0001", "\"$1\": invalid code point" },
- { "FOCH0002", "\"$1\": unsuported collation${: 2}" },
- { "FOCH0003", "\"$1\": unsupported normalization form" },
- { "FOCH0004", "\"$1\": collation does not support collation units" },
- { "FODC0001", "no context document for $1() function" },
- { "FODC0002", "\"$1\": error retrieving resource${: 2}" },
- { "FODC0003", "function stability not defined" },
- { "FODC0004", "\"$1\": invalid argument to fn:collection()${: 2}" },
- { "FODC0005", "\"$1\": invalid argument to fn:doc() or fn:doc-available()" },
- { "FODC0006", "invalid content passed to $1: $2" },
- { "FODC0007", "\"$1\": base URI passed to fn:parse() is not a valid absolute URI" },
- { "FODF1280", "\"$1\": invalid decimal format name for fn:format-number()" },
- { "FODF1310", "\"$1\": invalid fn:format-number() picture string" },
- { "FODT0001", "overflow/underflow in date/time operation" },
- { "FODT0002", "overflow/underflow in duration operation" },
- { "FODT0003", "\"$1\": invalid timezone value" },
- { "FOER0000", "unidentifier error" },
- { "FOFI0001", "\"$1\": not castable to xs:language" },
- { "FOFI0002", "invalid argument in format-integer: $1" },
- { "FONS0004", "\"$1\": no namespace found for prefix" },
- { "FONS0005", "base-URI not defined in the static context" },
- { "FORG0001", "${\"1\": }invalid value for cast/constructor${: 2}" },
- { "FORG0002", "\"$1\": invalid argument to fn:resolve-uri()${: 2}" },
- { "FORG0003", "fn:zero-or-one() called with a sequnce containing more than one item" },
- { "FORG0004", "fn:one-or-more() called with a sequence containing no items" },
- { "FORG0005", "fn:exactly-one() called with a sequence containing zero or more than one item" },
- { "FORG0006", "$1" },
- { "FORG0008", "\"$1\" and \"$2\": two arguments to fn:dateTime() have inconsistent timezones" },
- { "FORG0009", "error resolving a relative URI against a base URI in fn:resolve-uri()${: 1}" },
- { "FORX0001", "'$1': invalid regular expression flag" },
- { "FORX0002", "\"$1\": invalid regular expression${: 2}" },
- { "FORX0003", "\"$1\": regular expression matches zero-length string" },
- { "FORX0004", "\"$1\": invalid replacement string${: 2}" },
- { "FOTY0012", "\"$1\": element node of type $2 does not have a typed value" },
- { "FOTY0013", "\"$1\": argument to fn:data() is function item" },
- { "FOTY0014", "\"$1\": argument to fn:string() is a function item" },
- { "FOTY0015", "\"$1\": argument to fn:deep-equal() contains a function item" },
- { "FOUP0001", "first operand of fn:put() is not a node of a supported kind" },
- { "FOUP0002", "second operand of fn:put() is not a valid lexical representation of the xs:anyURI type" },
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTDY0016", "\"$1\": invalid weight: absolute value must be in [0,1000]" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTDY0017", "mild-not contains StringExclude" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTDY0020", "${\"1\": }invalid wildcard syntax${: 2}" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTST0008", "\"$1\": unknown stop-word list" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTST0009", "\"$1\": unsupported language" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTST0018", "\"$1\": unknown thesaurus" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "FTST0019", "\"$1\": match option specified more than once" },
-#endif
- { "SENR0001", "\"$1\": can not serialize $2" },
- { "SEPM0004", "doctype-system parameter, or standalone parameter with a value other than \"omit\", specified" },
- { "SEPM0009", "omit-xml-declaration parameter is \"yes\" and $1" },
- { "SEPM0010", "the output method is \"xml\", the value of the undeclare-prefixes parameter is \"yes\", and the value of the version parameter is \"1.0\"" },
- { "SEPM0016", "\"$1\": value for parameter \"$2\" invalid${; $3}" },
- { "SERE0003", "serializer can't satisfy the rules for either a well-formed XML document entity or a well-formed XML external general parsed entity" },
- { "SERE0005", "invalid NCName character" },
- { "SERE0006", "\"$1\": invalid character for XML version $2" },
- { "SERE0008", "\"$1\": can not encode character as character reference here" },
- { "SERE0012", "normalization-form parameter value is fully-normalized and any relevant construct of the result begins with a combining character" },
- { "SERE0014", "\"#$1\": character not allowed for HTML output method" },
- { "SERE0015", "can not use '>' within processing instruction for HTML output method" },
- { "SESU0007", "\"$1\": unsupported encoding" },
- { "SESU0011", "\"$1\": unsupported normalization form" },
- { "SESU0013", "\"$1\": unsupported $2 version; supported versions are: $3" },
- { "XPDY0002", "\"$1\": $2" },
- { "XPDY0050", "invalid treat expression type" },
- { "XPST0001", "${\"1\": }undefined value${: 2}" },
- { "XPST0003", "invalid expression${: 1}" },
- { "XPST0005", "static type must not be empty-sequence()" },
- { "XPST0008", "\"$1\": undefined $2" },
- { "XPST0017", "\"$1\": $2" },
- { "XPST0051", "\"$1\": not defined as atomic type${: 2}" },
- { "XPST0080", "\"$1\": invalid type for \"cast\" or \"castable\" exression" },
- { "XPST0081", "\"$1\": can not expand namespace prefix to URI" },
- { "XPST0083", "\"$1\": not a string literal" },
- { "XPTY0004", "$1" },
- { "XPTY0018", "path expression last step must not have nodes and atomic values" },
- { "XPTY0019", "path expression non-last step must not be an atomic value" },
- { "XPTY0020", "axis step context item is not a node" },
- { "XQDY0025", "\"$1\": duplicate attribute name" },
- { "XQDY0026", "computed processing instrucion must not contain \"?>\"" },
- { "XQDY0027", "\"$1\": unexpected validity property${: 2}" },
- { "XQDY0041", "can not cast to xs:NCName" },
- { "XQDY0044", "\"$1\": invalid attibute node-name" },
- { "XQDY0061", "invalid validate expression operand${: 1}" },
- { "XQDY0064", "\"XML\": invalid name expression" },
- { "XQDY0072", "comment must not contain \"--\" or end with \"-\"" },
- { "XQDY0074", "${\"1\": }can not convert to expanded QName${: 2}" },
- { "XQDY0084", "validated element does not have a top-level element declaration in the in-scope element declarations${: 1}" },
- { "XQDY0091", "\"xml:id\" encountered" },
- { "XQDY0092", "\"$1\": must be either \"preserve\" or \"default\"" },
- { "XQDY0096", "\"$1\": invalid node-name" },
- { "XQST0009", "schema import not supported" },
- { "XQST0012", "invalid schema definitions" },
- { "XQST0013", "invalid pragma content" },
- { "XQST0022", "namespace declaration attribute is not a URI literal" },
- { "XQST0031", "\"$1\": $2" },
- { "XQST0032", "multiple base URI declarations" },
- { "XQST0033", "\"$1\": namespace prefix already bound to \"$2\"" },
- { "XQST0034", "\"$1\": duplicate function declaration" },
- { "XQST0035", "\"$1\": name previosly imported" },
- { "XQST0036", "$1" },
- { "XQST0038", "multiple default collation declarations" },
- { "XQST0039", "\"$1\": duplicate parameter name" },
- { "XQST0040", "\"$1\": non-distinct expanded attribute QName" },
- { "XQST0045", "\"$1\": invalid function or annotation namespace" },
- { "XQST0046", "${\"1\": }invalid URI literal${: 2}" },
- { "XQST0047", "\"$1\": duplicate target namespace" },
- { "XQST0048", "\"$1\": not in library namespace" },
- { "XQST0049", "\"$1\": duplicate variable declaration" },
- { "XQST0054", "${\"1\": }variable must not depend on itself" },
- { "XQST0055", "multiple copy-namespaces declarations" },
- { "XQST0057", "empty target namespace" },
- { "XQST0058", "\"$1\": duplicate target namespace" },
- { "XQST0059", "\"$1\": target namespace not found for schema/module${ 2}" },
- { "XQST0060", "\"$1\": function name has a null namespace URI" },
- { "XQST0065", "multiple ordering mode declaraions" },
- { "XQST0066", "multiple element/type/function namespace declarations" },
- { "XQST0067", "multiple construction declarations" },
- { "XQST0068", "multiple boundary-space declarations" },
- { "XQST0069", "multiple empty order declarations" },
- { "XQST0070", "\"$1\": $2" },
- { "XQST0071", "\"$1\": duplicate namespace declaration attribute" },
- { "XQST0076", "\"$1\": unknown collation" },
- { "XQST0079", "unknown pragma or empty expression" },
- { "XQST0085", "namespace URI is empty" },
- { "XQST0087", "\"$1\": invalid encoding" },
- { "XQST0088", "empty target namespace literal" },
- { "XQST0089", "\"$1\": duplicate variable name" },
- { "XQST0090", "\"$1\": invalid character reference in XML $2" },
- { "XQST0093", "\"$1\": module must not depend on itself" },
- { "XQST0098", "properties \"$1\" and \"$2\", representing characters used in picture string, do not have distinct values" },
- { "XQST0106", "$1: multiple annotations with $2 names" },
- { "XQST0111", "$1" },
- { "XQTY0024", "element constructor content sequence must not have an attribute node following a non-attribute node" },
- { "XQTY0030", "validate argument must be exactly one document or element node" },
- { "XQTY0086", "typed value of copied element or attribute node is namespace-sensitive when construction mode is preserve and copy-namespaces mode is no-preserve" },
- { "XSST0001", "\"$1\": function cannot be declared as both updating and sequential" },
- { "XSST0002", "\"$1\": function declared sequential but has updating body" },
- { "XSST0003", "\"$1\": function declared updating but has sequential body" },
- { "XSST0004", "\"$1\": function declared nonsequential but has sequential body" },
- { "XSST0005", "expression cannot be both updating and sequential" },
- { "XSST0006", "sequential expression not allowed here" },
- { "XSST0007", "\"$1\": variable not assignable" },
- { "XSST0008", "\"while\" statement with non-sequential body" },
- { "XSST0009", "\"break loop\" statement not inside while statement" },
- { "XSST0010", "\"continue loop\" statement not inside while statement" },
- { "XTDE1310", "\"$1\": picture string does not satisfy format-number() function rules" },
- { "XTDE1340", "\"$1\": invalid picture string for date/time" },
- { "XTDE1350", "component specifier not available" },
- { "XUDY0009", "node has no parent in \"replace\" expression (without \"value of\")" },
- { "XUDY0014", "\"modify\" can not modify node not created by \"copy\"" },
- { "XUDY0015", "node is target of multiple \"rename\" expressions in same query" },
- { "XUDY0016", "node is target of multiple \"replace\" expressions (without \"value of\") in same query" },
- { "XUDY0017", "node is target of multiple \"replace value of\" expressions in same query" },
- { "XUDY0018", "\"$1\": function declared external, non-updating returns non-empty pending update list" },
- { "XUDY0019", "\"$1\": function declated external, updating returns non-empty data model instance" },
- { "XUDY0021", "updates violate constraint" },
- { "XUDY0023", "\"$1\": namespace binding conflicts with $2=$3" },
- { "XUDY0024", "\"$1\": namespace binding conflicts with $2=$3" },
- { "XUDY0027", "target expression is empty sequence" },
- { "XUDY0029", "node has no parent in \"insert\" expression (with \"before\" or \"after\")" },
- { "XUDY0030", "insertion of attrhbute node before or after document node child" },
- { "XUDY0031", "\"$1\": same URI used in multiple calls to fn:put() in same snapshot" },
- { "XUST0001", "$1" },
- { "XUST0002", "simple expression not allowed here" },
- { "XUST0003", "multiple revalidation declarations" },
- { "XUST0028", "\"$1\": function can not be updating with a return type" },
- { "XUTY0004", "attribute node follows non-attribute node" },
- { "XUTY0005", "target expression not a single element or document node" },
- { "XUTY0006", "target expression not a single element, text, comment, or processing instruction node" },
- { "XUTY0007", "target expression does not return a sequence of zero or more nodes" },
- { "XUTY0008", "target expression not a single element, attribute, text, comment, or processing instruction node" },
- { "XUTY0010", "replacement sequence does not consist of zero or more element, text, comment, or processing instruction nodes" },
- { "XUTY0011", "replacement sequence does not consist of zero or more attribute nodes" },
- { "XUTY0012", "multiple elements, attributes, or processing-instruction nodes returned" },
- { "XUTY0013", "source expression of \"copy\" clause must return a single node" },
- { "XUTY0022", "insertion of attribute node into document node" },
- { "ZAPI0002", "XQuery compilation failed${: 1}" },
- { "ZAPI0003", "XQuery not compiled" },
- { "ZAPI0004", "XQuery already compiled" },
- { "ZAPI0005", "XQuery already executing" },
- { "ZAPI0006", "XQuery already closed" },
- { "ZAPI0007", "cannot serialize pul" },
- { "ZAPI0008", "can not execute a non-updating XQuery" },
- { "ZAPI0009", "XQuery not compiled in debug mode" },
- { "ZAPI0014", "\"$1\": invalid argument${: 2}" },
- { "ZAPI0015", "\"$1\": createModule() function not found${: 2}" },
- { "ZAPI0019", "\"$1\": external module already registered" },
- { "ZAPI0020", "\"$1\": document already exists in store" },
- { "ZAPI0021", "\"$1\": item to load is not a node" },
- { "ZAPI0027", "cannot update dynamic context with iterators" },
- { "ZAPI0028", "\"$1\": invalid node URI" },
- { "ZAPI0039", "XQuery has iterator already" },
- { "ZAPI0040", "iterator is not open" },
- { "ZAPI0041", "iterator is already open" },
- { "ZAPI0042", "iterator is closed" },
- { "ZAPI0070", "\"$1\": invalid serialization method for SAX" },
- { "ZAPI0080", "can not retrieve node-reference for a node that is not in a collection." },
- { "ZCSE0001", "\"$1\": nonexistent input field" },
- { "ZCSE0002", "\"$1\": incompatible input field${: type=2}${, class=3}" },
- { "ZCSE0003", "\"$1\": unrecognized class field" },
- { "ZCSE0004", "\"$1\": unresolved field reference" },
- { "ZCSE0005", "class version for \"$1\" ($2) is too new; supported version is $3" },
- { "ZCSE0006", "class version for \"$1\" ($2) is too old; minimum supported version is $3; use Zorba 0x$4 instead" },
- { "ZCSE0007", "input archive used for out serialization" },
- { "ZCSE0008", "output archive used for in serialization" },
- { "ZCSE0009", "\"$1\": class not serializable" },
- { "ZCSE0010", "\"$1\": item type not serializable; only atomic, node, function, and error items are supported" },
- { "ZCSE0011", "input archive not Zorba archive" },
- { "ZCSE0012", "\"$1\": incompatible archive version; expected \"$2\"" },
- { "ZCSE0013", "failed to load pre-compiled query${: 1}" },
- { "ZCSE0014", "cannot save execution plan: infinite circular dependencies" },
- { "ZCSE0015", "cannot load execution plan: incompatible between 32/64 bits or little/big-endian" },
- { "ZCSE0016", "cannot load execution plan saved from release mode Zorba into debug mode Zorba" },
- { "ZCSE0017", "cannot load execution plan saved from debug mode Zorba into release mode Zorba" },
- { "ZDDY0001", "\"$1\": collection not declared" },
- { "ZDDY0002", "\"$1\": collection already exists" },
- { "ZDDY0003", "\"$1\": collection does not exist" },
- { "ZDDY0004", "\"$1\": can not update constant collection" },
- { "ZDDY0005", "\"$1\": illegal insert into append-only collection" },
- { "ZDDY0006", "\"$1\": illegal insert into queue collection" },
- { "ZDDY0007", "\"$1\": illegal delete from append-only collection" },
- { "ZDDY0008", "\"$1\": illegal delete from queue collection" },
- { "ZDDY0009", "\"$1\": not all nodes to delete are at the beginning of this queue collection" },
- { "ZDDY0010", "\"$1\": illegal update of read-only nodes" },
- { "ZDDY0011", "\"$1\": collection does not contain node" },
- { "ZDDY0012", "\"$1\": illegal insert into unordered collection" },
- { "ZDDY0013", "\"$1\": can not delete collection because indexes reference it" },
- { "ZDDY0014", "\"$1\": can not delete collection because integrity constraints reference it" },
- { "ZDDY0015", "\"$1\": can not delete collection because there are references to its nodes" },
- { "ZDDY0016", "\"$1\": multiple attemps to create a collection in the same snapshot" },
- { "ZDDY0017", "node does not belong to any collection" },
- { "ZDDY0018", "all nodes must be in same collection" },
- { "ZDDY0020", "\"$1\": index domain expression yields nodes that are not in collection" },
- { "ZDDY0021", "\"$1\": undeclared index" },
- { "ZDDY0022", "\"$1\": index already exists" },
- { "ZDDY0023", "\"$1\": index does not exist" },
- { "ZDDY0024", "\"$1\": index uniqueness violation" },
- { "ZDDY0025", "${\"1\": }invalid number of arguments in probe" },
- { "ZDDY0026", "\"$1\": index range probe not allowed" },
- { "ZDDY0027", "\"$1\": index multiple creates" },
- { "ZDDY0028", "\"$1\": index domain has duplicate nodes" },
- { "ZDDY0029", "\"$1\": index point-general probe not allowed" },
- { "ZDDY0030", "\"$1\": index range-general probe not allowed" },
- { "ZDDY0031", "\"$1\": integrity constraint is not declared" },
- { "ZDDY0032", "\"$1\": integrity constraint is not activated" },
- { "ZDDY0033", "\"$1\": integrity constraint not met for collection \"$2\"" },
- { "ZDST0001", "\"$1\": collection already declared" },
- { "ZDST0002", "\"$1\": collection already imported into module \"$2\"" },
- { "ZDST0003", "\"$1\": collection declaration not allowed in main module" },
- { "ZDST0004", "collection multiple property values" },
- { "ZDST0006", "collection invalid property value" },
- { "ZDST0007", "\"$1\": collection declaration in foreign module" },
- { "ZDST0021", "\"$1\": index already declared" },
- { "ZDST0022", "\"$1\": index already imported into module \"$2\"" },
- { "ZDST0023", "\"$1\": index declaration not allowed in main module" },
- { "ZDST0024", "index multiple property values" },
- { "ZDST0026", "index invalid property value" },
- { "ZDST0027", "\"$1\": index bad key type" },
- { "ZDST0028", "\"$1\": index not deterministic" },
- { "ZDST0029", "\"$1\": index invalid data source" },
- { "ZDST0030", "\"$1\": index non-constant data source" },
- { "ZDST0031", "\"$1\": index has free vars" },
- { "ZDST0032", "\"$1\": index references context item" },
- { "ZDST0033", "\"$1\": index non-simple expression" },
- { "ZDST0034", "\"$1\": index can not do automatic maintenance" },
- { "ZDST0035", "\"$1\": index general multikey" },
- { "ZDST0036", "\"$1\": index declaration in foreign module" },
- { "ZDST0041", "\"$1\": integrity constraint already declared" },
- { "ZDST0044", "\"$1\": integrity constraint declaration not allowed in main module" },
- { "ZDST0048", "\"$1\": integrity constraint declaration in foreign module" },
- { "ZDST0060", "\"$1\": feature not supported; $2" },
- { "ZDTY0001", "\"$1\": invalid node type in collection \"$2\"" },
- { "ZDTY0010", "\"$1\": index domain expression yields a non-node item" },
- { "ZDTY0011", "result of some key expression of index $1 does not match its declared type" },
- { "ZDTY0012", "\"$1\": general range index key item has type for which no ordering relationship exists" },
-#if defined(ZORBA_WITH_DEBUGGER)
- { "ZGDB0001", "" },
-#endif
- { "ZOSE0001", "\"$1\": file not found" },
- { "ZOSE0002", "\"$1\": not plain file" },
- { "ZOSE0003", "stream read failure" },
- { "ZOSE0004", "${\"1\": }I/O error${: 2}" },
- { "ZOSE0005", "\"$1\": error loading dynamic library${: 2}" },
- { "ZSTR0001", "\"$1\": index already exists" },
- { "ZSTR0002", "\"$1\": index does not exist" },
- { "ZSTR0003", "\"$1\": partial key insertion into index \"$2\"" },
- { "ZSTR0004", "\"$1\": partial key deletion from index \"$2\"" },
- { "ZSTR0005", "\"$1\": partial key probe into index \"$2\"" },
- { "ZSTR0006", "for index \"$1\": $2" },
- { "ZSTR0007", "\"$1\": unsupported probe condition for index \"$2\"" },
- { "ZSTR0008", "\"$1\": collection already exists" },
- { "ZSTR0009", "\"$1\": collection not found" },
- { "ZSTR0010", "can not insert node into colletion \"$1\" because it already belongs to collection \"$2\"" },
- { "ZSTR0011", "non-root node can not be inserted into collection \"$1\"" },
- { "ZSTR0012", "non-node item used with collection \"$1\"" },
- { "ZSTR0015", "\"$1\": integrity constraint already exists" },
- { "ZSTR0016", "\"$1\": integrity constraint does not exist" },
- { "ZSTR0020", "loader I/O error${: 1}" },
- { "ZSTR0021", "loader parsing error${: 1}" },
- { "ZSTR0030", "NodeID error${: 1}" },
- { "ZSTR0040", "type error${: 1}" },
- { "ZSTR0041", "NaN comparison" },
- { "ZSTR0045", "duplicate node found in sequence" },
- { "ZSTR0050", "\"$1\" not implemented for item type \"$2\"" },
- { "ZSTR0055", "streamable string has already been consumed" },
- { "ZSTR0060", "out of range: $1" },
- { "ZWST0002", "\"$1\": unknown or unsupported annotation" },
- { "ZWST0003", "\"$1\": function declared sequential, but has non-sequential body" },
- { "ZWST0004", "Sequential FLWOR expr may not have the semantics you expect" },
- { "ZXQD0001", "\"$1\": prefix not declared when calling function \"$2\" from $3" },
- { "ZXQD0002", "\"$1\": $2" },
- { "ZXQD0003", "inconsistent options to the parse-xml-fragment() function: $1" },
- { "ZXQD0004", "invalid parameter: $1" },
- { "ZXQD0005", "key with type $1 not subtype or castable to target type $2 of map ($3)" },
- { "ZXQP0000", "no error" },
- { "ZXQP0001", "dynamic runtime error${: 1}" },
- { "ZXQP0002", "\"$1\": assertion failed" },
- { "ZXQP0003", "internal error${: 1}" },
- { "ZXQP0004", "not yet implemented: $1" },
- { "ZXQP0005", "\"$1\": feature not enabled" },
- { "ZXQP0007", "\"$1\": function signature does not match declaration" },
- { "ZXQP0008", "\"$1\": function implementation not found" },
- { "ZXQP0009", "\"$1\": function referred to by this local-name has the local-name \"$2\" instead" },
- { "ZXQP0010", "\"$1\": builtin sequential function not implemented as sequential" },
- { "ZXQP0013", "FxCharHeap error: $1 ($2)" },
- { "ZXQP0016", "\"$1\": reserved module target namespace" },
- { "ZXQP0017", "file access disabled" },
- { "ZXQP0020", "\"$1\": invalid URI${: 2}" },
- { "ZXQP0021", "user error" },
- { "ZXQP0024", "XML does not match schema${: \"1\"}${ 2}" },
- { "ZXQP0025", "item creation failed" },
- { "ZXQP0026", "\"$1\": invalid enumerated value for $2" },
- { "ZXQP0028", "\"$1\": target namespace not provided by module from $2" },
- { "ZXQP0029", "\"$1\": module import not allowed" },
- { "ZXQP0030", "deadlock" },
- { "ZXQP0031", "malformed XQueryX XML input${: 1}" },
- { "ZXQP0032", "error transforming XQueryX to XQuery${: 1}" },
- { "ZXQP0036", "BreakIterator creation failed" },
- { "ZXQP0037", "\"$1\": loaded module version \"$2\" does not match import version specification" },
- { "ZXQP0038", "Query requires Zorba version \"$1\"; you are running Zorba \"$2\"" },
- { "ZXQP0039", "\"$1\": invalid version specification" },
- { "ZXQP0040", "\"$1\": function invokes a nondeterministic function but is missing the nondeterministic annotation" },
- { "ZXQP0050", "\"$1\": feature not available" },
- { "ZXQP0060", "\"$1\": unkown option" },
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "ZXQP8401", "\"$1\": wrong WordNet file version; should be \"$2\"" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "ZXQP8402", "thesaurus data endianness does not match CPU" },
-#endif
-#if !defined(ZORBA_NO_FULL_TEXT)
- { "ZXQP8403", "thesaurus data error${: 1}" },
-#endif
- { "~AllMatchesHasExcludes", "AllMatches contains StringExclude" },
- { "~AlreadySpecified", "already specified" },
- { "~ArithOpNotDefinedBetween_23", "arithmetic operation not defined between types \"$2\" and \"$3\"" },
- { "~AtomizationHasMoreThanOneValue", "atomization has more than one value" },
- { "~AtomizationOfGroupByMakesMoreThanOneItem", "atomization of groupby variable produces more than one item" },
- { "~AttributeName", "attribute name" },
- { "~AttributeNode", "attribute node" },
- { "~BackRef0Illegal", "\"0\": illegal backreference" },
- { "~BackRefIllegalInCharClass", "backreference illegal in character class" },
- { "~BadAnyURI", "invalid xs:anyURI" },
- { "~BadArgTypeForFn_2o34o", "${\"2\": }invalid argument type for function $3()${: 4}" },
- { "~BadCharAfter_34", "'$3': illegal character after '$4'" },
- { "~BadCharInBraces_3", "'$3': illegal character within { }" },
- { "~BadDecDigit_3", "'$3': invalid decimal digit" },
- { "~BadFileURIAuthority_2", "\"$2\": invalid authority for \"file\" scheme" },
- { "~BadHexDigit_3", "'$3': invalid hexedecimal digit" },
- { "~BadHexSequence", "invalid hexedecimal sequence" },
- { "~BadItem", "invalid item" },
- { "~BadIterator", "invalid iterator" },
- { "~BadLibraryModule", "invalid library module" },
- { "~BadPath", "invalid path" },
- { "~BadStreamState", "bad I/O stream state" },
- { "~BadTokenInBraces_3", "\"$3\": illegal token within { }" },
- { "~BadTraceStream", "trace stream not retrievable using SerializationCallback" },
- { "~BadTypeFor_23", "\"$2\": invalid type for $3" },
- { "~BadType_23o", "\"$2\": invalid type${: 3}" },
- { "~BadURIScheme_3", "\"$3\": unknown URI scheme" },
- { "~BadURISyntaxForScheme_3", "invalid URI syntax for \"$3\" scheme" },
- { "~BadUnicodeChar_3", "\"$3\": invalid character code-point" },
- { "~BadWordNetPartOfSpeech_2", "\"$2\": invalid part-of-speech" },
- { "~BadWordNetPtr_2", "\"$2\": invalid pointer type" },
- { "~BadXMLDocument_2o", "malformed XML document${ at \"2\"}" },
- { "~BadXMLForXQDoc_3", "can not parse as XML for xqdoc: $3" },
- { "~BadXQueryVersion", "unsupported XQuery version" },
- { "~Base64BadChar", "invalid Base64 character" },
- { "~Base64Equals", "in Base64, '=' must be at the end and followed by one of [AEIMQUYcgkosw048]" },
- { "~Base64EqualsEquals", "in Base64, \"==\" must be at the end and followed by one of [AQgw]" },
- { "~Base64Multiple4", "Base64 data must be a multiple of 4 characters" },
- { "~BaseURI", "base URI" },
- { "~BoxCondTooManyColumns", "box condition has more columns than index" },
- { "~CastFromToFailed_34", "$3 to $4 cast failed" },
- { "~CharExpected_3", "'$3' expected" },
- { "~CloneNotImplemented", "clone() not implemented for expression" },
- { "~ClosingBraceWithoutOpen", "'}' encountered without '{' first" },
- { "~CollectionIteratorNotOpen", "collection iterator not open" },
- { "~CountClause11", "\"count\" clause only available in XQuery 1.1 or later" },
- { "~DefaultCollation", "default collation" },
- { "~DivisionNoINF", "division can not have +-INF dividend" },
- { "~DivisionNoNaN", "division can not involve NaN" },
- { "~DocNodeMultipleElements", "document node has more than one element" },
- { "~EBVNotDefSeq_5", "effective boolean value not defined for sequence of more than one item that starts with \"$5\"" },
- { "~EffectiveBooleanValue", "effective boolean value" },
- { "~ElementName", "element name" },
- { "~EmptyPath", "empty path" },
- { "~EmptySeqNoCastToQName", "empty sequence can not be cast to QName" },
- { "~EmptySeqNoCastToTypeWithQuantOne", "empty sequence can not be cast to type with quantifier '1'" },
- { "~EmptySeqNoFnRemoveArg", "empty sequence not allowed as 2nd argument of fn:remove()" },
- { "~EmptySeqNoPromoteTo", "empty sequence can not be promoted to type \"$2\"" },
- { "~EmptySeqNoSearchItem", "empty sequence not allowed as search item of fn:index-of()" },
- { "~EmptySeqNotAsFunctionResult_23", "empty sequence not allowed as result of function $2() that returns \"$3\"" },
- { "~EmptySequence", "empty sequence" },
- { "~ErrorCodeMessage_12", "error $2: $3" },
- { "~Eval11", "\"eval\" only available in XQuery 1.1 or later" },
- { "~ExpectedNumericOrDurationType", "expected numeric or duration type" },
- { "~ExpectedNumericType", "expected numeric type" },
- { "~ExpectedType_5", "expected type \"$5\"" },
- { "~ExprNoReturnUpdateList", "expression does not return a pending update list" },
- { "~ExprReturnsTooManyUpdateLists", "expression does not return a pending update list" },
- { "~ExternFnDeterministic", "only external functions may be declared deterministic" },
- { "~ExternFnNondeterministic", "only external functions may be declared nondeterministic" },
- { "~FileNotFoundOrReadable", "file not found or readable" },
- { "~FnNilledArgNotNode", "fn:nilled() argument not a node" },
- { "~FnOnlyInXQueryVersion_3", "function only available in XQuery $3" },
- { "~FullTextNotEnabled", "full-text was not enabled in this build" },
- { "~FunctionFailedErrorCodeMessage_123", "$2 failed (error $3): $4" },
- { "~FunctionFailed_12o", "$2 failed${: 3}" },
- { "~FunctionUndeclared_3", "function with arity $3 not declared" },
- { "~GoodValuesAreUTF8", "valid values are: UTF-8, UTF-16" },
- { "~GoodValuesAreXMLEtc", "valid values are: xml, html, xhtml, text, binary" },
- { "~GoodValuesAreYesNo", "valid values are: yes, no" },
- { "~GoodValuesAreYesNoOmit", "valid values are: yes, no, omit" },
- { "~GroupByVarHasMoreThanOneItem_2", "\"$2\": value of groupby variable has more than one item" },
- { "~HexBinaryMustBeEven", "HexBinary value must contain an even number of characters" },
- { "~IncompleteKeyInIndexBuild", "incomplete key during index build" },
- { "~IncompleteKeyInIndexRefresh", "incomplete key during index refresh" },
- { "~LibModVersionMismatch_3", "XQuery library version can not be imported by a $3 version module" },
- { "~ModuleDeclNotInMain", "module declaration must not be in main module" },
- { "~ModuleNotFound", "module not found" },
- { "~MustBeAbsoluteURI", "must be absolute" },
- { "~MustBeNCName", "must be an xs:NCName" },
- { "~NoAttrNodesInDocument", "document node must not contain attribute nodes" },
- { "~NoBindURI", "namespace URI can not be bound to prefix" },
- { "~NoCastToCInt_2", "\"$2\": 2nd operand can not be cast from \"xs:integer\" to C++ \"int\"" },
- { "~NoCastTo_34o", "can not cast to \"$3\"${: 4}" },
- { "~NoCastTo_45o", "can not cast to \"$4\"${: 5}" },
- { "~NoCompareTypes_23", "can not compare item of type $2 with item of type $3" },
- { "~NoCompareWithType_4", "can not compare for equality to type \"$4\"" },
- { "~NoDriveSpecification", "missing drive specification" },
- { "~NoEmptyLocalname", "local-name can not be empty" },
- { "~NoEmptySeqAsBaseURI", "can't treat empty sequence as base URI" },
- { "~NoEmptySeqAsCollationParam", "empty-sequence not allowed as collation parameter" },
- { "~NoHashItemOfType_2", "can not hash item of type \"$2\"" },
- { "~NoInputData", "no input data" },
- { "~NoModuleURIResolver", "no module URI resolver could be retrieved using SerializationCallback" },
- { "~NoMultiKeyNodeValues_2", "node with more than one key value found during probe on index \"$2\"" },
- { "~NoParseFnArity", "could not parse function arity (maybe it's too large)" },
- { "~NoRebindPrefix", "can not rebind predefined prefix" },
- { "~NoRegisteredSerializationCallback_2", "external module \"$2\" not available using registered SerializationCallback" },
- { "~NoResolveRelativeURI", "could not resolve relative URI" },
- { "~NoSeqAsArithOp", "sequence of more than one item can not be operand for arithmetic operation" },
- { "~NoSeqAsCollationParam", "sequence of more than one item not allowed as collation parameter" },
- { "~NoSeqCastToTypeWithQuantOneOrQuestion", "sequence of more than one item can not be cast to type with quantifier '1' or '?'" },
- { "~NoSeqForFnOp_2", "sequence of more than one item can not be operand for function \"$2()\"" },
- { "~NoSeqInValueComp", "sequnce of more than one item can not be in value comparisons" },
- { "~NoSeqTestedForAtomicEquiv", "sequence of more than one item can not be tested for atomic value equivalence" },
- { "~NoSeqTypePromotion", "type promotion not possible on sequence of more than one item" },
- { "~NoSeqTypePromotion_23", "sequence of more than one item can not be promoted to the return type \"$2\" of function $3()" },
- { "~NoSerializationCallbackForDocColMod", "document, collection, or module resolver required but no SerializationCallback given" },
- { "~NoSerializationCallbackForModule", "no SerializationCallback for required external module \"$2\"" },
- { "~NoSerializationCallbackForTraceStream", "no SerializationCallback for required trace stream" },
- { "~NoSourceURI", "no URI" },
- { "~NoTreatAs_4", "can not treat as \"$4\"" },
- { "~NoTypeInCtx", "undefined type in current context" },
- { "~NoTypeInMainModule_4", "type of variable \"$4\" is not among the in-scope types of the main module" },
- { "~NoTypeInModule_45", "type of variable \"$4\" is not among the in-scope types module \"$5\"" },
- { "~NoTypePromotion_23", "\"$2\": can not promote to type \"$3\"" },
- { "~NoTypePromotion_234", "\"$2\": can not promote to return type \"$3\" of function $4()" },
- { "~NoURIAuthority", "no authority" },
- { "~NoURIInStore", "URI for document not found in store" },
- { "~NoURIScheme", "no URI scheme" },
- { "~NoUntypedKeyNodeValue_2", "node with untyped key value found during probe on index \"$2\"" },
- { "~NodeIDNeedsBytes_2", "nodeid requires more than $2 bytes" },
- { "~NodeIDTooBig", "nodeid component too big for encoding" },
- { "~NonClosedBackRef_3", "'$$3': non-closed backreference" },
- { "~NonFileThesaurusURI", "non-file thesaurus URI" },
- { "~NonLocalhostAuthority", "non-localhost authority" },
- { "~NonexistentBackRef_3", "'$$3': non-existent backreference" },
- { "~NotAllowedForTypeName", "not allowed for typeName (use xsd:untyped instead)" },
- { "~NotAmongInScopeSchemaTypes", "not among in-scope schema types" },
- { "~NotDefInDynamicCtx", "not defined in dynamic context" },
- { "~NotDocOrElementNode", "not a document or element node" },
- { "~NotInStaticCtx", "not found in static context" },
- { "~NotPlainFile", "not plain file" },
- { "~NotSpecified", "not specified" },
- { "~OpIsSameNodeMustHaveNodes", "op:is-same-node() must have nodes as parameters" },
- { "~OpNodeAfterMustHaveNodes", "op:node-after() must have nodes as parameters" },
- { "~OpNodeBeforeMustHaveNodes", "op:node-before() must have nodes as parameters" },
- { "~OperationNotDef_23", "$2 not defined for type \"$3\"" },
- { "~OperationNotPossibleWithTypes_234", "\"$2\": operation not possible with parameters of type \"$3\" and \"$4\"" },
- { "~OuterForClause11", "\"outer-for\" clause only available in XQuery 1.1 or later" },
- { "~ParseFragmentOptionCombinationNotAllowed", "specifying both $2 and $3 is an error" },
- { "~ParseFragmentOptionDSLNotAllowed", "if the e option is specified, none of the options d, s, or l may be enabled" },
- { "~ParserInitFailed", "parser initialization failed" },
- { "~ParserNoCreateTree", "XML tree creation failed" },
- { "~PromotionImpossible", "promotion not possible" },
- { "~QuotedColon_23", "\"$2\": $3" },
- { "~SEPM0009_Not10", "the version parameter has a value other than \"1.0\" and the doctype-system parameter is specified" },
- { "~SEPM0009_NotOmit", "the standalone attribute has a value other than \"omit\"" },
- { "~SchemaAttributeName", "schema-attribute name" },
- { "~SchemaElementName", "schema-element name" },
- { "~SchemaOutOfMemory", "OutOfMemoryException during parsing" },
- { "~SchemaParseError", "error during parsing" },
- { "~SchemaUnexpected", "unexpected exception during parsing" },
- { "~SearchKeyTypeMismatch_234", "\"$2\": search key type for index \"$3\" does not match expected type \"$4\"" },
- { "~SearchKeyTypeNoProbeIndex_23", "\"$2\": search key type can not probe index \"$3\"" },
- { "~SeqFnBody", "only a function declared sequential can have a body that is a sequential expression" },
- { "~SeqNoCastToQName", "sequence of more than one item can not be cast to QName" },
- { "~SingletonExpected_2o", "singleton expected${ (2)}" },
- { "~StackOverflow", "stack overflow" },
- { "~StartEndTagMismatch_23", "start tag \"$2\" does not match end tag \"$3\"" },
- { "~StingLiteral", "string literal" },
- { "~StringValue", "string value" },
- { "~SumImpossibleWithTypes_23", "sum not possible with parameters of type \"$2\" and \"$3\"" },
- { "~SwitchExpr11", "\"switch\" expressions only available in XQuery 1.1 or later" },
- { "~TrailingChar_3", "trailing '$3'" },
- { "~TryCatchExpr11", "\"try/catch\" expressions only available in XQuery 1.1 or later" },
- { "~TwoDecimalFormatsSameName_2", "\"$2\": two decimal formats with this name" },
- { "~TwoDefaultDecimalFormats", "two default decimal formats" },
- { "~TypeIsNotSubtype", "item type is not a subtype of \"$3\"" },
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_BAD_ESCAPE_SEQUENCE", "unrecognized backslash escape sequence" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_BAD_INTERVAL", "error in {min,max} interval" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_INTERNAL_ERROR", "an internal ICU error (bug) was detected" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_INVALID_BACK_REF", "backreference to a non-existent capture group" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_INVALID_FLAG", "invalid value for match mode flags" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_INVALID_RANGE", "in character range [x-y], x is greater than y" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_INVALID_STATE", "RegexMatcher in invalid state for requested operation" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_LOOK_BEHIND_LIMIT", "look-behind pattern matches must have a bounded maximum length" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_MAX_LT_MIN", "in {min,max}, max is less than min" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_MISMATCHED_PAREN", "incorrectly nested parentheses" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_MISSING_CLOSE_BRACKET", "missing ']'" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_NUMBER_TOO_BIG", "decimal number is too large" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_OCTAL_TOO_BIG", "octal character constants must be <= 0377" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_PROPERTY_SYNTAX", "incorrect Unicode property" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_RULE_SYNTAX", "syntax error" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_SET_CONTAINS_STRING", "can not have UnicodeSets containing strings" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_STACK_OVERFLOW", "backtrack stack overflow" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_STOPPED_BY_CALLER", "matching operation aborted by user callback fn" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_TIME_OUT", "maximum allowed match time exceeded" },
-#endif
-#if !defined(ZORBA_NO_UNICODE)
- { "~U_REGEX_UNIMPLEMENTED", "use of regular expression feature that is not yet implemented" },
-#endif
- { "~UnaryArithOp", "unary arithmetic operator" },
- { "~UnbalancedChar_3", "missing '$3'" },
- { "~UnexpectedElement", "unexpected element" },
- { "~VarValMustBeSingleItem_2", "\"$2\": variable value must be single item" },
- { "~Variable", "variable" },
- { "~VariabledHasNoValue", "variable has no value" },
- { "~VariabledUndeclared", "undeclared variable" },
- { "~WindowClause11", "\"window\" clause only available in XQuery 1.1 or later" },
- { "~XMLSchema", "XML schema" },
- { "~XQST0106_CONFLICTING", "conflicting" },
- { "~XQST0106_THE_SAME", "the same" },
- { "~XQueryVersionAtLeast10_2", "\"$2\": XQuery version must be at least 1.0" },
- { "~XUST0001_CONCAT", "comma expression with updating and non-updating branches" },
- { "~XUST0001_Generic", "updating expression illegal here" },
- { "~XUST0001_IF", "conditional expression with updating and non-updating branch" },
- { "~XUST0001_UDF_2", "\"$2\": function declared simple but body is updating" },
- { "~XUST0002_Transform", "transform expression witn non-updating or vacuous modify clause" },
- { "~XUST0002_UDF_2", "\"$2\": function declared updating but body is not updating or vacuous" },
- { "~ZDST0060_unknown_localname", "unknown localname ($3)" },
- { "~ZDST0060_unknown_namespace", "unknown namespace ($3)" },
- { "~ZXQD0004_NON_NEGATIVE", "given value must be non-negative ($2)" },
- { "~ZXQD0004_NOT_WITHIN_RANGE", "not within allowed range ($2)" },
- { "~ZXQP0004_TypeOps_is_in_scope_ForFunctionItemTypes", "TypeOps::is_in_scope() for function-item types" },
- { "~ZeroLenURI", "zero-length URI (and no base URI given)" },
- { "~Zorba API error", "Zorba API error" },
- { "~Zorba data-definition error", "Zorba data-definition error" },
- { "~Zorba dynamic error", "Zorba dynamic error" },
- { "~Zorba dynamic warning", "Zorba dynamic warning" },
- { "~Zorba error", "Zorba error" },
- { "~Zorba serialization error", "Zorba serialization error" },
- { "~Zorba serialization warning", "Zorba serialization warning" },
- { "~Zorba static error", "Zorba static error" },
- { "~Zorba static warning", "Zorba static warning" },
- { "~Zorba store error", "Zorba store error" },
- { "~Zorba type error", "Zorba type error" },
- { "~Zorba type warning", "Zorba type warning" },
- { "~Zorba warning", "Zorba warning" },
- { "~dynamic error", "dynamic error" },
- { "~dynamic warning", "dynamic warning" },
- { "~error", "error" },
- { "~format_integer_bad_picture_format", "bad $picture format: $2" },
- { "~format_integer_duplicated_optional_format_modifier", "duplicated optional format modifier '$2'" },
- { "~format_integer_optional_format_modifier_not_closed", "bad optional format modifier ($2), cannot find closing ')' " },
- { "~format_integer_picture_empty", "$picture parameter should not be empty" },
- { "~format_integer_unknown_optional_format_modifier_character", "unknown optional format modifier character '$2'" },
- { "~format_integer_value_1_10", "$value ($2) should be between 1 and 10 for this formatting picture" },
- { "~format_integer_value_1_20", "$value ($2) should be between 1 and 20 for this formatting picture" },
- { "~format_integer_value_gt_3000", "$value ($2) should be less than 3000 for Roman representation" },
- { "~full-text dynamic error", "full-text dynamic error" },
- { "~full-text dynamic warning", "full-text dynamic warning" },
- { "~full-text static error", "full-text static error" },
- { "~full-text static warning", "full-text static warning" },
- { "~full-text type error", "full-text type error" },
- { "~full-text type warning", "full-text type warning" },
- { "~operating system error", "operating system error" },
- { "~scripting static error", "scripting static error" },
- { "~scripting static warning", "scripting static warning" },
- { "~serialization error", "serialization error" },
- { "~serialization warning", "serialization warning" },
- { "~static error", "static error" },
- { "~static warning", "static warning" },
- { "~type error", "type error" },
- { "~type warning", "type warning" },
- { "~update dynamic error", "update dynamic error" },
- { "~update dynamic warning", "update dynamic warning" },
- { "~update static error", "update static error" },
- { "~update static warning", "update static warning" },
- { "~update type error", "update type error" },
- { "~update type warning", "update type warning" },
- { "~user-defined error", "user-defined error" },
- { "~user-defined warning", "user-defined warning" },
- { "~warning", "warning" },
- { "~xqueryx_empty_content", "xqueryx content is empty" },
-};
-DEF_DICT_END(en);
-
-} // namespace dict
-} // namespace diagnostic
-} // namespace zorba
-/*
- * Local variables:
- * mode: c++
- * End:
- */
+/**
+ * Copyright 2006-2011 The FLWOR Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+ /*
+ * THIS FILE IS GENERATED.
+ * PLEASE DO NOT EDIT.
+ */
+
+#include "stdafx.h"
+#include "zorba/config.h"
+#include "diagnostics/dict_impl.h"
+
+namespace zorba {
+namespace diagnostic {
+namespace dict {
+
+extern entry const dict_en[] = {
+ { "FOAR0001", "division by zero" },
+ { "FOAR0002", "numeric operation overflow/underflow${: 1}" },
+ { "FOCA0001", "\"$1\": value too large for decimal" },
+ { "FOCA0002", "\"$1\": invalid lexical value${: 2}" },
+ { "FOCA0003", "\"$1\": value too large for integer" },
+ { "FOCA0005", "NaN supplied as float/double value" },
+ { "FOCA0006", "\"$1\": string to be cast to decimal has too many digits of precision" },
+ { "FOCH0001", "\"$1\": invalid code point" },
+ { "FOCH0002", "\"$1\": unsuported collation${: 2}" },
+ { "FOCH0003", "\"$1\": unsupported normalization form" },
+ { "FOCH0004", "\"$1\": collation does not support collation units" },
+ { "FODC0001", "no context document for $1() function" },
+ { "FODC0002", "\"$1\": error retrieving resource${: 2}" },
+ { "FODC0003", "function stability not defined" },
+ { "FODC0004", "\"$1\": invalid argument to fn:collection()${: 2}" },
+ { "FODC0005", "\"$1\": invalid argument to fn:doc() or fn:doc-available()" },
+ { "FODC0006", "invalid content passed to $1: $2" },
+ { "FODC0007", "\"$1\": base URI passed to fn:parse() is not a valid absolute URI" },
+ { "FODF1280", "\"$1\": invalid decimal format name for fn:format-number()" },
+ { "FODF1310", "\"$1\": invalid fn:format-number() picture string" },
+ { "FODT0001", "overflow/underflow in date/time operation" },
+ { "FODT0002", "overflow/underflow in duration operation" },
+ { "FODT0003", "\"$1\": invalid timezone value" },
+ { "FOER0000", "unidentifier error" },
+ { "FOFI0001", "\"$1\": not castable to xs:language" },
+ { "FOFI0002", "invalid argument in format-integer: $1" },
+ { "FONS0004", "\"$1\": no namespace found for prefix" },
+ { "FONS0005", "base-URI not defined in the static context" },
+ { "FORG0001", "${\"1\": }invalid value for cast/constructor${: 2}" },
+ { "FORG0002", "\"$1\": invalid argument to fn:resolve-uri()${: 2}" },
+ { "FORG0003", "fn:zero-or-one() called with a sequnce containing more than one item" },
+ { "FORG0004", "fn:one-or-more() called with a sequence containing no items" },
+ { "FORG0005", "fn:exactly-one() called with a sequence containing zero or more than one item" },
+ { "FORG0006", "$1" },
+ { "FORG0008", "\"$1\" and \"$2\": two arguments to fn:dateTime() have inconsistent timezones" },
+ { "FORG0009", "error resolving a relative URI against a base URI in fn:resolve-uri()${: 1}" },
+ { "FORX0001", "'$1': invalid regular expression flag" },
+ { "FORX0002", "\"$1\": invalid regular expression${: 2}" },
+ { "FORX0003", "\"$1\": regular expression matches zero-length string" },
+ { "FORX0004", "\"$1\": invalid replacement string${: 2}" },
+ { "FOTY0012", "\"$1\": element node of type $2 does not have a typed value" },
+ { "FOTY0013", "\"$1\": argument to fn:data() is function item" },
+ { "FOTY0014", "\"$1\": argument to fn:string() is a function item" },
+ { "FOTY0015", "\"$1\": argument to fn:deep-equal() contains a function item" },
+ { "FOUP0001", "first operand of fn:put() is not a node of a supported kind" },
+ { "FOUP0002", "second operand of fn:put() is not a valid lexical representation of the xs:anyURI type" },
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTDY0016", "\"$1\": invalid weight: absolute value must be in [0,1000]" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTDY0017", "mild-not contains StringExclude" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTDY0020", "${\"1\": }invalid wildcard syntax${: 2}" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTST0008", "\"$1\": unknown stop-word list" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTST0009", "\"$1\": unsupported language" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTST0018", "\"$1\": unknown thesaurus" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "FTST0019", "\"$1\": match option specified more than once" },
+#endif
+ { "SENR0001", "\"$1\": can not serialize $2" },
+ { "SEPM0004", "doctype-system parameter, or standalone parameter with a value other than \"omit\", specified" },
+ { "SEPM0009", "omit-xml-declaration parameter is \"yes\" and $1" },
+ { "SEPM0010", "the output method is \"xml\", the value of the undeclare-prefixes parameter is \"yes\", and the value of the version parameter is \"1.0\"" },
+ { "SEPM0016", "\"$1\": value for parameter \"$2\" invalid${; $3}" },
+ { "SERE0003", "serializer can't satisfy the rules for either a well-formed XML document entity or a well-formed XML external general parsed entity" },
+ { "SERE0005", "invalid NCName character" },
+ { "SERE0006", "\"$1\": invalid character for XML version $2" },
+ { "SERE0008", "\"$1\": can not encode character as character reference here" },
+ { "SERE0012", "normalization-form parameter value is fully-normalized and any relevant construct of the result begins with a combining character" },
+ { "SERE0014", "\"#$1\": character not allowed for HTML output method" },
+ { "SERE0015", "can not use '>' within processing instruction for HTML output method" },
+ { "SESU0007", "\"$1\": unsupported encoding" },
+ { "SESU0011", "\"$1\": unsupported normalization form" },
+ { "SESU0013", "\"$1\": unsupported $2 version; supported versions are: $3" },
+ { "XPDY0002", "\"$1\": $2" },
+ { "XPDY0050", "invalid treat expression type" },
+ { "XPST0001", "${\"1\": }undefined value${: 2}" },
+ { "XPST0003", "invalid expression${: 1}" },
+ { "XPST0005", "static type must not be empty-sequence()" },
+ { "XPST0008", "\"$1\": undefined $2" },
+ { "XPST0017", "\"$1\": $2" },
+ { "XPST0051", "\"$1\": not defined as atomic type${: 2}" },
+ { "XPST0080", "\"$1\": invalid type for \"cast\" or \"castable\" exression" },
+ { "XPST0081", "\"$1\": can not expand namespace prefix to URI" },
+ { "XPST0083", "\"$1\": not a string literal" },
+ { "XPTY0004", "$1" },
+ { "XPTY0018", "path expression last step must not have nodes and atomic values" },
+ { "XPTY0019", "path expression non-last step must not be an atomic value" },
+ { "XPTY0020", "axis step context item is not a node" },
+ { "XQDY0025", "\"$1\": duplicate attribute name" },
+ { "XQDY0026", "computed processing instrucion must not contain \"?>\"" },
+ { "XQDY0027", "\"$1\": unexpected validity property${: 2}" },
+ { "XQDY0041", "can not cast to xs:NCName" },
+ { "XQDY0044", "\"$1\": invalid attibute node-name" },
+ { "XQDY0061", "invalid validate expression operand${: 1}" },
+ { "XQDY0064", "\"XML\": invalid name expression" },
+ { "XQDY0072", "comment must not contain \"--\" or end with \"-\"" },
+ { "XQDY0074", "${\"1\": }can not convert to expanded QName${: 2}" },
+ { "XQDY0084", "validated element does not have a top-level element declaration in the in-scope element declarations${: 1}" },
+ { "XQDY0091", "\"xml:id\" encountered" },
+ { "XQDY0092", "\"$1\": must be either \"preserve\" or \"default\"" },
+ { "XQDY0096", "\"$1\": invalid node-name" },
+ { "XQST0009", "schema import not supported" },
+ { "XQST0012", "invalid schema definitions" },
+ { "XQST0013", "invalid pragma content" },
+ { "XQST0022", "namespace declaration attribute is not a URI literal" },
+ { "XQST0031", "\"$1\": $2" },
+ { "XQST0032", "multiple base URI declarations" },
+ { "XQST0033", "\"$1\": namespace prefix already bound to \"$2\"" },
+ { "XQST0034", "\"$1\": duplicate function declaration" },
+ { "XQST0035", "\"$1\": name previosly imported" },
+ { "XQST0036", "$1" },
+ { "XQST0038", "multiple default collation declarations" },
+ { "XQST0039", "\"$1\": duplicate parameter name" },
+ { "XQST0040", "\"$1\": non-distinct expanded attribute QName" },
+ { "XQST0045", "\"$1\": invalid function or annotation namespace" },
+ { "XQST0046", "${\"1\": }invalid URI literal${: 2}" },
+ { "XQST0047", "\"$1\": duplicate target namespace" },
+ { "XQST0048", "\"$1\": not in library namespace" },
+ { "XQST0049", "\"$1\": duplicate variable declaration" },
+ { "XQST0054", "${\"1\": }variable must not depend on itself" },
+ { "XQST0055", "multiple copy-namespaces declarations" },
+ { "XQST0057", "empty target namespace" },
+ { "XQST0058", "\"$1\": duplicate target namespace" },
+ { "XQST0059", "\"$1\": target namespace not found for schema/module${ 2}" },
+ { "XQST0060", "\"$1\": function name has a null namespace URI" },
+ { "XQST0065", "multiple ordering mode declaraions" },
+ { "XQST0066", "multiple element/type/function namespace declarations" },
+ { "XQST0067", "multiple construction declarations" },
+ { "XQST0068", "multiple boundary-space declarations" },
+ { "XQST0069", "multiple empty order declarations" },
+ { "XQST0070", "\"$1\": $2" },
+ { "XQST0071", "\"$1\": duplicate namespace declaration attribute" },
+ { "XQST0076", "\"$1\": unknown collation" },
+ { "XQST0079", "unknown pragma or empty expression" },
+ { "XQST0085", "namespace URI is empty" },
+ { "XQST0087", "\"$1\": invalid encoding" },
+ { "XQST0088", "empty target namespace literal" },
+ { "XQST0089", "\"$1\": duplicate variable name" },
+ { "XQST0090", "\"$1\": invalid character reference in XML $2" },
+ { "XQST0093", "\"$1\": module must not depend on itself" },
+ { "XQST0098", "properties \"$1\" and \"$2\", representing characters used in picture string, do not have distinct values" },
+ { "XQST0106", "$1: multiple annotations with $2 names" },
+ { "XQST0111", "$1" },
+ { "XQTY0024", "element constructor content sequence must not have an attribute node following a non-attribute node" },
+ { "XQTY0030", "validate argument must be exactly one document or element node" },
+ { "XQTY0086", "typed value of copied element or attribute node is namespace-sensitive when construction mode is preserve and copy-namespaces mode is no-preserve" },
+ { "XSST0001", "\"$1\": function cannot be declared as both updating and sequential" },
+ { "XSST0002", "\"$1\": function declared sequential but has updating body" },
+ { "XSST0003", "\"$1\": function declared updating but has sequential body" },
+ { "XSST0004", "\"$1\": function declared nonsequential but has sequential body" },
+ { "XSST0005", "expression cannot be both updating and sequential" },
+ { "XSST0006", "sequential expression not allowed here" },
+ { "XSST0007", "\"$1\": variable not assignable" },
+ { "XSST0008", "\"while\" statement with non-sequential body" },
+ { "XSST0009", "\"break loop\" statement not inside while statement" },
+ { "XSST0010", "\"continue loop\" statement not inside while statement" },
+ { "XTDE1310", "\"$1\": picture string does not satisfy format-number() function rules" },
+ { "XTDE1340", "\"$1\": invalid picture string for date/time" },
+ { "XTDE1350", "component specifier not available" },
+ { "XUDY0009", "node has no parent in \"replace\" expression (without \"value of\")" },
+ { "XUDY0014", "\"modify\" can not modify node not created by \"copy\"" },
+ { "XUDY0015", "node is target of multiple \"rename\" expressions in same query" },
+ { "XUDY0016", "node is target of multiple \"replace\" expressions (without \"value of\") in same query" },
+ { "XUDY0017", "node is target of multiple \"replace value of\" expressions in same query" },
+ { "XUDY0018", "\"$1\": function declared external, non-updating returns non-empty pending update list" },
+ { "XUDY0019", "\"$1\": function declated external, updating returns non-empty data model instance" },
+ { "XUDY0021", "updates violate constraint" },
+ { "XUDY0023", "\"$1\": namespace binding conflicts with $2=$3" },
+ { "XUDY0024", "\"$1\": namespace binding conflicts with $2=$3" },
+ { "XUDY0027", "target expression is empty sequence" },
+ { "XUDY0029", "node has no parent in \"insert\" expression (with \"before\" or \"after\")" },
+ { "XUDY0030", "insertion of attrhbute node before or after document node child" },
+ { "XUDY0031", "\"$1\": same URI used in multiple calls to fn:put() in same snapshot" },
+ { "XUST0001", "$1" },
+ { "XUST0002", "simple expression not allowed here" },
+ { "XUST0003", "multiple revalidation declarations" },
+ { "XUST0028", "\"$1\": function can not be updating with a return type" },
+ { "XUTY0004", "attribute node follows non-attribute node" },
+ { "XUTY0005", "target expression not a single element or document node" },
+ { "XUTY0006", "target expression not a single element, text, comment, or processing instruction node" },
+ { "XUTY0007", "target expression does not return a sequence of zero or more nodes" },
+ { "XUTY0008", "target expression not a single element, attribute, text, comment, or processing instruction node" },
+ { "XUTY0010", "replacement sequence does not consist of zero or more element, text, comment, or processing instruction nodes" },
+ { "XUTY0011", "replacement sequence does not consist of zero or more attribute nodes" },
+ { "XUTY0012", "multiple elements, attributes, or processing-instruction nodes returned" },
+ { "XUTY0013", "source expression of \"copy\" clause must return a single node" },
+ { "XUTY0022", "insertion of attribute node into document node" },
+ { "ZAPI0002", "XQuery compilation failed${: 1}" },
+ { "ZAPI0003", "XQuery not compiled" },
+ { "ZAPI0004", "XQuery already compiled" },
+ { "ZAPI0005", "XQuery already executing" },
+ { "ZAPI0006", "XQuery already closed" },
+ { "ZAPI0007", "cannot serialize pul" },
+ { "ZAPI0008", "can not execute a non-updating XQuery" },
+ { "ZAPI0009", "XQuery not compiled in debug mode" },
+ { "ZAPI0014", "\"$1\": invalid argument${: 2}" },
+ { "ZAPI0015", "\"$1\": createModule() function not found${: 2}" },
+ { "ZAPI0019", "\"$1\": external module already registered" },
+ { "ZAPI0020", "\"$1\": document already exists in store" },
+ { "ZAPI0021", "\"$1\": item to load is not a node" },
+ { "ZAPI0027", "cannot update dynamic context with iterators" },
+ { "ZAPI0028", "\"$1\": invalid node URI" },
+ { "ZAPI0039", "XQuery has iterator already" },
+ { "ZAPI0040", "iterator is not open" },
+ { "ZAPI0041", "iterator is already open" },
+ { "ZAPI0042", "iterator is closed" },
+ { "ZAPI0070", "\"$1\": invalid serialization method for SAX" },
+ { "ZAPI0080", "can not retrieve node-reference for a node that is not in a collection." },
+ { "ZCSE0001", "\"$1\": nonexistent input field" },
+ { "ZCSE0002", "\"$1\": incompatible input field${: type=2}${, class=3}" },
+ { "ZCSE0003", "\"$1\": unrecognized class field" },
+ { "ZCSE0004", "\"$1\": unresolved field reference" },
+ { "ZCSE0005", "class version for \"$1\" ($2) is too new; supported version is $3" },
+ { "ZCSE0006", "class version for \"$1\" ($2) is too old; minimum supported version is $3; use Zorba 0x$4 instead" },
+ { "ZCSE0007", "input archive used for out serialization" },
+ { "ZCSE0008", "output archive used for in serialization" },
+ { "ZCSE0009", "\"$1\": class not serializable" },
+ { "ZCSE0010", "\"$1\": item type not serializable; only atomic, node, function, and error items are supported" },
+ { "ZCSE0011", "input archive not Zorba archive" },
+ { "ZCSE0012", "\"$1\": incompatible archive version; expected \"$2\"" },
+ { "ZCSE0013", "failed to load pre-compiled query${: 1}" },
+ { "ZCSE0014", "cannot save execution plan: infinite circular dependencies" },
+ { "ZCSE0015", "cannot load execution plan: incompatible between 32/64 bits or little/big-endian" },
+ { "ZCSE0016", "cannot load execution plan saved from release mode Zorba into debug mode Zorba" },
+ { "ZCSE0017", "cannot load execution plan saved from debug mode Zorba into release mode Zorba" },
+ { "ZDDY0001", "\"$1\": collection not declared" },
+ { "ZDDY0002", "\"$1\": collection already exists" },
+ { "ZDDY0003", "\"$1\": collection does not exist" },
+ { "ZDDY0004", "\"$1\": can not update constant collection" },
+ { "ZDDY0005", "\"$1\": illegal insert into append-only collection" },
+ { "ZDDY0006", "\"$1\": illegal insert into queue collection" },
+ { "ZDDY0007", "\"$1\": illegal delete from append-only collection" },
+ { "ZDDY0008", "\"$1\": illegal delete from queue collection" },
+ { "ZDDY0009", "\"$1\": not all nodes to delete are at the beginning of this queue collection" },
+ { "ZDDY0010", "\"$1\": illegal update of read-only nodes" },
+ { "ZDDY0011", "\"$1\": collection does not contain node" },
+ { "ZDDY0012", "\"$1\": illegal insert into unordered collection" },
+ { "ZDDY0013", "\"$1\": can not delete collection because indexes reference it" },
+ { "ZDDY0014", "\"$1\": can not delete collection because integrity constraints reference it" },
+ { "ZDDY0015", "\"$1\": can not delete collection because there are references to its nodes" },
+ { "ZDDY0016", "\"$1\": multiple attemps to create a collection in the same snapshot" },
+ { "ZDDY0017", "node does not belong to any collection" },
+ { "ZDDY0018", "all nodes must be in same collection" },
+ { "ZDDY0020", "\"$1\": index domain expression yields nodes that are not in collection" },
+ { "ZDDY0021", "\"$1\": undeclared index" },
+ { "ZDDY0022", "\"$1\": index already exists" },
+ { "ZDDY0023", "\"$1\": index does not exist" },
+ { "ZDDY0024", "\"$1\": index uniqueness violation" },
+ { "ZDDY0025", "${\"1\": }invalid number of arguments in probe" },
+ { "ZDDY0026", "\"$1\": index range probe not allowed" },
+ { "ZDDY0027", "\"$1\": index multiple creates" },
+ { "ZDDY0028", "\"$1\": index domain has duplicate nodes" },
+ { "ZDDY0029", "\"$1\": index point-general probe not allowed" },
+ { "ZDDY0030", "\"$1\": index range-general probe not allowed" },
+ { "ZDDY0031", "\"$1\": integrity constraint is not declared" },
+ { "ZDDY0032", "\"$1\": integrity constraint is not activated" },
+ { "ZDDY0033", "\"$1\": integrity constraint not met for collection \"$2\"" },
+ { "ZDST0001", "\"$1\": collection already declared" },
+ { "ZDST0002", "\"$1\": collection already imported into module \"$2\"" },
+ { "ZDST0003", "\"$1\": collection declaration not allowed in main module" },
+ { "ZDST0004", "collection multiple property values" },
+ { "ZDST0006", "collection invalid property value" },
+ { "ZDST0007", "\"$1\": collection declaration in foreign module" },
+ { "ZDST0021", "\"$1\": index already declared" },
+ { "ZDST0022", "\"$1\": index already imported into module \"$2\"" },
+ { "ZDST0023", "\"$1\": index declaration not allowed in main module" },
+ { "ZDST0024", "index multiple property values" },
+ { "ZDST0026", "index invalid property value" },
+ { "ZDST0027", "\"$1\": index bad key type" },
+ { "ZDST0028", "\"$1\": index not deterministic" },
+ { "ZDST0029", "\"$1\": index invalid data source" },
+ { "ZDST0030", "\"$1\": index non-constant data source" },
+ { "ZDST0031", "\"$1\": index has free vars" },
+ { "ZDST0032", "\"$1\": index references context item" },
+ { "ZDST0033", "\"$1\": index non-simple expression" },
+ { "ZDST0034", "\"$1\": index can not do automatic maintenance" },
+ { "ZDST0035", "\"$1\": index general multikey" },
+ { "ZDST0036", "\"$1\": index declaration in foreign module" },
+ { "ZDST0041", "\"$1\": integrity constraint already declared" },
+ { "ZDST0044", "\"$1\": integrity constraint declaration not allowed in main module" },
+ { "ZDST0048", "\"$1\": integrity constraint declaration in foreign module" },
+ { "ZDST0060", "\"$1\": feature not supported; $2" },
+ { "ZDTY0001", "\"$1\": invalid node type in collection \"$2\"" },
+ { "ZDTY0010", "\"$1\": index domain expression yields a non-node item" },
+ { "ZDTY0011", "result of some key expression of index $1 does not match its declared type" },
+ { "ZDTY0012", "\"$1\": general range index key item has type for which no ordering relationship exists" },
+#if defined(ZORBA_WITH_DEBUGGER)
+ { "ZGDB0001", "" },
+#endif
+ { "ZOSE0001", "\"$1\": file not found" },
+ { "ZOSE0002", "\"$1\": not plain file" },
+ { "ZOSE0003", "stream read failure" },
+ { "ZOSE0004", "${\"1\": }I/O error${: 2}" },
+ { "ZOSE0005", "\"$1\": error loading dynamic library${: 2}" },
+ { "ZSTR0001", "\"$1\": index already exists" },
+ { "ZSTR0002", "\"$1\": index does not exist" },
+ { "ZSTR0003", "\"$1\": partial key insertion into index \"$2\"" },
+ { "ZSTR0004", "\"$1\": partial key deletion from index \"$2\"" },
+ { "ZSTR0005", "\"$1\": partial key probe into index \"$2\"" },
+ { "ZSTR0006", "for index \"$1\": $2" },
+ { "ZSTR0007", "\"$1\": unsupported probe condition for index \"$2\"" },
+ { "ZSTR0008", "\"$1\": collection already exists" },
+ { "ZSTR0009", "\"$1\": collection not found" },
+ { "ZSTR0010", "can not insert node into colletion \"$1\" because it already belongs to collection \"$2\"" },
+ { "ZSTR0011", "non-root node can not be inserted into collection \"$1\"" },
+ { "ZSTR0012", "non-node item used with collection \"$1\"" },
+ { "ZSTR0015", "\"$1\": integrity constraint already exists" },
+ { "ZSTR0016", "\"$1\": integrity constraint does not exist" },
+ { "ZSTR0020", "loader I/O error${: 1}" },
+ { "ZSTR0021", "loader parsing error${: 1}" },
+ { "ZSTR0030", "NodeID error${: 1}" },
+ { "ZSTR0040", "type error${: 1}" },
+ { "ZSTR0041", "NaN comparison" },
+ { "ZSTR0045", "duplicate node found in sequence" },
+ { "ZSTR0050", "\"$1\" not implemented for item type \"$2\"" },
+ { "ZSTR0055", "streamable string has already been consumed" },
+ { "ZSTR0060", "out of range: $1" },
+ { "ZWST0002", "\"$1\": unknown or unsupported annotation" },
+ { "ZWST0003", "\"$1\": function declared sequential, but has non-sequential body" },
+ { "ZWST0004", "Sequential FLWOR expr may not have the semantics you expect" },
+ { "ZXQD0001", "\"$1\": prefix not declared when calling function \"$2\" from $3" },
+ { "ZXQD0002", "\"$1\": $2" },
+ { "ZXQD0003", "inconsistent options to the parse-xml-fragment() function: $1" },
+ { "ZXQD0004", "invalid parameter: $1" },
+ { "ZXQD0005", "key with type $1 not subtype or castable to target type $2 of map ($3)" },
+ { "ZXQP0000", "no error" },
+ { "ZXQP0001", "dynamic runtime error${: 1}" },
+ { "ZXQP0002", "\"$1\": assertion failed" },
+ { "ZXQP0003", "internal error${: 1}" },
+ { "ZXQP0004", "not yet implemented: $1" },
+ { "ZXQP0005", "\"$1\": feature not enabled" },
+ { "ZXQP0007", "\"$1\": function signature does not match declaration" },
+ { "ZXQP0008", "\"$1\": function implementation not found" },
+ { "ZXQP0009", "\"$1\": function referred to by this local-name has the local-name \"$2\" instead" },
+ { "ZXQP0010", "\"$1\": builtin sequential function not implemented as sequential" },
+ { "ZXQP0013", "FxCharHeap error: $1 ($2)" },
+ { "ZXQP0016", "\"$1\": reserved module target namespace" },
+ { "ZXQP0017", "file access disabled" },
+ { "ZXQP0020", "\"$1\": invalid URI${: 2}" },
+ { "ZXQP0021", "user error" },
+ { "ZXQP0024", "XML does not match schema${: \"1\"}${ 2}" },
+ { "ZXQP0025", "item creation failed" },
+ { "ZXQP0026", "\"$1\": invalid enumerated value for $2" },
+ { "ZXQP0028", "\"$1\": target namespace not provided by module from $2" },
+ { "ZXQP0029", "\"$1\": module import not allowed" },
+ { "ZXQP0030", "deadlock" },
+ { "ZXQP0031", "malformed XQueryX XML input${: 1}" },
+ { "ZXQP0032", "error transforming XQueryX to XQuery${: 1}" },
+ { "ZXQP0036", "BreakIterator creation failed" },
+ { "ZXQP0037", "\"$1\": loaded module version \"$2\" does not match import version specification" },
+ { "ZXQP0038", "Query requires Zorba version \"$1\"; you are running Zorba \"$2\"" },
+ { "ZXQP0039", "\"$1\": invalid version specification" },
+ { "ZXQP0040", "\"$1\": function invokes a nondeterministic function but is missing the nondeterministic annotation" },
+ { "ZXQP0050", "\"$1\": feature not available" },
+ { "ZXQP0060", "\"$1\": unkown option" },
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "ZXQP8401", "\"$1\": wrong WordNet file version; should be \"$2\"" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "ZXQP8402", "thesaurus data endianness does not match CPU" },
+#endif
+#if !defined(ZORBA_NO_FULL_TEXT)
+ { "ZXQP8403", "thesaurus data error${: 1}" },
+#endif
+ { "~AllMatchesHasExcludes", "AllMatches contains StringExclude" },
+ { "~AlreadySpecified", "already specified" },
+ { "~ArithOpNotDefinedBetween_23", "arithmetic operation not defined between types \"$2\" and \"$3\"" },
+ { "~AtomizationHasMoreThanOneValue", "atomization has more than one value" },
+ { "~AtomizationOfGroupByMakesMoreThanOneItem", "atomization of groupby variable produces more than one item" },
+ { "~AttributeName", "attribute name" },
+ { "~AttributeNode", "attribute node" },
+ { "~BackRef0Illegal", "\"0\": illegal backreference" },
+ { "~BackRefIllegalInCharClass", "backreference illegal in character class" },
+ { "~BadAnyURI", "invalid xs:anyURI" },
+ { "~BadArgTypeForFn_2o34o", "${\"2\": }invalid argument type for function $3()${: 4}" },
+ { "~BadCharAfter_34", "'$3': illegal character after '$4'" },
+ { "~BadCharInBraces_3", "'$3': illegal character within { }" },
+ { "~BadDecDigit_3", "'$3': invalid decimal digit" },
+ { "~BadFileURIAuthority_2", "\"$2\": invalid authority for \"file\" scheme" },
+ { "~BadHexDigit_3", "'$3': invalid hexedecimal digit" },
+ { "~BadHexSequence", "invalid hexedecimal sequence" },
+ { "~BadItem", "invalid item" },
+ { "~BadIterator", "invalid iterator" },
+ { "~BadLibraryModule", "invalid library module" },
+ { "~BadPath", "invalid path" },
+ { "~BadStreamState", "bad I/O stream state" },
+ { "~BadTokenInBraces_3", "\"$3\": illegal token within { }" },
+ { "~BadTraceStream", "trace stream not retrievable using SerializationCallback" },
+ { "~BadTypeFor_23", "\"$2\": invalid type for $3" },
+ { "~BadType_23o", "\"$2\": invalid type${: 3}" },
+ { "~BadURIScheme_3", "\"$3\": unknown URI scheme" },
+ { "~BadURISyntaxForScheme_3", "invalid URI syntax for \"$3\" scheme" },
+ { "~BadUnicodeChar_3", "\"$3\": invalid character code-point" },
+ { "~BadWordNetPartOfSpeech_2", "\"$2\": invalid part-of-speech" },
+ { "~BadWordNetPtr_2", "\"$2\": invalid pointer type" },
+ { "~BadXMLDocument_2o", "malformed XML document${ at \"2\"}" },
+ { "~BadXMLForXQDoc_3", "can not parse as XML for xqdoc: $3" },
+ { "~BadXQueryVersion", "unsupported XQuery version" },
+ { "~Base64BadChar", "invalid Base64 character" },
+ { "~Base64Equals", "in Base64, '=' must be at the end and followed by one of [AEIMQUYcgkosw048]" },
+ { "~Base64EqualsEquals", "in Base64, \"==\" must be at the end and followed by one of [AQgw]" },
+ { "~Base64Multiple4", "Base64 data must be a multiple of 4 characters" },
+ { "~BaseURI", "base URI" },
+ { "~BoxCondTooManyColumns", "box condition has more columns than index" },
+ { "~CastFromToFailed_34", "$3 to $4 cast failed" },
+ { "~CharExpected_3", "'$3' expected" },
+ { "~CloneNotImplemented", "clone() not implemented for expression" },
+ { "~ClosingBraceWithoutOpen", "'}' encountered without '{' first" },
+ { "~CollectionIteratorNotOpen", "collection iterator not open" },
+ { "~CountClause11", "\"count\" clause only available in XQuery 1.1 or later" },
+ { "~DefaultCollation", "default collation" },
+ { "~DivisionNoINF", "division can not have +-INF dividend" },
+ { "~DivisionNoNaN", "division can not involve NaN" },
+ { "~DocNodeMultipleElements", "document node has more than one element" },
+ { "~EBVNotDefSeq_5", "effective boolean value not defined for sequence of more than one item that starts with \"$5\"" },
+ { "~EffectiveBooleanValue", "effective boolean value" },
+ { "~ElementName", "element name" },
+ { "~EmptyPath", "empty path" },
+ { "~EmptySeqNoCastToQName", "empty sequence can not be cast to QName" },
+ { "~EmptySeqNoCastToTypeWithQuantOne", "empty sequence can not be cast to type with quantifier '1'" },
+ { "~EmptySeqNoFnRemoveArg", "empty sequence not allowed as 2nd argument of fn:remove()" },
+ { "~EmptySeqNoPromoteTo", "empty sequence can not be promoted to type \"$2\"" },
+ { "~EmptySeqNoSearchItem", "empty sequence not allowed as search item of fn:index-of()" },
+ { "~EmptySeqNotAsFunctionResult_23", "empty sequence not allowed as result of function $2() that returns \"$3\"" },
+ { "~EmptySequence", "empty sequence" },
+ { "~ErrorCodeMessage_12", "error $2: $3" },
+ { "~Eval11", "\"eval\" only available in XQuery 1.1 or later" },
+ { "~ExpectedNumericOrDurationType", "expected numeric or duration type" },
+ { "~ExpectedNumericType", "expected numeric type" },
+ { "~ExpectedType_5", "expected type \"$5\"" },
+ { "~ExprNoReturnUpdateList", "expression does not return a pending update list" },
+ { "~ExprReturnsTooManyUpdateLists", "expression does not return a pending update list" },
+ { "~ExternFnDeterministic", "only external functions may be declared deterministic" },
+ { "~ExternFnNondeterministic", "only external functions may be declared nondeterministic" },
+ { "~FileNotFoundOrReadable", "file not found or readable" },
+ { "~FnNilledArgNotNode", "fn:nilled() argument not a node" },
+ { "~FnOnlyInXQueryVersion_3", "function only available in XQuery $3" },
+ { "~FullTextNotEnabled", "full-text was not enabled in this build" },
+ { "~FunctionFailedErrorCodeMessage_123", "$2 failed (error $3): $4" },
+ { "~FunctionFailed_12o", "$2 failed${: 3}" },
+ { "~FunctionUndeclared_3", "function with arity $3 not declared" },
+ { "~GoodValuesAreUTF8", "valid values are: UTF-8, UTF-16" },
+ { "~GoodValuesAreXMLEtc", "valid values are: xml, html, xhtml, text, binary" },
+ { "~GoodValuesAreYesNo", "valid values are: yes, no" },
+ { "~GoodValuesAreYesNoOmit", "valid values are: yes, no, omit" },
+ { "~GroupByVarHasMoreThanOneItem_2", "\"$2\": value of groupby variable has more than one item" },
+ { "~HexBinaryMustBeEven", "HexBinary value must contain an even number of characters" },
+ { "~IncompleteKeyInIndexBuild", "incomplete key during index build" },
+ { "~IncompleteKeyInIndexRefresh", "incomplete key during index refresh" },
+ { "~LibModVersionMismatch_3", "XQuery library version can not be imported by a $3 version module" },
+ { "~ModuleDeclNotInMain", "module declaration must not be in main module" },
+ { "~ModuleNotFound", "module not found" },
+ { "~MustBeAbsoluteURI", "must be absolute" },
+ { "~MustBeNCName", "must be an xs:NCName" },
+ { "~NoAttrNodesInDocument", "document node must not contain attribute nodes" },
+ { "~NoBindURI", "namespace URI can not be bound to prefix" },
+ { "~NoCastToCInt_2", "\"$2\": 2nd operand can not be cast from \"xs:integer\" to C++ \"int\"" },
+ { "~NoCastTo_34o", "can not cast to \"$3\"${: 4}" },
+ { "~NoCastTo_45o", "can not cast to \"$4\"${: 5}" },
+ { "~NoCompareTypes_23", "can not compare item of type $2 with item of type $3" },
+ { "~NoCompareWithType_4", "can not compare for equality to type \"$4\"" },
+ { "~NoDriveSpecification", "missing drive specification" },
+ { "~NoEmptyLocalname", "local-name can not be empty" },
+ { "~NoEmptySeqAsBaseURI", "can't treat empty sequence as base URI" },
+ { "~NoEmptySeqAsCollationParam", "empty-sequence not allowed as collation parameter" },
+ { "~NoHashItemOfType_2", "can not hash item of type \"$2\"" },
+ { "~NoInputData", "no input data" },
+ { "~NoModuleURIResolver", "no module URI resolver could be retrieved using SerializationCallback" },
+ { "~NoMultiKeyNodeValues_2", "node with more than one key value found during probe on index \"$2\"" },
+ { "~NoParseFnArity", "could not parse function arity (maybe it's too large)" },
+ { "~NoRebindPrefix", "can not rebind predefined prefix" },
+ { "~NoRegisteredSerializationCallback_2", "external module \"$2\" not available using registered SerializationCallback" },
+ { "~NoResolveRelativeURI", "could not resolve relative URI" },
+ { "~NoSeqAsArithOp", "sequence of more than one item can not be operand for arithmetic operation" },
+ { "~NoSeqAsCollationParam", "sequence of more than one item not allowed as collation parameter" },
+ { "~NoSeqCastToTypeWithQuantOneOrQuestion", "sequence of more than one item can not be cast to type with quantifier '1' or '?'" },
+ { "~NoSeqForFnOp_2", "sequence of more than one item can not be operand for function \"$2()\"" },
+ { "~NoSeqInValueComp", "sequnce of more than one item can not be in value comparisons" },
+ { "~NoSeqTestedForAtomicEquiv", "sequence of more than one item can not be tested for atomic value equivalence" },
+ { "~NoSeqTypePromotion", "type promotion not possible on sequence of more than one item" },
+ { "~NoSeqTypePromotion_23", "sequence of more than one item can not be promoted to the return type \"$2\" of function $3()" },
+ { "~NoSerializationCallbackForDocColMod", "document, collection, or module resolver required but no SerializationCallback given" },
+ { "~NoSerializationCallbackForModule", "no SerializationCallback for required external module \"$2\"" },
+ { "~NoSerializationCallbackForTraceStream", "no SerializationCallback for required trace stream" },
+ { "~NoSourceURI", "no URI" },
+ { "~NoTreatAs_4", "can not treat as \"$4\"" },
+ { "~NoTypeInCtx", "undefined type in current context" },
+ { "~NoTypeInMainModule_4", "type of variable \"$4\" is not among the in-scope types of the main module" },
+ { "~NoTypeInModule_45", "type of variable \"$4\" is not among the in-scope types module \"$5\"" },
+ { "~NoTypePromotion_23", "\"$2\": can not promote to type \"$3\"" },
+ { "~NoTypePromotion_234", "\"$2\": can not promote to return type \"$3\" of function $4()" },
+ { "~NoURIAuthority", "no authority" },
+ { "~NoURIInStore", "URI for document not found in store" },
+ { "~NoURIScheme", "no URI scheme" },
+ { "~NoUntypedKeyNodeValue_2", "node with untyped key value found during probe on index \"$2\"" },
+ { "~NodeIDNeedsBytes_2", "nodeid requires more than $2 bytes" },
+ { "~NodeIDTooBig", "nodeid component too big for encoding" },
+ { "~NonClosedBackRef_3", "'$$3': non-closed backreference" },
+ { "~NonFileThesaurusURI", "non-file thesaurus URI" },
+ { "~NonLocalhostAuthority", "non-localhost authority" },
+ { "~NonexistentBackRef_3", "'$$3': non-existent backreference" },
+ { "~NotAllowedForTypeName", "not allowed for typeName (use xsd:untyped instead)" },
+ { "~NotAmongInScopeSchemaTypes", "not among in-scope schema types" },
+ { "~NotDefInDynamicCtx", "not defined in dynamic context" },
+ { "~NotDocOrElementNode", "not a document or element node" },
+ { "~NotInStaticCtx", "not found in static context" },
+ { "~NotPlainFile", "not plain file" },
+ { "~NotSpecified", "not specified" },
+ { "~OpIsSameNodeMustHaveNodes", "op:is-same-node() must have nodes as parameters" },
+ { "~OpNodeAfterMustHaveNodes", "op:node-after() must have nodes as parameters" },
+ { "~OpNodeBeforeMustHaveNodes", "op:node-before() must have nodes as parameters" },
+ { "~OperationNotDef_23", "$2 not defined for type \"$3\"" },
+ { "~OperationNotPossibleWithTypes_234", "\"$2\": operation not possible with parameters of type \"$3\" and \"$4\"" },
+ { "~OuterForClause11", "\"outer-for\" clause only available in XQuery 1.1 or later" },
+ { "~ParseFragmentOptionCombinationNotAllowed", "specifying both $2 and $3 is an error" },
+ { "~ParseFragmentOptionDSLNotAllowed", "if the e option is specified, none of the options d, s, or l may be enabled" },
+ { "~ParserInitFailed", "parser initialization failed" },
+ { "~ParserNoCreateTree", "XML tree creation failed" },
+ { "~PromotionImpossible", "promotion not possible" },
+ { "~QuotedColon_23", "\"$2\": $3" },
+ { "~SEPM0009_Not10", "the version parameter has a value other than \"1.0\" and the doctype-system parameter is specified" },
+ { "~SEPM0009_NotOmit", "the standalone attribute has a value other than \"omit\"" },
+ { "~SchemaAttributeName", "schema-attribute name" },
+ { "~SchemaElementName", "schema-element name" },
+ { "~SchemaOutOfMemory", "OutOfMemoryException during parsing" },
+ { "~SchemaParseError", "error during parsing" },
+ { "~SchemaUnexpected", "unexpected exception during parsing" },
+ { "~SearchKeyTypeMismatch_234", "\"$2\": search key type for index \"$3\" does not match expected type \"$4\"" },
+ { "~SearchKeyTypeNoProbeIndex_23", "\"$2\": search key type can not probe index \"$3\"" },
+ { "~SeqFnBody", "only a function declared sequential can have a body that is a sequential expression" },
+ { "~SeqNoCastToQName", "sequence of more than one item can not be cast to QName" },
+ { "~SingletonExpected_2o", "singleton expected${ (2)}" },
+ { "~StackOverflow", "stack overflow" },
+ { "~StartEndTagMismatch_23", "start tag \"$2\" does not match end tag \"$3\"" },
+ { "~StingLiteral", "string literal" },
+ { "~StringValue", "string value" },
+ { "~SumImpossibleWithTypes_23", "sum not possible with parameters of type \"$2\" and \"$3\"" },
+ { "~SwitchExpr11", "\"switch\" expressions only available in XQuery 1.1 or later" },
+ { "~TrailingChar_3", "trailing '$3'" },
+ { "~TryCatchExpr11", "\"try/catch\" expressions only available in XQuery 1.1 or later" },
+ { "~TwoDecimalFormatsSameName_2", "\"$2\": two decimal formats with this name" },
+ { "~TwoDefaultDecimalFormats", "two default decimal formats" },
+ { "~TypeIsNotSubtype", "item type is not a subtype of \"$3\"" },
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_BAD_ESCAPE_SEQUENCE", "unrecognized backslash escape sequence" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_BAD_INTERVAL", "error in {min,max} interval" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_INTERNAL_ERROR", "an internal ICU error (bug) was detected" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_INVALID_BACK_REF", "backreference to a non-existent capture group" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_INVALID_FLAG", "invalid value for match mode flags" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_INVALID_RANGE", "in character range [x-y], x is greater than y" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_INVALID_STATE", "RegexMatcher in invalid state for requested operation" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_LOOK_BEHIND_LIMIT", "look-behind pattern matches must have a bounded maximum length" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_MAX_LT_MIN", "in {min,max}, max is less than min" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_MISMATCHED_PAREN", "incorrectly nested parentheses" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_MISSING_CLOSE_BRACKET", "missing ']'" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_NUMBER_TOO_BIG", "decimal number is too large" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_OCTAL_TOO_BIG", "octal character constants must be <= 0377" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_PROPERTY_SYNTAX", "incorrect Unicode property" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_RULE_SYNTAX", "syntax error" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_SET_CONTAINS_STRING", "can not have UnicodeSets containing strings" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_STACK_OVERFLOW", "backtrack stack overflow" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_STOPPED_BY_CALLER", "matching operation aborted by user callback fn" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_TIME_OUT", "maximum allowed match time exceeded" },
+#endif
+#if !defined(ZORBA_NO_UNICODE)
+ { "~U_REGEX_UNIMPLEMENTED", "use of regular expression feature that is not yet implemented" },
+#endif
+ { "~UnaryArithOp", "unary arithmetic operator" },
+ { "~UnbalancedChar_3", "missing '$3'" },
+ { "~UnexpectedElement", "unexpected element" },
+ { "~VarValMustBeSingleItem_2", "\"$2\": variable value must be single item" },
+ { "~Variable", "variable" },
+ { "~VariabledHasNoValue", "variable has no value" },
+ { "~VariabledUndeclared", "undeclared variable" },
+ { "~WindowClause11", "\"window\" clause only available in XQuery 1.1 or later" },
+ { "~XMLSchema", "XML schema" },
+ { "~XQST0106_CONFLICTING", "conflicting" },
+ { "~XQST0106_THE_SAME", "the same" },
+ { "~XQueryVersionAtLeast10_2", "\"$2\": XQuery version must be at least 1.0" },
+ { "~XUST0001_CONCAT", "comma expression with updating and non-updating branches" },
+ { "~XUST0001_Generic", "updating expression illegal here" },
+ { "~XUST0001_IF", "conditional expression with updating and non-updating branch" },
+ { "~XUST0001_UDF_2", "\"$2\": function declared simple but body is updating" },
+ { "~XUST0002_Transform", "transform expression witn non-updating or vacuous modify clause" },
+ { "~XUST0002_UDF_2", "\"$2\": function declared updating but body is not updating or vacuous" },
+ { "~ZDST0060_unknown_localname", "unknown localname ($3)" },
+ { "~ZDST0060_unknown_namespace", "unknown namespace ($3)" },
+ { "~ZXQD0004_NON_NEGATIVE", "given value must be non-negative ($2)" },
+ { "~ZXQD0004_NOT_WITHIN_RANGE", "not within allowed range ($2)" },
+ { "~ZXQP0004_TypeOps_is_in_scope_ForFunctionItemTypes", "TypeOps::is_in_scope() for function-item types" },
+ { "~ZeroLenURI", "zero-length URI (and no base URI given)" },
+ { "~Zorba API error", "Zorba API error" },
+ { "~Zorba data-definition error", "Zorba data-definition error" },
+ { "~Zorba dynamic error", "Zorba dynamic error" },
+ { "~Zorba dynamic warning", "Zorba dynamic warning" },
+ { "~Zorba error", "Zorba error" },
+ { "~Zorba serialization error", "Zorba serialization error" },
+ { "~Zorba serialization warning", "Zorba serialization warning" },
+ { "~Zorba static error", "Zorba static error" },
+ { "~Zorba static warning", "Zorba static warning" },
+ { "~Zorba store error", "Zorba store error" },
+ { "~Zorba type error", "Zorba type error" },
+ { "~Zorba type warning", "Zorba type warning" },
+ { "~Zorba warning", "Zorba warning" },
+ { "~dynamic error", "dynamic error" },
+ { "~dynamic warning", "dynamic warning" },
+ { "~error", "error" },
+ { "~format_integer_bad_picture_format", "bad $picture format: $2" },
+ { "~format_integer_duplicated_optional_format_modifier", "duplicated optional format modifier '$2'" },
+ { "~format_integer_optional_format_modifier_not_closed", "bad optional format modifier ($2), cannot find closing ')' " },
+ { "~format_integer_picture_empty", "$picture parameter should not be empty" },
+ { "~format_integer_unknown_optional_format_modifier_character", "unknown optional format modifier character '$2'" },
+ { "~format_integer_value_1_10", "$value ($2) should be between 1 and 10 for this formatting picture" },
+ { "~format_integer_value_1_20", "$value ($2) should be between 1 and 20 for this formatting picture" },
+ { "~format_integer_value_gt_3000", "$value ($2) should be less than 3000 for Roman representation" },
+ { "~full-text dynamic error", "full-text dynamic error" },
+ { "~full-text dynamic warning", "full-text dynamic warning" },
+ { "~full-text static error", "full-text static error" },
+ { "~full-text static warning", "full-text static warning" },
+ { "~full-text type error", "full-text type error" },
+ { "~full-text type warning", "full-text type warning" },
+ { "~operating system error", "operating system error" },
+ { "~scripting static error", "scripting static error" },
+ { "~scripting static warning", "scripting static warning" },
+ { "~serialization error", "serialization error" },
+ { "~serialization warning", "serialization warning" },
+ { "~static error", "static error" },
+ { "~static warning", "static warning" },
+ { "~type error", "type error" },
+ { "~type warning", "type warning" },
+ { "~update dynamic error", "update dynamic error" },
+ { "~update dynamic warning", "update dynamic warning" },
+ { "~update static error", "update static error" },
+ { "~update static warning", "update static warning" },
+ { "~update type error", "update type error" },
+ { "~update type warning", "update type warning" },
+ { "~user-defined error", "user-defined error" },
+ { "~user-defined warning", "user-defined warning" },
+ { "~warning", "warning" },
+ { "~xqueryx_empty_content", "xqueryx content is empty" },
+};
+DEF_DICT_END(en);
+
+} // namespace dict
+} // namespace diagnostic
+} // namespace zorba
+/*
+ * Local variables:
+ * mode: c++
+ * End:
+ */
=== modified file 'src/runtime/strings/strings_impl.cpp'
--- src/runtime/strings/strings_impl.cpp 2011-08-10 18:58:11 +0000
+++ src/runtime/strings/strings_impl.cpp 2011-09-22 11:09:58 +0000
@@ -1,2091 +1,2091 @@
-/*
- * Copyright 2006-2008 The FLWOR Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "stdafx.h"
-
-#include <iostream>
-
-#include "common/common.h"
-
-#include "zorbamisc/ns_consts.h"
-#include "diagnostics/assert.h"
-#include "diagnostics/xquery_diagnostics.h"
-
-#include "zorbatypes/numconversions.h"
-
-#include "system/globalenv.h"
-
-#include "context/static_context.h"
-
-#include "compiler/api/compilercb.h"
-
-#include "runtime/strings/strings.h"
-#include "runtime/visitors/planiter_visitor.h"
-
-#include "store/api/item.h"
-#include "store/api/item_factory.h"
-
-#include "zorbautils/string_util.h"
-
-#include "util/regex.h"
-#include "util/utf8_util.h"
-#include "util/utf8_string.h"
-#include "util/string_util.h"
-#include "util/uri_util.h"
-#include "util/xml_util.h"
-
-
-using namespace std;
-
-namespace zorba {
-
-
-/**
- *______________________________________________________________________
- *
- * 7.2.1 fn:codepoints-to-string
- *
- * fn:codepoints-to-string($arg as xs:integer*) as xs:string
- *_______________________________________________________________________*/
-bool
-CodepointsToStringIterator::nextImpl(store::Item_t& result, PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- while(true)
- {
- if (consumeNext(item, theChildren [0].getp(), planState ))
- {
- {
- zstring lUtf8Code = item->getIntegerValue().toString();
- try
- {
- xs_unsignedInt lCode = ztd::aton<xs_unsignedInt>(lUtf8Code.c_str());
- if (!xml::is_valid(lCode))
- throw std::invalid_argument( lUtf8Code.str() );
- utf8::encode( lCode, &resStr );
- }
- catch ( std::exception const& )
- {
- throw XQUERY_EXCEPTION(
- err::FOCH0001, ERROR_PARAMS( lUtf8Code ), ERROR_LOC( loc )
- );
- }
- }
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state );
- break;
- }
- }
- STACK_END (state);
-}
-
-/**
- *______________________________________________________________________
- *
- * 7.2.2 fn:string-to-codepoints
- *
- * fn:string-to-codepoints($arg as xs:string?) as xs:integer*
- *_______________________________________________________________________
- */
-bool StringToCodepointsIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- // TODO Optimization for large strings: large strings mean that a large
- // integer vector should be stored in the state that is not good.
- store::Item_t item;
- zstring inputStr;
-
- StringToCodepointsIteratorState* state;
- DEFAULT_STACK_INIT(StringToCodepointsIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState ))
- {
- item->getStringValue2(inputStr);
-
- if (!inputStr.empty())
- {
- utf8::to_codepoints(inputStr, &state->theResult);
-
- while (state->theIterator < state->theResult.size())
- {
- GENV_ITEMFACTORY->createInteger(
- result,
- Integer(state->theResult[state->theIterator])
- );
-
- STACK_PUSH(true, state );
- state->theIterator = state->theIterator + 1;
- }
- }
- }
- STACK_END (state);
-}
-
-
-void StringToCodepointsIteratorState::init(PlanState& planState)
-{
- PlanIteratorState::init(planState);
- theIterator = 0;
- theResult.clear();
-}
-
-
-void StringToCodepointsIteratorState::reset(PlanState& planState)
-{
- PlanIteratorState::reset(planState);
- theIterator = 0;
- theResult.clear();
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.3.2 fn:compare
- *
- * fn:compare($comparand1 as xs:string?,
- * $comparand2 as xs:string?) as xs:integer
- * fn:compare($comparand1 as xs:string?,
- * $comparand2 as xs:string?,
- * $collation as xs:string) as xs:integer?
- *_______________________________________________________________________*/
-bool CompareStrIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t n0;
- store::Item_t n1;
- store::Item_t n2;
- int res;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(n0, theChildren[0].getp(), planState ))
- {
- if (consumeNext(n1, theChildren[1].getp(), planState ))
- {
- XQPCollator* coll;
-
- if (theChildren.size() == 3)
- {
- consumeNext(n2, theChildren[2].getp(), planState);
-
- coll = theSctx->get_collator(n2->getStringValue().str(), loc);
- }
- else
- {
- coll = theSctx->get_default_collator(loc);
- }
-
- res = utf8::compare(n0->getStringValue(), n1->getStringValue(), coll);
-
- res = (res < 0 ? -1 : (res > 0 ? 1 : 0));
-
- GENV_ITEMFACTORY->createInteger(result, Integer(res));
-
- STACK_PUSH(true, state);
- }
- }
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.3.3 fn:codepoint-equal
- *
- * fn:codepoint-equal($comparand1 as xs:string?,
- * $comparand2 as xs:string?) as xs:boolean?
- *_______________________________________________________________________*/
-bool CodepointEqualIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item0, theChildren [0].getp(), planState ))
- {
- if (consumeNext(item1, theChildren [1].getp(), planState ))
- {
- GENV_ITEMFACTORY->createBoolean(result,
- item0->getStringValue() == item1->getStringValue());
- STACK_PUSH(true, state);
- }
- }
- STACK_END(state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.1 fn:concat
- *
- * fn:concat($arg1 as xs:anyAtomicType?,
- * $arg2 as xs:anyAtomicType?,
- * ... ) as xs:string
- *_______________________________________________________________________*/
-bool ConcatStrIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t lItem;
- std::stringstream lResStream;
- zstring tmp;
-
- checked_vector<PlanIter_t>::const_iterator iter = theChildren.begin();
- checked_vector<PlanIter_t>::const_iterator end = theChildren.end();
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- for(; iter != end; ++iter )
- {
- if (consumeNext(lItem, *iter, planState))
- {
- lResStream << lItem->getStringValue();
-
- if (consumeNext(lItem, *iter, planState))
- {
- throw XQUERY_EXCEPTION(
- err::XPTY0004,
- ERROR_PARAMS( ZED( NoSeqForFnOp_2 ), "fn:concat" ),
- ERROR_LOC( loc )
- );
- }
- }
- }
-
- tmp = lResStream.str();
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, tmp), state);
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.2 fn:string-join
- *
- * fn:string-join($arg1 as xs:string*,
- * $arg2 as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool StringJoinIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
- zstring separator;
- bool lFirst;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if(theChildren.size() > 1)
- {
- consumeNext(item, theChildren[1].getp(), planState);
- item->getStringValue2(separator);
- }
-
- if (separator.empty())
- {
- while(true)
- {
- if (consumeNext(item, theChildren[0].getp(), planState))
- {
- item->appendStringValue(resStr);
- }
- else
- {
- GENV_ITEMFACTORY->createString(result, resStr);
- STACK_PUSH(true, state);
- break;
- }
- }
- }
- else
- {
- lFirst = true;
-
- while(true)
- {
- if (consumeNext(item, theChildren[0].getp(), planState))
- {
- if (!lFirst)
- {
- resStr += separator;
- item->appendStringValue(resStr);
- }
- else
- {
- item->getStringValue2(resStr);
- lFirst = false;
- }
- }
- else
- {
- GENV_ITEMFACTORY->createString(result, resStr);
- STACK_PUSH(true, state);
- break;
- }
- }
- }
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.3 fn:substring
- *
- *fn:substring($sourceString as xs:string?,
- * $startingLoc as xs:double) as xs:string
- *fn:substring($sourceString as xs:string?,
- * $startingLoc as xs:double,
- * $length as xs:double) as xs:string
- *_______________________________________________________________________*/
-bool SubstringIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t stringItem;
- store::Item_t startItem;
- store::Item_t lenItem;
- zstring strval;
- zstring resStr;
- xs_double start;
- xs_double len;
- xs_int istart;
- xs_int ilen;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(stringItem, theChildren[0].getp(), planState ))
- {
- stringItem->getStringValue2(strval);
-
- if (!strval.empty())
- {
- bool startExists = consumeNext(startItem, theChildren[1], planState);
-
- ZORBA_ASSERT(startExists);
-
- // note: The first character of a string is located at position 1,
- // not position 0.
-
- start = startItem->getDoubleValue();
-
- if (!start.isNaN())
- {
- if (start.isFinite())
- {
- try
- {
- istart = to_xs_int(start.round());
- }
- catch ( std::range_error const& )
- {
- istart = (xs_int)utf8_string<zstring>(strval).length();
- }
- }
- else
- {
- istart = (xs_int)utf8_string<zstring>(strval).length();
- }
-
- if( theChildren.size() == 2)
- {
- if (istart <= 0)
- {
- resStr = strval;
- }
- else
- {
- try
- {
- resStr = utf8_string<zstring>(strval).substr(istart-1);
- }
- catch (...)
- {
- zstring::size_type numChars = utf8_string<zstring>(strval).length();
- if (static_cast<zstring::size_type>(istart) > numChars)
- {
- // result is the empty string
- }
- else
- {
- throw;
- }
- }
- }
- }
- else
- {
- bool lenItemExists = consumeNext(lenItem, theChildren[2], planState);
-
- ZORBA_ASSERT(lenItemExists);
-
- len = lenItem->getDoubleValue();
-
- if (!len.isNaN())
- {
- if (len.isFinite())
- {
- try
- {
- ilen = to_xs_int(len.round());
- }
- catch ( std::range_error const& )
- {
- ilen = (xs_int)(utf8_string<zstring>(strval).length() - istart + 1);
- }
- }
- else
- {
- ilen = (xs_int)(utf8_string<zstring>(strval).length() - istart + 1);
- }
-
- if( !(start + len).isNaN())
- {
- if (ilen >= 0)
- {
- if (istart <= 0)
- {
- if ((ilen + istart - 1) >= 0)
- resStr = utf8_string<zstring>(strval).substr(0, istart - 1 + ilen);
- }
- else
- {
- try
- {
- resStr = utf8_string<zstring>(strval).substr(istart-1, ilen);
- }
- catch (...)
- {
- zstring::size_type numChars = utf8_string<zstring>(strval).length();
- if (static_cast<zstring::size_type>(istart) > numChars)
- {
- // result is the empty string
- }
- else
- {
- throw;
- }
- }
- }
- }
- }
- }
- }
- } // non NaN start arg
- } // non empty string arg
- } // non NULL string arg
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.4 fn:string-length
- *
- *fn:string-length() as xs:integer
- *fn:string-length($arg as xs:string?) as xs:integer
- *_______________________________________________________________________*/
-bool StringLengthIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring strval;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(strval);
-
- STACK_PUSH(
- GENV_ITEMFACTORY->createInteger(
- result, Integer( utf8::length( strval ) )
- ),
- state
- );
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createInteger(result, Integer::zero()),
- state);
- }
- STACK_END(state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.5 fn:normalize-space
- *
- *fn:normalize-space() as xs:string
- *fn:normalize-space($arg as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool NormalizeSpaceIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(resStr);
- ascii::normalize_whitespace(resStr);
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.6 fn:normalize-unicode
- *
- *fn:normalize-unicode($arg as xs:string?) as xs:string
- *fn:normalize-unicode($arg as xs:string?,
- * $normalizationForm as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool NormalizeUnicodeIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- zstring normForm;
- zstring resStr;
- unicode::normalization::type normType;
- bool success;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item0, theChildren[0], planState ))
- {
- if(theChildren.size() == 2)
- {
- if (!consumeNext(item1, theChildren[1].getp(), planState ))
- ZORBA_ASSERT(false);
-
- item1->getStringValue2(normForm);
- ascii::trim_whitespace(normForm);
- zstring tmp(normForm);
- utf8::to_upper(tmp, &normForm);
- }
- else
- {
- normForm = "NFC";
- }
-
- if(normForm.empty())
- {
- normType = unicode::normalization::none;
- }
- else if (ZSTREQ(normForm, "NFC"))
- {
- normType = unicode::normalization::NFC;
- }
- else if (ZSTREQ(normForm, "NFKC"))
- {
- normType = unicode::normalization::NFKC;
- }
- else if (ZSTREQ(normForm, "NFD"))
- {
- normType = unicode::normalization::NFD;
- }
- else if (ZSTREQ(normForm, "NFKD"))
- {
- normType = unicode::normalization::NFKD;
- }
- else
- {
- throw XQUERY_EXCEPTION(
- err::FOCH0003, ERROR_PARAMS( normForm ), ERROR_LOC( loc )
- );
- }
-
- item0->getStringValue2(resStr);
-#ifndef ZORBA_NO_UNICODE
- success = utf8::normalize(resStr, normType, &resStr);
- ZORBA_ASSERT(success);
-#endif//#ifndef ZORBA_NO_UNICODE
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state );
- }
- else
- {
- // must push empty string due to return type of function
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.7 fn:upper-case
- *
- *fn:upper-case($arg as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool UpperCaseIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
- zstring strval;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(strval);
-
- utf8::to_upper(strval, &resStr);
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.8 fn:lower-case
- *
- *fn:lower-case($arg as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool LowerCaseIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
- zstring strval;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(strval);
-
- utf8::to_lower(strval, &resStr);
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.9 fn:translate
- *
- *fn:translate($arg as xs:string?,
- * $mapString as xs:string,
- * $transString as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool TranslateIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t arg_item, map_item, trans_item;
- bool res = false;
- zstring arg_string;
- zstring map_string;
- zstring trans_string;
- zstring result_string;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if ( consumeNext( arg_item , theChildren[0].getp(), planState ) &&
- consumeNext( map_item , theChildren[1].getp(), planState ) &&
- consumeNext( trans_item, theChildren[2].getp(), planState ) ) {
-
- arg_string = arg_item ->getStringValue().str();
- map_string = map_item ->getStringValue().str();
- trans_string = trans_item->getStringValue().str();
-
- typedef std::map<unicode::code_point,unicode::code_point> cp_map_type;
- cp_map_type trans_map;
-
- if ( !map_string.empty() ) {
- utf8_string<zstring const> const u_map_string ( map_string );
- utf8_string<zstring const> const u_trans_string( trans_string );
-
- utf8_string<zstring const>::const_iterator
- map_i = u_map_string .begin(),
- map_end = u_map_string .end (),
- trans_i = u_trans_string.begin(),
- trans_end = u_trans_string.end ();
-
- for ( ; map_i != map_end && trans_i != trans_end; ++map_i, ++trans_i )
- trans_map[ *map_i ] = *trans_i;
-
- for ( ; map_i != map_end; ++map_i )
- trans_map[ *map_i ] = ~0;
- }
-
- utf8_string<zstring> u_result_string( result_string );
- utf8_string<zstring const> const u_arg_string( arg_string );
-
- utf8_string<zstring const>::const_iterator
- arg_i = u_arg_string.begin(),
- arg_end = u_arg_string.end ();
-
- for ( ; arg_i != arg_end; ++arg_i ) {
- unicode::code_point cp = *arg_i;
- cp_map_type::const_iterator const found_i = trans_map.find( cp );
- if ( found_i != trans_map.end() ) {
- cp = found_i->second;
- if ( cp == ~0 )
- continue;
- }
- u_result_string += cp;
- }
-
- res = GENV_ITEMFACTORY->createString(result, result_string);
- }
-
- if (!res)
- {
- res = GENV_ITEMFACTORY->createString(result, result_string);
- }
-
- STACK_PUSH( res, state );
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.10 fn:encode-for-uri
- *
- *fn:encode-for-uri($uri-part as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool EncodeForUriIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring resStr;
- zstring strval;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(strval);
- uri::encode(strval, &resStr, true);
- }
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.11 fn:iri-to-uri
- *
- *fn:iri-to-uri($iri as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool IriToUriIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring lStrIri;
- zstring lStrRes;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(lStrIri);
-
- utf8::iri_to_uri(lStrIri, &lStrRes);
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.4.12 fn:escape-html-uri
- *
- *fn:escape-html-uri($uri as xs:string?) as xs:string
- *_______________________________________________________________________*/
-bool EscapeHtmlUriIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring lStrUri;
- zstring lStrRes;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren [0].getp(), planState))
- {
- item->getStringValue2(lStrUri);
-
- utf8::to_html_uri(lStrUri, &lStrRes);
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
- }
- else
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.5.1 fn:contains
- *
- *fn:contains( $arg1 as xs:string?,
- * $arg2 as xs:string?) as xs:boolean
- *fn:contains( $arg1 as xs:string?,
- * $arg2 as xs:string?,
- * $collation as xs:string) as xs:boolean
- *_______________________________________________________________________*/
-bool ContainsIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- store::Item_t itemColl;
- bool resBool = false;
- zstring arg1;
- zstring arg2;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item0, theChildren[0].getp(), planState ))
- {
- item0->getStringValue2(arg1);
- }
-
- if (consumeNext(item1, theChildren[1].getp(), planState ))
- {
- item1->getStringValue2(arg2);
- }
-
- if (arg2.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
- }
- else if (arg1.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
- }
- else
- {
- if (theChildren.size() == 2)
- {
- resBool = (arg1.find(arg2) != zstring::npos);
- }
- else
- {
- if (consumeNext(itemColl, theChildren[2].getp(), planState ))
- {
- XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
- resBool = (utf8::find(arg1, arg2, coll) != zstring::npos);
- }
- }
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
- }
-
- STACK_END (state);
-}
-/*end class ContainsIterator*/
-
-/**
- *______________________________________________________________________
- *
- * 7.5.2 fn:starts-with
- *
- *fn:starts-with($arg1 as xs:string?,
- * $arg2 as xs:string?) as xs:boolean
- *fn:starts-with($arg1 as xs:string?,
- * $arg2 as xs:string?,
- * $collation as xs:string) as xs:boolean
- *_______________________________________________________________________*/
-bool StartsWithIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- store::Item_t itemColl;
- bool resBool = false;
- zstring arg1;
- zstring arg2;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (theChildren.size() == 2 || theChildren.size()==3)
- {
- if (consumeNext(item0, theChildren[0].getp(), planState ))
- {
- item0->getStringValue2(arg1);
- }
-
- if (consumeNext(item1, theChildren[1].getp(), planState ))
- {
- item1->getStringValue2(arg2);
- }
-
- if (arg2.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
- }
- else if (arg1.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
- }
- else
- {
- if (theChildren.size() == 2)
- {
- resBool = (arg1.find(arg2) == 0);
- }
- else
- {
- if (consumeNext(itemColl, theChildren[2].getp(), planState ))
- {
- XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
- resBool = (utf8::find(arg1, arg2, coll) == 0);
- }
- }
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
- }
- }
- STACK_END (state);
-}
-/*end class StartsWithIterator*/
-
-/**
- *______________________________________________________________________
- *
- * 7.5.3 fn:ends-with
- *
- *fn:ends-with($arg1 as xs:string?,
- * $arg2 as xs:string?) as xs:boolean
- *fn:ends-with($arg1 as xs:string?,
- * $arg2 as xs:string?,
- * $collation as xs:string) as xs:boolean
- *_______________________________________________________________________*/
-bool EndsWithIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- store::Item_t itemColl;
- bool resBool = false;
- zstring arg1;
- zstring arg2;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item0, theChildren[0].getp(), planState ))
- {
- item0->getStringValue2(arg1);
- }
-
- if (consumeNext(item1, theChildren[1].getp(), planState ))
- {
- item1->getStringValue2(arg2);
- }
-
- if (arg2.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
- }
- else if (arg1.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
- }
- else
- {
- if (theChildren.size() == 2)
- {
- resBool = utf8::ends_with(arg1, arg2);
- }
- else
- {
- if (consumeNext(itemColl, theChildren[2].getp(), planState ))
- {
- XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
-
- resBool = utf8::ends_with(arg1, arg2, coll);
- }
- }
- STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
- }
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.5.4 fn:substring-before
- *
- *fn:substring-before( $arg1 as xs:string?,
- * $arg2 as xs:string?) as xs:string
- *fn:substring-before( $arg1 as xs:string?,
- * $arg2 as xs:string?,
- * $collation as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool SubstringBeforeIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- store::Item_t itemColl;
- zstring::size_type index = zstring::npos;
- zstring arg1;
- zstring arg2;
- zstring resStr;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if(theChildren.size() == 2 || theChildren.size()==3)
- {
- if (consumeNext(item0, theChildren[0].getp(), planState ))
- {
- item0->getStringValue2(arg1);
- }
-
- if (consumeNext(item1, theChildren[1].getp(), planState ))
- {
- item1->getStringValue2(arg2);
- }
-
- if (arg1.empty() || arg2.empty())
- {
- STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
- }
- else
- {
- if (theChildren.size() == 2)
- {
- index = arg1.find(arg2);
- }
- else
- {
- if (consumeNext(itemColl, theChildren[2].getp(), planState ))
- {
- XQPCollator* coll = 0;
- coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
- index = utf8::find(arg1, arg2, coll);
- }
- }
-
- if (index != zstring::npos)
- resStr = arg1.substr(0, index);
-
- STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
- }
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.5.5 fn:substring-after
- *
- *fn:substring-after($arg1 as xs:string?,
- * $arg2 as xs:string?) as xs:string
- *fn:substring-after($arg1 as xs:string?,
- * $arg2 as xs:string?,
- * $collation as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool SubstringAfterIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item0;
- store::Item_t item1;
- store::Item_t itemColl;
- zstring::size_type startPos = zstring::npos;
- zstring arg1;
- zstring arg2;
- zstring resStr;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (theChildren.size() == 2 || theChildren.size() == 3)
- {
- if (consumeNext(item0, theChildren[0].getp(), planState ))
- {
- item0->getStringValue2(arg1);
- }
-
- if (consumeNext(item1, theChildren[1].getp(), planState ))
- {
- item1->getStringValue2(arg2);
- }
-
- if (arg1.empty())
- {
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- else if (arg2.empty())
- {
- resStr = arg1;
- STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
- }
- else
- {
- if (theChildren.size() == 2)
- {
- startPos = arg1.find(arg2);
- }
- else
- {
- if (consumeNext(itemColl, theChildren[2].getp(), planState))
- {
- XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
- startPos = utf8::find(arg1, arg2, coll);
- }
- }
-
- if (startPos != zstring::npos)
- {
- startPos += arg2.size();
- resStr = arg1.substr(startPos, arg1.size() - startPos);
- }
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
- }
- }
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.6.2 fn:matches
- *
- *fn:matches($input as xs:string?,
- * $pattern as xs:string) as xs:boolean
- *fn:matches($input as xs:string?,
- * $pattern as xs:string,
- * $flags as xs:string) as xs:boolean
- *_______________________________________________________________________*/
-bool FnMatchesIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- zstring input;
- zstring xquery_pattern;
- zstring flags;
- store::Item_t item;
- bool res = false;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren[0].getp(), planState))
- item->getStringValue2(input);
-
- if (!consumeNext(item, theChildren[1].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(xquery_pattern);
-
- if(theChildren.size() == 3)
- {
- if (!consumeNext(item, theChildren[2].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(flags);
- }
-
- try
- {
- zstring lib_pattern;
- convert_xquery_re( xquery_pattern, &lib_pattern, flags.c_str() );
- res = utf8::match_part(input, lib_pattern, flags.c_str());
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- STACK_PUSH(GENV_ITEMFACTORY->createBoolean(result, res), state);
-
- STACK_END(state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.6.3 fn:replace
- *
- *fn:replace($input as xs:string?,
- * $pattern as xs:string,
- * $replacement as xs:string) as xs:string
- *fn:replace($input as xs:string?,
- * $pattern as xs:string,
- * $replacement as xs:string,
- * $flags as xs:string) as xs:string
- *_______________________________________________________________________*/
-bool FnReplaceIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- zstring input;
- zstring flags;
- zstring pattern;
- zstring replacement, replacement2;
- zstring resStr;
- store::Item_t item;
- bool tmp;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren[0].getp(), planState))
- item->getStringValue2(input);
-
- if (!consumeNext(item, theChildren[1].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(pattern);
-
- if (!consumeNext(item, theChildren[2].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(replacement);
-
- if(theChildren.size() == 4)
- {
- if (!consumeNext(item, theChildren[3].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(flags);
- }
-
- try
- {
- tmp = utf8::match_part(zstring(), pattern, flags.c_str());
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- if (tmp)
- throw XQUERY_EXCEPTION(
- err::FORX0003, ERROR_PARAMS( pattern ), ERROR_LOC( loc )
- );
-
- { // local scope
- int num_capturing_groups = 0;
-
- bool got_paren = false;
- FOR_EACH( zstring, c, pattern ) {
- if ( got_paren && *c != '?' )
- ++num_capturing_groups;
- got_paren = *c == '(';
- }
-
- bool got_backslash = false, got_dollar = false;
- FOR_EACH( zstring, c, replacement ) {
- if ( got_backslash ) {
- switch ( *c ) {
- case '\\':
- case '$':
- replacement2 += '\\';
- replacement2 += *c;
- got_backslash = false;
- continue;
- default:
- throw XQUERY_EXCEPTION(
- err::FORX0004,
- ERROR_PARAMS( replacement, ZED( BadCharAfter_34 ), *c, '\\' ),
- ERROR_LOC( loc )
- );
- }
- }
- if ( got_dollar ) {
- if ( !ascii::is_digit( *c ) )
- throw XQUERY_EXCEPTION(
- err::FORX0004,
- ERROR_PARAMS( replacement, ZED( BadCharAfter_34 ), *c, '$' ),
- ERROR_LOC( loc )
- );
- if ( *c - '0' <= num_capturing_groups ) {
- replacement2 += '$';
- replacement2 += *c;
- }
- got_dollar = false;
- continue;
- }
- switch ( *c ) {
- case '\\':
- got_backslash = true;
- break;
- case '$':
- got_dollar = true;
- break;
- default:
- replacement2 += *c;
- break;
- }
- } // FOR_EACH
- if ( got_backslash )
- throw XQUERY_EXCEPTION(
- err::FORX0004,
- ERROR_PARAMS( replacement, ZED( TrailingChar_3 ), '\\' ),
- ERROR_LOC( loc )
- );
- if ( got_dollar )
- throw XQUERY_EXCEPTION(
- err::FORX0004,
- ERROR_PARAMS( replacement, ZED( TrailingChar_3 ), '$' ),
- ERROR_LOC( loc )
- );
- } // local scope
-
- try
- {
- zstring lib_pattern;
- convert_xquery_re( pattern, &lib_pattern, flags.c_str() );
- utf8::replace_all(input, lib_pattern, flags.c_str(), replacement2, &resStr);
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
-
- STACK_END (state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * 7.6.4 fn:tokenize
- *
- *fn:tokenize($input as xs:string?,
- * $pattern as xs:string) as xs:string*
- *fn:tokenize($input as xs:string?,
- * $pattern as xs:string,
- * $flags as xs:string) as xs:string*
- *_______________________________________________________________________
- */
-void FnTokenizeIteratorState::reset(PlanState& planState)
-{
- PlanIteratorState::reset(planState);
- theString.clear();
- start_pos = 0;
- hasmatched = false;
- thePattern.clear();
- theFlags.clear();
-}
-
-
-bool FnTokenizeIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- zstring token;
- store::Item_t item;
- bool tmp;
- zstring strval;
- unicode::string u_string;
-
- FnTokenizeIteratorState* state;
- DEFAULT_STACK_INIT(FnTokenizeIteratorState, state, planState);
-
- if (consumeNext(item, theChildren[0].getp(), planState))
- {
- item->getStringValue2(strval);
- state->theString = strval.str();
- }
-
- if (!consumeNext(item, theChildren[1].getp(), planState))
- ZORBA_ASSERT(false);
-
- item->getStringValue2(strval);
- state->thePattern = strval.str();
-
- if(theChildren.size() == 3)
- {
- if (!consumeNext(item, theChildren[2].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(strval);
-
- state->theFlags = strval.str();
- }
-
- try
- {
- static zstring const empty;
- tmp = utf8::match_part( empty, state->thePattern, state->theFlags );
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- if(tmp)
- throw XQUERY_EXCEPTION(
- err::FORX0003, ERROR_PARAMS( state->thePattern ), ERROR_LOC( loc )
- );
-
-
- while ((xs_unsignedInt)state->start_pos < state->theString.length ())
- {
- try
- {
- unicode::regex re;
- //
- // The RE needs to be compiled every time due to the weird stack macros.
- //
- re.compile( state->thePattern, state->theFlags );
- unicode::string u_token;
- bool const got_next = re.next_token(
- state->theString, &state->start_pos, &u_token, &state->hasmatched
- );
- utf8::to_string( u_token, &token );
- if ( !got_next )
- break;
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, token), state);
- }
-
- if(state->hasmatched)
- {
- //the last token is empty (is after the last match)
- token.clear();
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, token), state);
- }
- STACK_END(state);
-}
-
-/**
- *______________________________________________________________________
- *
- * 5.6.5 fn:analyze-string
- *
- *fn:analyze-string( $input as xs:string?,
- * $pattern as xs:string) as element(fn:analyze-string-result)
- *fn:analyze-string( $input as xs:string?,
- * $pattern as xs:string,
- * $flags as xs:string) as element(fn:analyze-string-result)
- *_______________________________________________________________________*/
-
-static void copyUtf8Chars(const char *&sin,
- int &utf8start,
- unsigned int &bytestart,
- int utf8end,
- zstring &out)
-{
- utf8::size_type clen;
- while(utf8start < utf8end)
- {
- clen = utf8::char_length(*sin);
- out.append(sin, clen);
- utf8start++;
- bytestart += clen;
- sin += clen;
- }
-}
-
-static void addNonMatchElement(store::Item_t &parent,
- int &match_end1,
- unsigned int &match_end1_bytes,
- int match_start2,
- const char *&strin)
-{
- store::Item_t non_match_elem;
- store::Item_t non_match_element_name;
- store::Item_t untyped_type_name;
- store::NsBindings ns_binding;
- zstring baseURI;
- GENV_ITEMFACTORY->createQName(untyped_type_name,
- "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
- GENV_ITEMFACTORY->createQName(non_match_element_name,
- static_context::W3C_FN_NS, "fn", "non-match");
- GENV_ITEMFACTORY->createElementNode(non_match_elem, parent, non_match_element_name, untyped_type_name, false, false, ns_binding, baseURI);
- //utf8_it += (match_start2 - match_end1);
- zstring non_match_str;
- //utf8_string<zstring> non_match_utf8(non_match_str);
- //while(match_end1 < match_start2)
- //{
- // non_match_utf8 += *utf8_it;
- // utf8_it++;
- // match_end1++;
- //}
- copyUtf8Chars(strin, match_end1, match_end1_bytes, match_start2, non_match_str);
- store::Item_t non_match_text_item;
- GENV_ITEMFACTORY->createTextNode(non_match_text_item, non_match_elem, non_match_str);
-}
-
-static void addGroupElement(store::Item_t &parent,
- store::Item_t &untyped_type_name,
- store::NsBindings &ns_binding,
- zstring &baseURI,
- int match_start2,
- int match_end2,
- unsigned int &match_end1_bytes,
- const char *&sin,
- unicode::regex &rx,
- int gparent,
- std::vector<int> &group_parent,
- int nr_pattern_groups,
- int &i)
-{
- int match_startg = match_start2;
- int match_endg = match_start2;
- int match_endgood = match_start2;
- store::Item_t group_element_name;
- store::Item_t nr_attrib_name;
- for(i=i+1;i<nr_pattern_groups;i++)
- {
- if(group_parent[i] < gparent)
- {
- i--;
- break;
- }
- match_startg = rx.get_match_start(i+1);
- if((match_startg < 0) && (gparent < 0))
- continue;
- if(match_endgood < match_startg)
- {
- //add non-group match text
- zstring non_group_str;
-
- copyUtf8Chars(sin, match_endgood, match_end1_bytes, match_startg, non_group_str);
- store::Item_t non_group_text_item;
- GENV_ITEMFACTORY->createTextNode(non_group_text_item, parent.getp(), non_group_str);
- }
- match_endg = rx.get_match_end(i+1);
- //add group match text
- GENV_ITEMFACTORY->createQName(group_element_name,
- static_context::W3C_FN_NS, "fn", "group");
- GENV_ITEMFACTORY->createQName(nr_attrib_name,
- "", "", "nr");
- store::Item_t group_elem;
- GENV_ITEMFACTORY->createElementNode(group_elem, parent, group_element_name, untyped_type_name, false, false, ns_binding, baseURI);
- char strid[40];
- sprintf(strid, "%d", i+1);
- zstring zstrid(strid);
- store::Item_t strid_item;
- GENV_ITEMFACTORY->createString(strid_item, zstrid);
- store::Item_t id_attrib_item;
- GENV_ITEMFACTORY->createAttributeNode(id_attrib_item, group_elem.getp(), nr_attrib_name, untyped_type_name, strid_item);
- if(match_startg < 0)
- continue;
- match_endgood = match_endg;
- if((i+1)<nr_pattern_groups)
- {
- if(group_parent[i+1] > gparent)
- {
- addGroupElement(group_elem, untyped_type_name, ns_binding, baseURI,
- match_startg, match_endg, match_end1_bytes,
- sin, rx,
- i, group_parent, nr_pattern_groups, i);
- continue;
- }
- }
- zstring group_str;
-
- copyUtf8Chars(sin, match_startg, match_end1_bytes, match_endg, group_str);
- store::Item_t group_text_item;
- GENV_ITEMFACTORY->createTextNode(group_text_item, group_elem.getp(), group_str);
- }
- //add last non-group match
- if(match_endgood < match_end2)
- {
- zstring non_group_str;
-
- copyUtf8Chars(sin, match_endgood, match_end1_bytes, match_end2, non_group_str);
- store::Item_t non_group_text_item;
- GENV_ITEMFACTORY->createTextNode(non_group_text_item, parent, non_group_str);
- }
-}
-
-static void addMatchElement(store::Item_t &parent,
- int match_start2,
- unsigned int &match_end1_bytes,
- int match_end2,
- //utf8_string<zstring_p>::const_iterator& utf8_it,
- const char *&sin,
- unicode::regex &rx,
- std::vector<int> &group_parent,
- int nr_pattern_groups)
-{
- store::Item_t match_element_name;
- store::Item_t untyped_type_name;
- store::NsBindings ns_binding;
- zstring baseURI;
- GENV_ITEMFACTORY->createQName(untyped_type_name,
- "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
- GENV_ITEMFACTORY->createQName(match_element_name,
- static_context::W3C_FN_NS, "fn", "match");
- store::Item_t match_elem;
- GENV_ITEMFACTORY->createElementNode(match_elem, parent, match_element_name, untyped_type_name, false, false, ns_binding, baseURI);
- int i = -1;
- addGroupElement(match_elem, untyped_type_name, ns_binding, baseURI, match_start2, match_end2, match_end1_bytes, sin, rx, -1, group_parent, nr_pattern_groups, i);
-}
-
-static void computePatternGroupsParents(zstring &xquery_pattern, std::vector<int> &group_parent)
-{
- utf8_string<zstring> utf8_pattern(xquery_pattern);
- utf8_string<zstring>::const_iterator c;
- std::list<int> parents;
- int i = 0;
-
- for(c = utf8_pattern.begin(); c != utf8_pattern.end(); c++)
- {
- if(*c == '\\')
- {
- c++;
- continue;
- }
- if(*c == '(')
- {
- //begin group
- if(parents.size())
- group_parent.push_back(parents.back());
- else
- group_parent.push_back(-1);
- parents.push_back(i);
- i++;
- }
- else if(*c == ')')
- {
- if(parents.size())
- parents.pop_back();
- }
- }
-}
-
-bool FnAnalyzeStringIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- bool is_input_stream = false;
- zstring input;
- std::istream *instream = NULL;
-#define STREAMBUF_CHUNK_SIZE 4*1024
- class SmartCharPtr
- {
- public:
- char *ptr;
- SmartCharPtr() : ptr(NULL) {}
- ~SmartCharPtr() {if(ptr) ::free(ptr);}
- };
- SmartCharPtr streambuf;
- zstring::size_type streambuf_allocated_size = 0;
- zstring::size_type streambuf_read = 0;
- //zstring::size_type streambuf_beg = 0;
- zstring xquery_pattern;
- zstring flags;
- store::Item_t item;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
- if (consumeNext(item, theChildren[0].getp(), planState))
- {
- if(!item->isStreamable())
- {
- item->getStringValue2(input);
- }
- else
- {
- instream = &item->getStream();
- is_input_stream = true;
- }
- }
-
- if (!consumeNext(item, theChildren[1].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(xquery_pattern);
-
- if(theChildren.size() == 3)
- {
- if (!consumeNext(item, theChildren[2].getp(), planState))
- ZORBA_ASSERT (false);
-
- item->getStringValue2(flags);
- }
-
- try
- {
- zstring lib_pattern;
- convert_xquery_re( xquery_pattern, &lib_pattern, flags.c_str() );
-
- if(is_input_stream)
- {
- streambuf.ptr = (char*)malloc(STREAMBUF_CHUNK_SIZE);
- streambuf_allocated_size = STREAMBUF_CHUNK_SIZE;
- instream->read(streambuf.ptr, streambuf_allocated_size);
- streambuf_read = (unsigned int)instream->gcount();
- if(streambuf_read == STREAMBUF_CHUNK_SIZE)
- {
- // Note: const_reverse_iterator would work here, but does not
- // compile with gcc 4.0.1 (which is the version in Xcode on MacOS 10.5).
- zstring::reverse_iterator xqit = xquery_pattern.rbegin();
- if((xqit != xquery_pattern.rend()) && (flags.find('m') == std::string::npos))
- {
- if(*xqit == '$')
- {
- xqit++;
- int bslashes = 0;
- while(xqit != xquery_pattern.rend())
- {
- if(*xqit == '\\')
- bslashes++;
- else
- break;
- }
- if(bslashes%2 == 0)
- {
- //better read all instream
- do{
- streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
- streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
- instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
- streambuf_read += (unsigned int)instream->gcount();
- }while(instream->gcount() == STREAMBUF_CHUNK_SIZE);
- }
- }
- }
- }
- }
-
- unicode::regex rx;
- rx.compile(lib_pattern, flags.c_str());
- int nr_pattern_groups = rx.get_pattern_group_count();
- std::vector<int> group_parent;
- computePatternGroupsParents(xquery_pattern, group_parent);
-
- //see if regex can match empty strings
- bool reachedEnd = false;
- rx.set_string("", 0);
- if(rx.find_next_match(&reachedEnd))
- {
- throw XQUERY_EXCEPTION(
- err::FORX0003, ERROR_PARAMS( lib_pattern )
- );
-
- }
-
- store::Item_t null_parent;
- store::Item_t result_element_name;
- store::Item_t untyped_type_name;
- store::NsBindings ns_binding;
- zstring baseURI;
- GENV_ITEMFACTORY->createQName(untyped_type_name,
- "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
- GENV_ITEMFACTORY->createQName(result_element_name,
- static_context::W3C_FN_NS, "fn", "analyze-string-result");
- GENV_ITEMFACTORY->createElementNode(result, NULL, result_element_name, untyped_type_name, false, false, ns_binding, baseURI);
-
- int nr_retry = 0;
- reachedEnd = false;
- do
- {
- const char *instr;
- if(!is_input_stream)
- {
- rx.set_string(input.data(), input.size());
- instr = input.c_str();
- streambuf_read = input.size();
- }
- else
- {
- unsigned int reducebytes = 0;
- if(!instream->eof())
- {
- //check the last bytes, maybe it is a truncated utf8 char
- unsigned int maxbytes = 6;
- if(maxbytes > streambuf_read)
- maxbytes = streambuf_read;
- for(reducebytes=1;reducebytes<=maxbytes;reducebytes++)
- {
- utf8::size_type clen = utf8::char_length(streambuf.ptr[streambuf_read-reducebytes]);
- if((clen > 1) && (clen > reducebytes))
- break;
- }
- if(reducebytes == (maxbytes+1))
- reducebytes = 0;
- }
- rx.set_string(streambuf.ptr, streambuf_read-reducebytes);
- instr = streambuf.ptr;
- }
- //zstring_p zinstr(instr);
- //utf8_string<zstring_p> utf8_instr(zinstr);
- //utf8_string<zstring_p>::const_iterator utf8_it = utf8_instr.begin();
-
- //int match_start1 = 0;
- int match_end1 = 0;
- unsigned int match_end1_bytes = 0;
- reachedEnd = false;
- while(rx.find_next_match(&reachedEnd))
- {
- int match_start2 = rx.get_match_start();
- int match_end2 = rx.get_match_end();
- ZORBA_ASSERT(match_start2 >= 0);
-
- if(is_input_stream && reachedEnd && !instream->eof())
- {
- //load some more data, maybe the match will be different
- break;
- }
-
- //construct the fn:non-match
- if(match_start2 > match_end1)
- {
- addNonMatchElement(result, match_end1, match_end1_bytes, match_start2, instr);
- }
-
- //construct the fn:match
- addMatchElement(result, match_start2, match_end1_bytes, match_end2, instr, rx, group_parent, nr_pattern_groups);
- match_end1 = match_end2;
- }
-
- if(is_input_stream && reachedEnd && !instream->eof())
- {
- //load some more data, maybe the match will be different
- if(match_end1_bytes)
- {
- memmove(streambuf.ptr, streambuf.ptr+match_end1_bytes, streambuf_read-match_end1_bytes);
- streambuf_read -= match_end1_bytes;
- nr_retry = 0;
- }
- else
- nr_retry++;
- if(!match_end1_bytes && (nr_retry == 2))
- {
- if(streambuf_allocated_size > streambuf_read)
- {
- instream->read(streambuf.ptr + streambuf_read, streambuf_allocated_size - streambuf_read);
- streambuf_read += (unsigned int)instream->gcount();
- }
- //better read all instream
- while(!instream->eof())
- {
- streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
- instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
- streambuf_read += (unsigned int)instream->gcount();
- streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
- }
- }
- else
- {
- //read some more data from instream
- if(streambuf_allocated_size > streambuf_read)
- {
- instream->read(streambuf.ptr + streambuf_read, streambuf_allocated_size - streambuf_read);
- streambuf_read += (unsigned int)instream->gcount();
- }
- else
- {
- streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
- instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
- streambuf_read += (unsigned int)instream->gcount();
- streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
- }
- }
- reachedEnd = false;
- }
- else
- {
- if(match_end1_bytes < streambuf_read)
- addNonMatchElement(result, match_end1, match_end1_bytes, streambuf_read, instr);
- if(is_input_stream && instream->eof())
- reachedEnd = true;
- }
-
- }while(is_input_stream && !reachedEnd);
- }
- catch(XQueryException& ex)
- {
- set_source( ex, loc );
- throw;
- }
-
- STACK_PUSH(true, state);
-
- STACK_END(state);
-}
-
-
-/**
- *______________________________________________________________________
- *
- * http://www.zorba-xquery.com/modules/string
- * string:materialize
- */
-
-bool StringMaterializeIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
- zstring lString;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
-#ifndef NDEBUG
- assert(consumeNext(item, theChildren[0].getp(), planState));
-#else
- consumeNext(item, theChildren[0].getp(), planState);
-#endif
- if (item->isStreamable()) {
- lString = item->getString();
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, lString), state);
- } else {
- result = item;
- STACK_PUSH(result != 0 , state);
- }
-
- STACK_END(state);
-}
-
-/**
- *______________________________________________________________________
- *
- * http://www.zorba-xquery.com/modules/string
- * string:materialize
- */
-bool StringIsStreamableIterator::nextImpl(
- store::Item_t& result,
- PlanState& planState) const
-{
- store::Item_t item;
-
- PlanIteratorState* state;
- DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
-
-#ifndef NDEBUG
- assert(consumeNext(item, theChildren[0].getp(), planState));
-#else
- consumeNext(item, theChildren[0].getp(), planState);
-#endif
- STACK_PUSH(GENV_ITEMFACTORY->createBoolean(result, item->isStreamable()), state);
-
- STACK_END(state);
-}
-
-} // namespace zorba
-/* vim:set et sw=2 ts=2: */
+/*
+ * Copyright 2006-2008 The FLWOR Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#include "stdafx.h"
+
+#include <iostream>
+
+#include "common/common.h"
+
+#include "zorbamisc/ns_consts.h"
+#include "diagnostics/assert.h"
+#include "diagnostics/xquery_diagnostics.h"
+
+#include "zorbatypes/numconversions.h"
+
+#include "system/globalenv.h"
+
+#include "context/static_context.h"
+
+#include "compiler/api/compilercb.h"
+
+#include "runtime/strings/strings.h"
+#include "runtime/visitors/planiter_visitor.h"
+
+#include "store/api/item.h"
+#include "store/api/item_factory.h"
+
+#include "zorbautils/string_util.h"
+
+#include "util/regex.h"
+#include "util/utf8_util.h"
+#include "util/utf8_string.h"
+#include "util/string_util.h"
+#include "util/uri_util.h"
+#include "util/xml_util.h"
+
+
+using namespace std;
+
+namespace zorba {
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.2.1 fn:codepoints-to-string
+ *
+ * fn:codepoints-to-string($arg as xs:integer*) as xs:string
+ *_______________________________________________________________________*/
+bool
+CodepointsToStringIterator::nextImpl(store::Item_t& result, PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ while(true)
+ {
+ if (consumeNext(item, theChildren [0].getp(), planState ))
+ {
+ {
+ zstring lUtf8Code = item->getIntegerValue().toString();
+ try
+ {
+ xs_unsignedInt lCode = ztd::aton<xs_unsignedInt>(lUtf8Code.c_str());
+ if (!xml::is_valid(lCode))
+ throw std::invalid_argument( lUtf8Code.str() );
+ utf8::encode( lCode, &resStr );
+ }
+ catch ( std::exception const& )
+ {
+ throw XQUERY_EXCEPTION(
+ err::FOCH0001, ERROR_PARAMS( lUtf8Code ), ERROR_LOC( loc )
+ );
+ }
+ }
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state );
+ break;
+ }
+ }
+ STACK_END (state);
+}
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.2.2 fn:string-to-codepoints
+ *
+ * fn:string-to-codepoints($arg as xs:string?) as xs:integer*
+ *_______________________________________________________________________
+ */
+bool StringToCodepointsIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ // TODO Optimization for large strings: large strings mean that a large
+ // integer vector should be stored in the state that is not good.
+ store::Item_t item;
+ zstring inputStr;
+
+ StringToCodepointsIteratorState* state;
+ DEFAULT_STACK_INIT(StringToCodepointsIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState ))
+ {
+ item->getStringValue2(inputStr);
+
+ if (!inputStr.empty())
+ {
+ utf8::to_codepoints(inputStr, &state->theResult);
+
+ while (state->theIterator < state->theResult.size())
+ {
+ GENV_ITEMFACTORY->createInteger(
+ result,
+ Integer(state->theResult[state->theIterator])
+ );
+
+ STACK_PUSH(true, state );
+ state->theIterator = state->theIterator + 1;
+ }
+ }
+ }
+ STACK_END (state);
+}
+
+
+void StringToCodepointsIteratorState::init(PlanState& planState)
+{
+ PlanIteratorState::init(planState);
+ theIterator = 0;
+ theResult.clear();
+}
+
+
+void StringToCodepointsIteratorState::reset(PlanState& planState)
+{
+ PlanIteratorState::reset(planState);
+ theIterator = 0;
+ theResult.clear();
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.3.2 fn:compare
+ *
+ * fn:compare($comparand1 as xs:string?,
+ * $comparand2 as xs:string?) as xs:integer
+ * fn:compare($comparand1 as xs:string?,
+ * $comparand2 as xs:string?,
+ * $collation as xs:string) as xs:integer?
+ *_______________________________________________________________________*/
+bool CompareStrIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t n0;
+ store::Item_t n1;
+ store::Item_t n2;
+ int res;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(n0, theChildren[0].getp(), planState ))
+ {
+ if (consumeNext(n1, theChildren[1].getp(), planState ))
+ {
+ XQPCollator* coll;
+
+ if (theChildren.size() == 3)
+ {
+ consumeNext(n2, theChildren[2].getp(), planState);
+
+ coll = theSctx->get_collator(n2->getStringValue().str(), loc);
+ }
+ else
+ {
+ coll = theSctx->get_default_collator(loc);
+ }
+
+ res = utf8::compare(n0->getStringValue(), n1->getStringValue(), coll);
+
+ res = (res < 0 ? -1 : (res > 0 ? 1 : 0));
+
+ GENV_ITEMFACTORY->createInteger(result, Integer(res));
+
+ STACK_PUSH(true, state);
+ }
+ }
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.3.3 fn:codepoint-equal
+ *
+ * fn:codepoint-equal($comparand1 as xs:string?,
+ * $comparand2 as xs:string?) as xs:boolean?
+ *_______________________________________________________________________*/
+bool CodepointEqualIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item0, theChildren [0].getp(), planState ))
+ {
+ if (consumeNext(item1, theChildren [1].getp(), planState ))
+ {
+ GENV_ITEMFACTORY->createBoolean(result,
+ item0->getStringValue() == item1->getStringValue());
+ STACK_PUSH(true, state);
+ }
+ }
+ STACK_END(state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.1 fn:concat
+ *
+ * fn:concat($arg1 as xs:anyAtomicType?,
+ * $arg2 as xs:anyAtomicType?,
+ * ... ) as xs:string
+ *_______________________________________________________________________*/
+bool ConcatStrIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t lItem;
+ std::stringstream lResStream;
+ zstring tmp;
+
+ checked_vector<PlanIter_t>::const_iterator iter = theChildren.begin();
+ checked_vector<PlanIter_t>::const_iterator end = theChildren.end();
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ for(; iter != end; ++iter )
+ {
+ if (consumeNext(lItem, *iter, planState))
+ {
+ lResStream << lItem->getStringValue();
+
+ if (consumeNext(lItem, *iter, planState))
+ {
+ throw XQUERY_EXCEPTION(
+ err::XPTY0004,
+ ERROR_PARAMS( ZED( NoSeqForFnOp_2 ), "fn:concat" ),
+ ERROR_LOC( loc )
+ );
+ }
+ }
+ }
+
+ tmp = lResStream.str();
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, tmp), state);
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.2 fn:string-join
+ *
+ * fn:string-join($arg1 as xs:string*,
+ * $arg2 as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool StringJoinIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+ zstring separator;
+ bool lFirst;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if(theChildren.size() > 1)
+ {
+ consumeNext(item, theChildren[1].getp(), planState);
+ item->getStringValue2(separator);
+ }
+
+ if (separator.empty())
+ {
+ while(true)
+ {
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ {
+ item->appendStringValue(resStr);
+ }
+ else
+ {
+ GENV_ITEMFACTORY->createString(result, resStr);
+ STACK_PUSH(true, state);
+ break;
+ }
+ }
+ }
+ else
+ {
+ lFirst = true;
+
+ while(true)
+ {
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ {
+ if (!lFirst)
+ {
+ resStr += separator;
+ item->appendStringValue(resStr);
+ }
+ else
+ {
+ item->getStringValue2(resStr);
+ lFirst = false;
+ }
+ }
+ else
+ {
+ GENV_ITEMFACTORY->createString(result, resStr);
+ STACK_PUSH(true, state);
+ break;
+ }
+ }
+ }
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.3 fn:substring
+ *
+ *fn:substring($sourceString as xs:string?,
+ * $startingLoc as xs:double) as xs:string
+ *fn:substring($sourceString as xs:string?,
+ * $startingLoc as xs:double,
+ * $length as xs:double) as xs:string
+ *_______________________________________________________________________*/
+bool SubstringIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t stringItem;
+ store::Item_t startItem;
+ store::Item_t lenItem;
+ zstring strval;
+ zstring resStr;
+ xs_double start;
+ xs_double len;
+ xs_int istart;
+ xs_int ilen;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(stringItem, theChildren[0].getp(), planState ))
+ {
+ stringItem->getStringValue2(strval);
+
+ if (!strval.empty())
+ {
+ bool startExists = consumeNext(startItem, theChildren[1], planState);
+
+ ZORBA_ASSERT(startExists);
+
+ // note: The first character of a string is located at position 1,
+ // not position 0.
+
+ start = startItem->getDoubleValue();
+
+ if (!start.isNaN())
+ {
+ if (start.isFinite())
+ {
+ try
+ {
+ istart = to_xs_int(start.round());
+ }
+ catch ( std::range_error const& )
+ {
+ istart = (xs_int)utf8_string<zstring>(strval).length();
+ }
+ }
+ else
+ {
+ istart = (xs_int)utf8_string<zstring>(strval).length();
+ }
+
+ if( theChildren.size() == 2)
+ {
+ if (istart <= 0)
+ {
+ resStr = strval;
+ }
+ else
+ {
+ try
+ {
+ resStr = utf8_string<zstring>(strval).substr(istart-1);
+ }
+ catch (...)
+ {
+ zstring::size_type numChars = utf8_string<zstring>(strval).length();
+ if (static_cast<zstring::size_type>(istart) > numChars)
+ {
+ // result is the empty string
+ }
+ else
+ {
+ throw;
+ }
+ }
+ }
+ }
+ else
+ {
+ bool lenItemExists = consumeNext(lenItem, theChildren[2], planState);
+
+ ZORBA_ASSERT(lenItemExists);
+
+ len = lenItem->getDoubleValue();
+
+ if (!len.isNaN())
+ {
+ if (len.isFinite())
+ {
+ try
+ {
+ ilen = to_xs_int(len.round());
+ }
+ catch ( std::range_error const& )
+ {
+ ilen = (xs_int)(utf8_string<zstring>(strval).length() - istart + 1);
+ }
+ }
+ else
+ {
+ ilen = (xs_int)(utf8_string<zstring>(strval).length() - istart + 1);
+ }
+
+ if( !(start + len).isNaN())
+ {
+ if (ilen >= 0)
+ {
+ if (istart <= 0)
+ {
+ if ((ilen + istart - 1) >= 0)
+ resStr = utf8_string<zstring>(strval).substr(0, istart - 1 + ilen);
+ }
+ else
+ {
+ try
+ {
+ resStr = utf8_string<zstring>(strval).substr(istart-1, ilen);
+ }
+ catch (...)
+ {
+ zstring::size_type numChars = utf8_string<zstring>(strval).length();
+ if (static_cast<zstring::size_type>(istart) > numChars)
+ {
+ // result is the empty string
+ }
+ else
+ {
+ throw;
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ } // non NaN start arg
+ } // non empty string arg
+ } // non NULL string arg
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.4 fn:string-length
+ *
+ *fn:string-length() as xs:integer
+ *fn:string-length($arg as xs:string?) as xs:integer
+ *_______________________________________________________________________*/
+bool StringLengthIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring strval;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(strval);
+
+ STACK_PUSH(
+ GENV_ITEMFACTORY->createInteger(
+ result, Integer( utf8::length( strval ) )
+ ),
+ state
+ );
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createInteger(result, Integer::zero()),
+ state);
+ }
+ STACK_END(state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.5 fn:normalize-space
+ *
+ *fn:normalize-space() as xs:string
+ *fn:normalize-space($arg as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool NormalizeSpaceIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(resStr);
+ ascii::normalize_whitespace(resStr);
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.6 fn:normalize-unicode
+ *
+ *fn:normalize-unicode($arg as xs:string?) as xs:string
+ *fn:normalize-unicode($arg as xs:string?,
+ * $normalizationForm as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool NormalizeUnicodeIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ zstring normForm;
+ zstring resStr;
+ unicode::normalization::type normType;
+ bool success;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item0, theChildren[0], planState ))
+ {
+ if(theChildren.size() == 2)
+ {
+ if (!consumeNext(item1, theChildren[1].getp(), planState ))
+ ZORBA_ASSERT(false);
+
+ item1->getStringValue2(normForm);
+ ascii::trim_whitespace(normForm);
+ zstring tmp(normForm);
+ utf8::to_upper(tmp, &normForm);
+ }
+ else
+ {
+ normForm = "NFC";
+ }
+
+ if(normForm.empty())
+ {
+ normType = unicode::normalization::none;
+ }
+ else if (ZSTREQ(normForm, "NFC"))
+ {
+ normType = unicode::normalization::NFC;
+ }
+ else if (ZSTREQ(normForm, "NFKC"))
+ {
+ normType = unicode::normalization::NFKC;
+ }
+ else if (ZSTREQ(normForm, "NFD"))
+ {
+ normType = unicode::normalization::NFD;
+ }
+ else if (ZSTREQ(normForm, "NFKD"))
+ {
+ normType = unicode::normalization::NFKD;
+ }
+ else
+ {
+ throw XQUERY_EXCEPTION(
+ err::FOCH0003, ERROR_PARAMS( normForm ), ERROR_LOC( loc )
+ );
+ }
+
+ item0->getStringValue2(resStr);
+#ifndef ZORBA_NO_UNICODE
+ success = utf8::normalize(resStr, normType, &resStr);
+ ZORBA_ASSERT(success);
+#endif//#ifndef ZORBA_NO_UNICODE
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state );
+ }
+ else
+ {
+ // must push empty string due to return type of function
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.7 fn:upper-case
+ *
+ *fn:upper-case($arg as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool UpperCaseIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+ zstring strval;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(strval);
+
+ utf8::to_upper(strval, &resStr);
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.8 fn:lower-case
+ *
+ *fn:lower-case($arg as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool LowerCaseIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+ zstring strval;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(strval);
+
+ utf8::to_lower(strval, &resStr);
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.9 fn:translate
+ *
+ *fn:translate($arg as xs:string?,
+ * $mapString as xs:string,
+ * $transString as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool TranslateIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t arg_item, map_item, trans_item;
+ bool res = false;
+ zstring arg_string;
+ zstring map_string;
+ zstring trans_string;
+ zstring result_string;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if ( consumeNext( arg_item , theChildren[0].getp(), planState ) &&
+ consumeNext( map_item , theChildren[1].getp(), planState ) &&
+ consumeNext( trans_item, theChildren[2].getp(), planState ) ) {
+
+ arg_string = arg_item ->getStringValue().str();
+ map_string = map_item ->getStringValue().str();
+ trans_string = trans_item->getStringValue().str();
+
+ typedef std::map<unicode::code_point,unicode::code_point> cp_map_type;
+ cp_map_type trans_map;
+
+ if ( !map_string.empty() ) {
+ utf8_string<zstring const> const u_map_string ( map_string );
+ utf8_string<zstring const> const u_trans_string( trans_string );
+
+ utf8_string<zstring const>::const_iterator
+ map_i = u_map_string .begin(),
+ map_end = u_map_string .end (),
+ trans_i = u_trans_string.begin(),
+ trans_end = u_trans_string.end ();
+
+ for ( ; map_i != map_end && trans_i != trans_end; ++map_i, ++trans_i )
+ trans_map[ *map_i ] = *trans_i;
+
+ for ( ; map_i != map_end; ++map_i )
+ trans_map[ *map_i ] = ~0;
+ }
+
+ utf8_string<zstring> u_result_string( result_string );
+ utf8_string<zstring const> const u_arg_string( arg_string );
+
+ utf8_string<zstring const>::const_iterator
+ arg_i = u_arg_string.begin(),
+ arg_end = u_arg_string.end ();
+
+ for ( ; arg_i != arg_end; ++arg_i ) {
+ unicode::code_point cp = *arg_i;
+ cp_map_type::const_iterator const found_i = trans_map.find( cp );
+ if ( found_i != trans_map.end() ) {
+ cp = found_i->second;
+ if ( cp == ~0 )
+ continue;
+ }
+ u_result_string += cp;
+ }
+
+ res = GENV_ITEMFACTORY->createString(result, result_string);
+ }
+
+ if (!res)
+ {
+ res = GENV_ITEMFACTORY->createString(result, result_string);
+ }
+
+ STACK_PUSH( res, state );
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.10 fn:encode-for-uri
+ *
+ *fn:encode-for-uri($uri-part as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool EncodeForUriIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring resStr;
+ zstring strval;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(strval);
+ uri::encode(strval, &resStr, true);
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.11 fn:iri-to-uri
+ *
+ *fn:iri-to-uri($iri as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool IriToUriIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring lStrIri;
+ zstring lStrRes;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(lStrIri);
+
+ utf8::iri_to_uri(lStrIri, &lStrRes);
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.4.12 fn:escape-html-uri
+ *
+ *fn:escape-html-uri($uri as xs:string?) as xs:string
+ *_______________________________________________________________________*/
+bool EscapeHtmlUriIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring lStrUri;
+ zstring lStrRes;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren [0].getp(), planState))
+ {
+ item->getStringValue2(lStrUri);
+
+ utf8::to_html_uri(lStrUri, &lStrRes);
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
+ }
+ else
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, lStrRes), state);
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.5.1 fn:contains
+ *
+ *fn:contains( $arg1 as xs:string?,
+ * $arg2 as xs:string?) as xs:boolean
+ *fn:contains( $arg1 as xs:string?,
+ * $arg2 as xs:string?,
+ * $collation as xs:string) as xs:boolean
+ *_______________________________________________________________________*/
+bool ContainsIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ store::Item_t itemColl;
+ bool resBool = false;
+ zstring arg1;
+ zstring arg2;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item0, theChildren[0].getp(), planState ))
+ {
+ item0->getStringValue2(arg1);
+ }
+
+ if (consumeNext(item1, theChildren[1].getp(), planState ))
+ {
+ item1->getStringValue2(arg2);
+ }
+
+ if (arg2.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
+ }
+ else if (arg1.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
+ }
+ else
+ {
+ if (theChildren.size() == 2)
+ {
+ resBool = (arg1.find(arg2) != zstring::npos);
+ }
+ else
+ {
+ if (consumeNext(itemColl, theChildren[2].getp(), planState ))
+ {
+ XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
+ resBool = (utf8::find(arg1, arg2, coll) != zstring::npos);
+ }
+ }
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
+ }
+
+ STACK_END (state);
+}
+/*end class ContainsIterator*/
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.5.2 fn:starts-with
+ *
+ *fn:starts-with($arg1 as xs:string?,
+ * $arg2 as xs:string?) as xs:boolean
+ *fn:starts-with($arg1 as xs:string?,
+ * $arg2 as xs:string?,
+ * $collation as xs:string) as xs:boolean
+ *_______________________________________________________________________*/
+bool StartsWithIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ store::Item_t itemColl;
+ bool resBool = false;
+ zstring arg1;
+ zstring arg2;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (theChildren.size() == 2 || theChildren.size()==3)
+ {
+ if (consumeNext(item0, theChildren[0].getp(), planState ))
+ {
+ item0->getStringValue2(arg1);
+ }
+
+ if (consumeNext(item1, theChildren[1].getp(), planState ))
+ {
+ item1->getStringValue2(arg2);
+ }
+
+ if (arg2.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
+ }
+ else if (arg1.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
+ }
+ else
+ {
+ if (theChildren.size() == 2)
+ {
+ resBool = (arg1.find(arg2) == 0);
+ }
+ else
+ {
+ if (consumeNext(itemColl, theChildren[2].getp(), planState ))
+ {
+ XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
+ resBool = (utf8::find(arg1, arg2, coll) == 0);
+ }
+ }
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
+ }
+ }
+ STACK_END (state);
+}
+/*end class StartsWithIterator*/
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.5.3 fn:ends-with
+ *
+ *fn:ends-with($arg1 as xs:string?,
+ * $arg2 as xs:string?) as xs:boolean
+ *fn:ends-with($arg1 as xs:string?,
+ * $arg2 as xs:string?,
+ * $collation as xs:string) as xs:boolean
+ *_______________________________________________________________________*/
+bool EndsWithIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ store::Item_t itemColl;
+ bool resBool = false;
+ zstring arg1;
+ zstring arg2;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item0, theChildren[0].getp(), planState ))
+ {
+ item0->getStringValue2(arg1);
+ }
+
+ if (consumeNext(item1, theChildren[1].getp(), planState ))
+ {
+ item1->getStringValue2(arg2);
+ }
+
+ if (arg2.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, true), state );
+ }
+ else if (arg1.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, false), state );
+ }
+ else
+ {
+ if (theChildren.size() == 2)
+ {
+ resBool = utf8::ends_with(arg1, arg2);
+ }
+ else
+ {
+ if (consumeNext(itemColl, theChildren[2].getp(), planState ))
+ {
+ XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
+
+ resBool = utf8::ends_with(arg1, arg2, coll);
+ }
+ }
+ STACK_PUSH( GENV_ITEMFACTORY->createBoolean(result, resBool), state );
+ }
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.5.4 fn:substring-before
+ *
+ *fn:substring-before( $arg1 as xs:string?,
+ * $arg2 as xs:string?) as xs:string
+ *fn:substring-before( $arg1 as xs:string?,
+ * $arg2 as xs:string?,
+ * $collation as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool SubstringBeforeIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ store::Item_t itemColl;
+ zstring::size_type index = zstring::npos;
+ zstring arg1;
+ zstring arg2;
+ zstring resStr;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if(theChildren.size() == 2 || theChildren.size()==3)
+ {
+ if (consumeNext(item0, theChildren[0].getp(), planState ))
+ {
+ item0->getStringValue2(arg1);
+ }
+
+ if (consumeNext(item1, theChildren[1].getp(), planState ))
+ {
+ item1->getStringValue2(arg2);
+ }
+
+ if (arg1.empty() || arg2.empty())
+ {
+ STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
+ }
+ else
+ {
+ if (theChildren.size() == 2)
+ {
+ index = arg1.find(arg2);
+ }
+ else
+ {
+ if (consumeNext(itemColl, theChildren[2].getp(), planState ))
+ {
+ XQPCollator* coll = 0;
+ coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
+ index = utf8::find(arg1, arg2, coll);
+ }
+ }
+
+ if (index != zstring::npos)
+ resStr = arg1.substr(0, index);
+
+ STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
+ }
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.5.5 fn:substring-after
+ *
+ *fn:substring-after($arg1 as xs:string?,
+ * $arg2 as xs:string?) as xs:string
+ *fn:substring-after($arg1 as xs:string?,
+ * $arg2 as xs:string?,
+ * $collation as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool SubstringAfterIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item0;
+ store::Item_t item1;
+ store::Item_t itemColl;
+ zstring::size_type startPos = zstring::npos;
+ zstring arg1;
+ zstring arg2;
+ zstring resStr;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (theChildren.size() == 2 || theChildren.size() == 3)
+ {
+ if (consumeNext(item0, theChildren[0].getp(), planState ))
+ {
+ item0->getStringValue2(arg1);
+ }
+
+ if (consumeNext(item1, theChildren[1].getp(), planState ))
+ {
+ item1->getStringValue2(arg2);
+ }
+
+ if (arg1.empty())
+ {
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ else if (arg2.empty())
+ {
+ resStr = arg1;
+ STACK_PUSH( GENV_ITEMFACTORY->createString(result, resStr), state );
+ }
+ else
+ {
+ if (theChildren.size() == 2)
+ {
+ startPos = arg1.find(arg2);
+ }
+ else
+ {
+ if (consumeNext(itemColl, theChildren[2].getp(), planState))
+ {
+ XQPCollator* coll = theSctx->get_collator(itemColl->getStringValue().str(), loc);
+ startPos = utf8::find(arg1, arg2, coll);
+ }
+ }
+
+ if (startPos != zstring::npos)
+ {
+ startPos += arg2.size();
+ resStr = arg1.substr(startPos, arg1.size() - startPos);
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+ }
+ }
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.6.2 fn:matches
+ *
+ *fn:matches($input as xs:string?,
+ * $pattern as xs:string) as xs:boolean
+ *fn:matches($input as xs:string?,
+ * $pattern as xs:string,
+ * $flags as xs:string) as xs:boolean
+ *_______________________________________________________________________*/
+bool FnMatchesIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ zstring input;
+ zstring xquery_pattern;
+ zstring flags;
+ store::Item_t item;
+ bool res = false;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ item->getStringValue2(input);
+
+ if (!consumeNext(item, theChildren[1].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(xquery_pattern);
+
+ if(theChildren.size() == 3)
+ {
+ if (!consumeNext(item, theChildren[2].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(flags);
+ }
+
+ try
+ {
+ zstring lib_pattern;
+ convert_xquery_re( xquery_pattern, &lib_pattern, flags.c_str() );
+ res = utf8::match_part(input, lib_pattern, flags.c_str());
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createBoolean(result, res), state);
+
+ STACK_END(state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.6.3 fn:replace
+ *
+ *fn:replace($input as xs:string?,
+ * $pattern as xs:string,
+ * $replacement as xs:string) as xs:string
+ *fn:replace($input as xs:string?,
+ * $pattern as xs:string,
+ * $replacement as xs:string,
+ * $flags as xs:string) as xs:string
+ *_______________________________________________________________________*/
+bool FnReplaceIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ zstring input;
+ zstring flags;
+ zstring pattern;
+ zstring replacement, replacement2;
+ zstring resStr;
+ store::Item_t item;
+ bool tmp;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ item->getStringValue2(input);
+
+ if (!consumeNext(item, theChildren[1].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(pattern);
+
+ if (!consumeNext(item, theChildren[2].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(replacement);
+
+ if(theChildren.size() == 4)
+ {
+ if (!consumeNext(item, theChildren[3].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(flags);
+ }
+
+ try
+ {
+ tmp = utf8::match_part(zstring(), pattern, flags.c_str());
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ if (tmp)
+ throw XQUERY_EXCEPTION(
+ err::FORX0003, ERROR_PARAMS( pattern ), ERROR_LOC( loc )
+ );
+
+ { // local scope
+ int num_capturing_groups = 0;
+
+ bool got_paren = false;
+ FOR_EACH( zstring, c, pattern ) {
+ if ( got_paren && *c != '?' )
+ ++num_capturing_groups;
+ got_paren = *c == '(';
+ }
+
+ bool got_backslash = false, got_dollar = false;
+ FOR_EACH( zstring, c, replacement ) {
+ if ( got_backslash ) {
+ switch ( *c ) {
+ case '\\':
+ case '$':
+ replacement2 += '\\';
+ replacement2 += *c;
+ got_backslash = false;
+ continue;
+ default:
+ throw XQUERY_EXCEPTION(
+ err::FORX0004,
+ ERROR_PARAMS( replacement, ZED( BadCharAfter_34 ), *c, '\\' ),
+ ERROR_LOC( loc )
+ );
+ }
+ }
+ if ( got_dollar ) {
+ if ( !ascii::is_digit( *c ) )
+ throw XQUERY_EXCEPTION(
+ err::FORX0004,
+ ERROR_PARAMS( replacement, ZED( BadCharAfter_34 ), *c, '$' ),
+ ERROR_LOC( loc )
+ );
+ if ( *c - '0' <= num_capturing_groups ) {
+ replacement2 += '$';
+ replacement2 += *c;
+ }
+ got_dollar = false;
+ continue;
+ }
+ switch ( *c ) {
+ case '\\':
+ got_backslash = true;
+ break;
+ case '$':
+ got_dollar = true;
+ break;
+ default:
+ replacement2 += *c;
+ break;
+ }
+ } // FOR_EACH
+ if ( got_backslash )
+ throw XQUERY_EXCEPTION(
+ err::FORX0004,
+ ERROR_PARAMS( replacement, ZED( TrailingChar_3 ), '\\' ),
+ ERROR_LOC( loc )
+ );
+ if ( got_dollar )
+ throw XQUERY_EXCEPTION(
+ err::FORX0004,
+ ERROR_PARAMS( replacement, ZED( TrailingChar_3 ), '$' ),
+ ERROR_LOC( loc )
+ );
+ } // local scope
+
+ try
+ {
+ zstring lib_pattern;
+ convert_xquery_re( pattern, &lib_pattern, flags.c_str() );
+ utf8::replace_all(input, lib_pattern, flags.c_str(), replacement2, &resStr);
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, resStr), state);
+
+ STACK_END (state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * 7.6.4 fn:tokenize
+ *
+ *fn:tokenize($input as xs:string?,
+ * $pattern as xs:string) as xs:string*
+ *fn:tokenize($input as xs:string?,
+ * $pattern as xs:string,
+ * $flags as xs:string) as xs:string*
+ *_______________________________________________________________________
+ */
+void FnTokenizeIteratorState::reset(PlanState& planState)
+{
+ PlanIteratorState::reset(planState);
+ theString.clear();
+ start_pos = 0;
+ hasmatched = false;
+ thePattern.clear();
+ theFlags.clear();
+}
+
+
+bool FnTokenizeIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ zstring token;
+ store::Item_t item;
+ bool tmp;
+ zstring strval;
+ unicode::string u_string;
+
+ FnTokenizeIteratorState* state;
+ DEFAULT_STACK_INIT(FnTokenizeIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ {
+ item->getStringValue2(strval);
+ state->theString = strval.str();
+ }
+
+ if (!consumeNext(item, theChildren[1].getp(), planState))
+ ZORBA_ASSERT(false);
+
+ item->getStringValue2(strval);
+ state->thePattern = strval.str();
+
+ if(theChildren.size() == 3)
+ {
+ if (!consumeNext(item, theChildren[2].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(strval);
+
+ state->theFlags = strval.str();
+ }
+
+ try
+ {
+ static zstring const empty;
+ tmp = utf8::match_part( empty, state->thePattern, state->theFlags );
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ if(tmp)
+ throw XQUERY_EXCEPTION(
+ err::FORX0003, ERROR_PARAMS( state->thePattern ), ERROR_LOC( loc )
+ );
+
+
+ while ((xs_unsignedInt)state->start_pos < state->theString.length ())
+ {
+ try
+ {
+ unicode::regex re;
+ //
+ // The RE needs to be compiled every time due to the weird stack macros.
+ //
+ re.compile( state->thePattern, state->theFlags );
+ unicode::string u_token;
+ bool const got_next = re.next_token(
+ state->theString, &state->start_pos, &u_token, &state->hasmatched
+ );
+ utf8::to_string( u_token, &token );
+ if ( !got_next )
+ break;
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, token), state);
+ }
+
+ if(state->hasmatched)
+ {
+ //the last token is empty (is after the last match)
+ token.clear();
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, token), state);
+ }
+ STACK_END(state);
+}
+
+/**
+ *______________________________________________________________________
+ *
+ * 5.6.5 fn:analyze-string
+ *
+ *fn:analyze-string( $input as xs:string?,
+ * $pattern as xs:string) as element(fn:analyze-string-result)
+ *fn:analyze-string( $input as xs:string?,
+ * $pattern as xs:string,
+ * $flags as xs:string) as element(fn:analyze-string-result)
+ *_______________________________________________________________________*/
+
+static void copyUtf8Chars(const char *&sin,
+ int &utf8start,
+ unsigned int &bytestart,
+ int utf8end,
+ zstring &out)
+{
+ utf8::size_type clen;
+ while(utf8start < utf8end)
+ {
+ clen = utf8::char_length(*sin);
+ out.append(sin, clen);
+ utf8start++;
+ bytestart += clen;
+ sin += clen;
+ }
+}
+
+static void addNonMatchElement(store::Item_t &parent,
+ int &match_end1,
+ unsigned int &match_end1_bytes,
+ int match_start2,
+ const char *&strin)
+{
+ store::Item_t non_match_elem;
+ store::Item_t non_match_element_name;
+ store::Item_t untyped_type_name;
+ store::NsBindings ns_binding;
+ zstring baseURI;
+ GENV_ITEMFACTORY->createQName(untyped_type_name,
+ "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
+ GENV_ITEMFACTORY->createQName(non_match_element_name,
+ static_context::W3C_FN_NS, "fn", "non-match");
+ GENV_ITEMFACTORY->createElementNode(non_match_elem, parent, non_match_element_name, untyped_type_name, false, false, ns_binding, baseURI);
+ //utf8_it += (match_start2 - match_end1);
+ zstring non_match_str;
+ //utf8_string<zstring> non_match_utf8(non_match_str);
+ //while(match_end1 < match_start2)
+ //{
+ // non_match_utf8 += *utf8_it;
+ // utf8_it++;
+ // match_end1++;
+ //}
+ copyUtf8Chars(strin, match_end1, match_end1_bytes, match_start2, non_match_str);
+ store::Item_t non_match_text_item;
+ GENV_ITEMFACTORY->createTextNode(non_match_text_item, non_match_elem, non_match_str);
+}
+
+static void addGroupElement(store::Item_t &parent,
+ store::Item_t &untyped_type_name,
+ store::NsBindings &ns_binding,
+ zstring &baseURI,
+ int match_start2,
+ int match_end2,
+ unsigned int &match_end1_bytes,
+ const char *&sin,
+ unicode::regex &rx,
+ int gparent,
+ std::vector<int> &group_parent,
+ int nr_pattern_groups,
+ int &i)
+{
+ int match_startg = match_start2;
+ int match_endg = match_start2;
+ int match_endgood = match_start2;
+ store::Item_t group_element_name;
+ store::Item_t nr_attrib_name;
+ for(i=i+1;i<nr_pattern_groups;i++)
+ {
+ if(group_parent[i] < gparent)
+ {
+ i--;
+ break;
+ }
+ match_startg = rx.get_match_start(i+1);
+ if((match_startg < 0) && (gparent < 0))
+ continue;
+ if(match_endgood < match_startg)
+ {
+ //add non-group match text
+ zstring non_group_str;
+
+ copyUtf8Chars(sin, match_endgood, match_end1_bytes, match_startg, non_group_str);
+ store::Item_t non_group_text_item;
+ GENV_ITEMFACTORY->createTextNode(non_group_text_item, parent.getp(), non_group_str);
+ }
+ match_endg = rx.get_match_end(i+1);
+ //add group match text
+ GENV_ITEMFACTORY->createQName(group_element_name,
+ static_context::W3C_FN_NS, "fn", "group");
+ GENV_ITEMFACTORY->createQName(nr_attrib_name,
+ "", "", "nr");
+ store::Item_t group_elem;
+ GENV_ITEMFACTORY->createElementNode(group_elem, parent, group_element_name, untyped_type_name, false, false, ns_binding, baseURI);
+ char strid[40];
+ sprintf(strid, "%d", i+1);
+ zstring zstrid(strid);
+ store::Item_t strid_item;
+ GENV_ITEMFACTORY->createString(strid_item, zstrid);
+ store::Item_t id_attrib_item;
+ GENV_ITEMFACTORY->createAttributeNode(id_attrib_item, group_elem.getp(), nr_attrib_name, untyped_type_name, strid_item);
+ if((match_startg < 0) || (match_startg < match_endgood))
+ continue;
+ match_endgood = match_endg;
+ if((i+1)<nr_pattern_groups)
+ {
+ if(group_parent[i+1] > gparent)
+ {
+ addGroupElement(group_elem, untyped_type_name, ns_binding, baseURI,
+ match_startg, match_endg, match_end1_bytes,
+ sin, rx,
+ i, group_parent, nr_pattern_groups, i);
+ continue;
+ }
+ }
+ zstring group_str;
+
+ copyUtf8Chars(sin, match_startg, match_end1_bytes, match_endg, group_str);
+ store::Item_t group_text_item;
+ GENV_ITEMFACTORY->createTextNode(group_text_item, group_elem.getp(), group_str);
+ }
+ //add last non-group match
+ if(match_endgood < match_end2)
+ {
+ zstring non_group_str;
+
+ copyUtf8Chars(sin, match_endgood, match_end1_bytes, match_end2, non_group_str);
+ store::Item_t non_group_text_item;
+ GENV_ITEMFACTORY->createTextNode(non_group_text_item, parent, non_group_str);
+ }
+}
+
+static void addMatchElement(store::Item_t &parent,
+ int match_start2,
+ unsigned int &match_end1_bytes,
+ int match_end2,
+ //utf8_string<zstring_p>::const_iterator& utf8_it,
+ const char *&sin,
+ unicode::regex &rx,
+ std::vector<int> &group_parent,
+ int nr_pattern_groups)
+{
+ store::Item_t match_element_name;
+ store::Item_t untyped_type_name;
+ store::NsBindings ns_binding;
+ zstring baseURI;
+ GENV_ITEMFACTORY->createQName(untyped_type_name,
+ "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
+ GENV_ITEMFACTORY->createQName(match_element_name,
+ static_context::W3C_FN_NS, "fn", "match");
+ store::Item_t match_elem;
+ GENV_ITEMFACTORY->createElementNode(match_elem, parent, match_element_name, untyped_type_name, false, false, ns_binding, baseURI);
+ int i = -1;
+ addGroupElement(match_elem, untyped_type_name, ns_binding, baseURI, match_start2, match_end2, match_end1_bytes, sin, rx, -1, group_parent, nr_pattern_groups, i);
+}
+
+static void computePatternGroupsParents(zstring &xquery_pattern, std::vector<int> &group_parent)
+{
+ utf8_string<zstring> utf8_pattern(xquery_pattern);
+ utf8_string<zstring>::const_iterator c;
+ std::list<int> parents;
+ int i = 0;
+
+ for(c = utf8_pattern.begin(); c != utf8_pattern.end(); c++)
+ {
+ if(*c == '\\')
+ {
+ c++;
+ continue;
+ }
+ if(*c == '(')
+ {
+ //begin group
+ if(parents.size())
+ group_parent.push_back(parents.back());
+ else
+ group_parent.push_back(-1);
+ parents.push_back(i);
+ i++;
+ }
+ else if(*c == ')')
+ {
+ if(parents.size())
+ parents.pop_back();
+ }
+ }
+}
+
+bool FnAnalyzeStringIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ bool is_input_stream = false;
+ zstring input;
+ std::istream *instream = NULL;
+#define STREAMBUF_CHUNK_SIZE 4*1024
+ class SmartCharPtr
+ {
+ public:
+ char *ptr;
+ SmartCharPtr() : ptr(NULL) {}
+ ~SmartCharPtr() {if(ptr) ::free(ptr);}
+ };
+ SmartCharPtr streambuf;
+ zstring::size_type streambuf_allocated_size = 0;
+ zstring::size_type streambuf_read = 0;
+ //zstring::size_type streambuf_beg = 0;
+ zstring xquery_pattern;
+ zstring flags;
+ store::Item_t item;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+ if (consumeNext(item, theChildren[0].getp(), planState))
+ {
+ if(!item->isStreamable())
+ {
+ item->getStringValue2(input);
+ }
+ else
+ {
+ instream = &item->getStream();
+ is_input_stream = true;
+ }
+ }
+
+ if (!consumeNext(item, theChildren[1].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(xquery_pattern);
+
+ if(theChildren.size() == 3)
+ {
+ if (!consumeNext(item, theChildren[2].getp(), planState))
+ ZORBA_ASSERT (false);
+
+ item->getStringValue2(flags);
+ }
+
+ try
+ {
+ zstring lib_pattern;
+ convert_xquery_re( xquery_pattern, &lib_pattern, flags.c_str() );
+
+ if(is_input_stream)
+ {
+ streambuf.ptr = (char*)malloc(STREAMBUF_CHUNK_SIZE);
+ streambuf_allocated_size = STREAMBUF_CHUNK_SIZE;
+ instream->read(streambuf.ptr, streambuf_allocated_size);
+ streambuf_read = (unsigned int)instream->gcount();
+ if(streambuf_read == STREAMBUF_CHUNK_SIZE)
+ {
+ // Note: const_reverse_iterator would work here, but does not
+ // compile with gcc 4.0.1 (which is the version in Xcode on MacOS 10.5).
+ zstring::reverse_iterator xqit = xquery_pattern.rbegin();
+ if((xqit != xquery_pattern.rend()) && (flags.find('m') == std::string::npos))
+ {
+ if(*xqit == '$')
+ {
+ xqit++;
+ int bslashes = 0;
+ while(xqit != xquery_pattern.rend())
+ {
+ if(*xqit == '\\')
+ bslashes++;
+ else
+ break;
+ }
+ if(bslashes%2 == 0)
+ {
+ //better read all instream
+ do{
+ streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
+ streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
+ instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
+ streambuf_read += (unsigned int)instream->gcount();
+ }while(instream->gcount() == STREAMBUF_CHUNK_SIZE);
+ }
+ }
+ }
+ }
+ }
+
+ unicode::regex rx;
+ rx.compile(lib_pattern, flags.c_str());
+ int nr_pattern_groups = rx.get_pattern_group_count();
+ std::vector<int> group_parent;
+ computePatternGroupsParents(xquery_pattern, group_parent);
+
+ //see if regex can match empty strings
+ bool reachedEnd = false;
+ rx.set_string("", 0);
+ if(rx.find_next_match(&reachedEnd))
+ {
+ throw XQUERY_EXCEPTION(
+ err::FORX0003, ERROR_PARAMS( lib_pattern )
+ );
+
+ }
+
+ store::Item_t null_parent;
+ store::Item_t result_element_name;
+ store::Item_t untyped_type_name;
+ store::NsBindings ns_binding;
+ zstring baseURI;
+ GENV_ITEMFACTORY->createQName(untyped_type_name,
+ "http://www.w3.org/2001/XMLSchema", "xs", "untyped");
+ GENV_ITEMFACTORY->createQName(result_element_name,
+ static_context::W3C_FN_NS, "fn", "analyze-string-result");
+ GENV_ITEMFACTORY->createElementNode(result, NULL, result_element_name, untyped_type_name, false, false, ns_binding, baseURI);
+
+ int nr_retry = 0;
+ reachedEnd = false;
+ do
+ {
+ const char *instr;
+ if(!is_input_stream)
+ {
+ rx.set_string(input.data(), input.size());
+ instr = input.c_str();
+ streambuf_read = input.size();
+ }
+ else
+ {
+ unsigned int reducebytes = 0;
+ if(!instream->eof())
+ {
+ //check the last bytes, maybe it is a truncated utf8 char
+ unsigned int maxbytes = 6;
+ if(maxbytes > streambuf_read)
+ maxbytes = streambuf_read;
+ for(reducebytes=1;reducebytes<=maxbytes;reducebytes++)
+ {
+ utf8::size_type clen = utf8::char_length(streambuf.ptr[streambuf_read-reducebytes]);
+ if((clen > 1) && (clen > reducebytes))
+ break;
+ }
+ if(reducebytes == (maxbytes+1))
+ reducebytes = 0;
+ }
+ rx.set_string(streambuf.ptr, streambuf_read-reducebytes);
+ instr = streambuf.ptr;
+ }
+ //zstring_p zinstr(instr);
+ //utf8_string<zstring_p> utf8_instr(zinstr);
+ //utf8_string<zstring_p>::const_iterator utf8_it = utf8_instr.begin();
+
+ //int match_start1 = 0;
+ int match_end1 = 0;
+ unsigned int match_end1_bytes = 0;
+ reachedEnd = false;
+ while(rx.find_next_match(&reachedEnd))
+ {
+ int match_start2 = rx.get_match_start();
+ int match_end2 = rx.get_match_end();
+ ZORBA_ASSERT(match_start2 >= 0);
+
+ if(is_input_stream && reachedEnd && !instream->eof())
+ {
+ //load some more data, maybe the match will be different
+ break;
+ }
+
+ //construct the fn:non-match
+ if(match_start2 > match_end1)
+ {
+ addNonMatchElement(result, match_end1, match_end1_bytes, match_start2, instr);
+ }
+
+ //construct the fn:match
+ addMatchElement(result, match_start2, match_end1_bytes, match_end2, instr, rx, group_parent, nr_pattern_groups);
+ match_end1 = match_end2;
+ }
+
+ if(is_input_stream && reachedEnd && !instream->eof())
+ {
+ //load some more data, maybe the match will be different
+ if(match_end1_bytes)
+ {
+ memmove(streambuf.ptr, streambuf.ptr+match_end1_bytes, streambuf_read-match_end1_bytes);
+ streambuf_read -= match_end1_bytes;
+ nr_retry = 0;
+ }
+ else
+ nr_retry++;
+ if(!match_end1_bytes && (nr_retry == 2))
+ {
+ if(streambuf_allocated_size > streambuf_read)
+ {
+ instream->read(streambuf.ptr + streambuf_read, streambuf_allocated_size - streambuf_read);
+ streambuf_read += (unsigned int)instream->gcount();
+ }
+ //better read all instream
+ while(!instream->eof())
+ {
+ streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
+ instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
+ streambuf_read += (unsigned int)instream->gcount();
+ streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
+ }
+ }
+ else
+ {
+ //read some more data from instream
+ if(streambuf_allocated_size > streambuf_read)
+ {
+ instream->read(streambuf.ptr + streambuf_read, streambuf_allocated_size - streambuf_read);
+ streambuf_read += (unsigned int)instream->gcount();
+ }
+ else
+ {
+ streambuf.ptr = (char*)realloc(streambuf.ptr, streambuf_allocated_size+STREAMBUF_CHUNK_SIZE);
+ instream->read(streambuf.ptr + streambuf_read, STREAMBUF_CHUNK_SIZE);
+ streambuf_read += (unsigned int)instream->gcount();
+ streambuf_allocated_size += STREAMBUF_CHUNK_SIZE;
+ }
+ }
+ reachedEnd = false;
+ }
+ else
+ {
+ if(match_end1_bytes < streambuf_read)
+ addNonMatchElement(result, match_end1, match_end1_bytes, streambuf_read, instr);
+ if(is_input_stream && instream->eof())
+ reachedEnd = true;
+ }
+
+ }while(is_input_stream && !reachedEnd);
+ }
+ catch(XQueryException& ex)
+ {
+ set_source( ex, loc );
+ throw;
+ }
+
+ STACK_PUSH(true, state);
+
+ STACK_END(state);
+}
+
+
+/**
+ *______________________________________________________________________
+ *
+ * http://www.zorba-xquery.com/modules/string
+ * string:materialize
+ */
+
+bool StringMaterializeIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+ zstring lString;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+#ifndef NDEBUG
+ assert(consumeNext(item, theChildren[0].getp(), planState));
+#else
+ consumeNext(item, theChildren[0].getp(), planState);
+#endif
+ if (item->isStreamable()) {
+ lString = item->getString();
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, lString), state);
+ } else {
+ result = item;
+ STACK_PUSH(result != 0 , state);
+ }
+
+ STACK_END(state);
+}
+
+/**
+ *______________________________________________________________________
+ *
+ * http://www.zorba-xquery.com/modules/string
+ * string:materialize
+ */
+bool StringIsStreamableIterator::nextImpl(
+ store::Item_t& result,
+ PlanState& planState) const
+{
+ store::Item_t item;
+
+ PlanIteratorState* state;
+ DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
+
+#ifndef NDEBUG
+ assert(consumeNext(item, theChildren[0].getp(), planState));
+#else
+ consumeNext(item, theChildren[0].getp(), planState);
+#endif
+ STACK_PUSH(GENV_ITEMFACTORY->createBoolean(result, item->isStreamable()), state);
+
+ STACK_END(state);
+}
+
+} // namespace zorba
+/* vim:set et sw=2 ts=2: */
=== modified file 'src/util/utf8_util_base.h'
--- src/util/utf8_util_base.h 2011-07-17 20:05:49 +0000
+++ src/util/utf8_util_base.h 2011-09-22 11:09:58 +0000
@@ -148,7 +148,6 @@
* @return Returns the Unicode code-point of the next character.
*/
template<class OctetIterator>
-ZORBA_DLL_PUBLIC
unicode::code_point next_char( OctetIterator &i );
/**
=== modified file 'src/zorbatypes/URI.cpp'
--- src/zorbatypes/URI.cpp 2011-06-24 23:00:33 +0000
+++ src/zorbatypes/URI.cpp 2011-09-22 11:09:58 +0000
@@ -1,1711 +1,1722 @@
-/*
- * Copyright 2006-2008 The FLWOR Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "stdafx.h"
-
-#include "schema_types.h"
-
-#include "diagnostics/xquery_diagnostics.h"
-#include "diagnostics/dict.h"
-#include "diagnostics/assert.h"
-
-#include <zorba/util/path.h>
-
-#include "URI.h"
-
-#include "util/ascii_util.h"
-#include "util/string_util.h"
-#include "util/uri_util.h"
-#include "util/utf8_util.h"
-#include "zorbautils/string_util.h"
-
-
-using namespace std;
-
-namespace zorba {
-
- /*
- ---------------------------------------------------------------------------
- URI-reference = [ absoluteURI | relativeURI ] [ "#" fragment ]
- absoluteURI = scheme ":" ( hier_part | opaque_part )
- relativeURI = ( net_path | abs_path | rel_path ) [ "?" query ]
- ---------------------------------------------------------------------------
- query = *uric
-
- fragment = *uric
----------------------------------------------------------------------------
- */
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_unreserved_char(uint32_t c)
-{
- static std::string lMarkCharacter("-_.!~*'{}");
- return (ascii::is_alnum(c) || (c == ' ') || (c > 127 ) ||
- ((c<128) && lMarkCharacter.find((char)c) != std::string::npos));
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_path_character(uint32_t c)
-{
- static std::string lPathChracters(";/\\:@&=+$,");
- return ((c<128) && lPathChracters.find((char)c) != std::string::npos);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_reservered_or_unreserved_char(uint32_t c)
-{
- static std::string lMarkOrReservedChars("-_.!~*'();/?:@&=+$,[]");
- return (ascii::is_alnum(c) ||
- (c == ' ') ||
- ((c<128) && lMarkOrReservedChars.find((char)c) != std::string::npos));
-}
-
-
-/*******************************************************************************
- Note: The encode_file_URI and decode_file_URI methods are hacks. Doing it
- properly would require boost-filesystem (or equivalent code).
-
- The decode_file_URI() method takes a file URI and converts it to a filepath
- in the native OS foramt.
-********************************************************************************/
-void URI::decode_file_URI(const zstring& uri, zstring& filepath)
-{
- // TODO: file://localhost/
-#ifdef WIN32
- if (uri.compare(0, 8, "file:///") == 0 &&
- ((uri.compare(9, 1, ":") == 0) || (uri.compare(9, 4, "%3A/") == 0)))
- {
- zstring tmp(uri.c_str() + 8);
- uri::decode(tmp, &filepath);
- }
- else
-#endif
- if (uri.compare(0, 8, "file:///") == 0)
- {
- zstring tmp(uri.c_str() + 7);
- uri::decode(tmp, &filepath);
- }
- else if (uri.compare(0, 17, "file://localhost/") == 0)
- {
- zstring tmp(uri.c_str() + 16);
- uri::decode(tmp, &filepath);
- }
- else
- {
- // should we raise an unknown host exception?
- filepath = uri;
- }
-
-#ifdef WIN32
- ascii::replace_all(filepath, '/', '\\');
-#endif
-}
-
-
-/*******************************************************************************
- The encode_file_URI() method takes a filepath and converts it to a file URI.
-
- Assumes input is absolute path.
-********************************************************************************/
-void URI::encode_file_URI(const zstring& filepath, zstring& uri)
-{
- if (filepath.find("://", 0, 3) != zstring::npos)
- {
- uri = filepath;
- return;
- }
-
-#ifdef WIN32
- uri = "file:///";
-
- zstring tmp1( filepath );
- ascii::replace_all( tmp1, '\\', '/' );
-
- zstring tmp2;
- uri::encode(tmp1, &tmp2, false);
-
- uri.append(tmp2);
-
-#else
- if (filepath[0] == '/')
- uri = "file://";
- else
- uri = "file:///";
-
- zstring tmp;
- uri::encode(filepath, &tmp, false);
-
- uri.append(tmp);
-#endif
-}
-
-
-/*******************************************************************************
- The encode_file_URI() method takes a filepath and converts it to a file URI.
-
- Assumes input is absolute path.
-********************************************************************************/
-std::string URI::encode_file_URI(const std::string& filepath)
-{
- zstring uri;
- encode_file_URI(filepath, uri);
- return uri.str();
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_well_formed_address(const char* addr, ulong addrLen)
-{
- if (addrLen == 0)
- {
- return false;
- }
-
- char c = addr[0];
-
- if (c == '[')
- {
- return is_well_formed_ipv6_reference(addr, addrLen);
- }
-
- if ( c == '.' || c == '-' || addr[addrLen-1] == '-')
- {
- return false;
- }
-
- zstring_b wrap;
- wrap.wrap_memory(addr, addrLen);
-
- zstring::size_type lLastPeriodPos = wrap.rfind(".");
-
- if ( lLastPeriodPos != zstring::npos && lLastPeriodPos + 1 == addrLen )
- {
- zstring_b wrap2;
- wrap2.wrap_memory(addr, lLastPeriodPos);
- lLastPeriodPos = wrap2.rfind(".");
-
- if ( lLastPeriodPos != zstring::npos && ascii::is_digit(addr[lLastPeriodPos + 1]) )
- {
- return false;
- }
- }
-
- if ( lLastPeriodPos != zstring::npos && ascii::is_digit(addr[lLastPeriodPos + 1]) )
- {
- return is_well_formed_ipv4_address(addr, addrLen);
- }
- else
- {
- if (addrLen > 255)
- {
- return false;
- }
-
- ulong lLabelCharCount = 0;
-
- for (ulong i = 0; i < addrLen; ++i)
- {
- char c1 = addr[i];
-
- if ( c1 == '.' )
- {
- if ( ( i > 0 && ! ascii::is_alnum(addr[i-1])) ||
- ( i + 1 < addrLen && ! ascii::is_alnum(addr[i+1])) )
- {
- return false;
- }
-
- lLabelCharCount = 0;
- }
- else if ( ! ascii::is_alnum(c1) && c1 != '-' )
- {
- return false;
- }
- else if ( ++lLabelCharCount > 63 )
- {
- return false;
- }
- }
- }
-
- return true;
-}
-
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_well_formed_ipv4_address(const char* addr, ulong length)
-{
- ulong numDots = 0;
- ulong numDigits = 0;
-
- for (ulong i = 0; i < length; ++i)
- {
- char c = addr[i];
-
- if (c == '.')
- {
- if ( (i == 0) || (i+1 == length) || ! ascii::is_digit(addr[i+1]) )
- return false;
- }
- else if ( ! ascii::is_digit(c) )
- {
- return false;
- }
- else if (++numDigits > 3)
- {
- return false;
- }
- else if (numDigits == 3)
- {
- char lFirst = addr[i-2];
- char lSecond = addr[i-1];
- char lLast = addr[i];
-
- if ( !(lFirst < '2' ||
- (lFirst == '2' && (lSecond < '5' || (lSecond == '5' && lLast <= '5')))))
- return false;
- }
- }
-
- return (numDots == 3);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_well_formed_ipv6_reference(const char* addr, ulong length)
-{
- long lIndex = 1;
- long lEnd = length-1;
-
- // Check if string is a potential match for IPv6reference.
- if (!(length > 2 && addr[0] == '[' && addr[lEnd] == ']'))
- {
- return false;
- }
-
- // Counter for the number of 16-bit sections read in the address.
- long lCounter = 0;
-
- lIndex = scanHexSequence(addr, lIndex, lEnd, lCounter);
- if ( lIndex == -1)
- {
- return false;
- }
-
- // Address must contain 128-bits of information.
- else if (lIndex == lEnd)
- {
- return (lCounter == 8);
- }
-
- if (lIndex+1 < lEnd && addr[lIndex] == ':')
- {
- if (addr[lIndex+1] == ':')
- {
- // '::' represents at least one 16-bit group of zeros.
- if (++lCounter > 8)
- {
- return false;
- }
-
- lIndex += 2;
-
- // Trailing zeros will fill out the rest of the address.
- if (lIndex == lEnd)
- {
- return true;
- }
- }
-
- // If the second character wasn't ':', in order to be valid,
- // the remainder of the string must match IPv4Address,
- // and we must have read exactly 6 16-bit groups.
- else
- {
- if (lCounter == 6)
- {
- return is_well_formed_ipv4_address(addr + lIndex+1, lEnd - lIndex - 1);
- }
- else
- {
- return false;
- }
- }
- }
- else
- {
- return false;
- }
-
- // 3. Scan hex sequence after '::'.
- int prevCount = lCounter;
-
- lIndex = scanHexSequence(addr, lIndex, lEnd, lCounter);
- if (lIndex == -1)
- {
- return false;
- }
-
- // If this is the end of the address then
- // we've got 128-bits of information.
- else if (lIndex == lEnd)
- {
- return true;
- }
-
- // The address ends in an IPv4 address, or it is invalid.
- // scanHexSequence has already made sure that we have the right number of bits.
- int shiftCount = (lCounter > prevCount) ? lIndex+1 : lIndex;
-
- return is_well_formed_ipv4_address(addr + shiftCount, lEnd - shiftCount);
-}
-
-
-/*******************************************************************************
- For use with isWellFormedIPv6Reference only.
-********************************************************************************/
-long URI::scanHexSequence(
- const char* addr,
- long index,
- long end,
- long& counter)
-{
- char c;
- long lNumDigits = 0;
- long lStart = index;
-
- // Trying to match the following productions:
- // hexseq = hex4 *( ":" hex4)
- // hex4 = 1*4HEXDIG
- for (; index < end; ++index)
- {
- c = addr[index];
-
- if ( c == ':' )
- {
- // IPv6 addresses are 128-bit, so there can be at most eight sections.
- if (lNumDigits > 0 && ++counter > 8)
- {
- return -1;
- }
-
- // This could be '::'.
- if (lNumDigits == 0 || ((index+1 < end) && addr[index+1] == ':'))
- {
- return index;
- }
-
- lNumDigits = 0;
- }
-
- // This might be invalid or an IPv4address. If it's potentially an IPv4address,
- // backup to just after the last valid character that matches hexseq.
- else if (!ascii::is_xdigit(c))
- {
- if (c == '.' &&
- lNumDigits < 4 &&
- lNumDigits > 0 &&
- counter <= 6)
- {
- long lBack = index - lNumDigits - 1;
- return (lBack >= lStart) ? lBack : lStart;
- }
-
- return -1;
- }
-
- // There can be at most 4 hex digits per group.
- else if (++lNumDigits > 4)
- {
- return -1;
- }
- }
-
- return (lNumDigits > 0 && ++counter <= 8) ? end : -1;
-}
-
-
-/*******************************************************************************
- construct a uri
-********************************************************************************/
-URI::URI(const zstring& uri, bool validate)
- :
- theState(0),
- thePort(0),
- valid(validate)
-{
- initialize(uri);
-
- //std::cout << "empty rep 2 = " << std::hex << theScheme.empty_rep() << std::endl;
-}
-
-
-/*******************************************************************************
- construct a uri and eventually resolve with the given base uri
-********************************************************************************/
-URI::URI(const URI& base_uri, const zstring& uri, bool validate)
- :
- theState(0),
- thePort(0),
- valid(validate)
-{
- initialize(uri, true);
- resolve(&base_uri);
-}
-
-
-/*******************************************************************************
- constructs a new uri by relativizing the full_uri against the base_uri
-********************************************************************************/
-URI::URI(const URI& full_uri, const URI& base_uri)
- :
- theState(0),
- thePort(0),
- valid(false)
-{
- initialize(full_uri.toString(), false);
- relativize(&base_uri);
-}
-
-
-/*******************************************************************************
- copy constructor
-********************************************************************************/
-URI::URI(const URI& to_copy)
-{
- initialize(to_copy);
-}
-
-
-/*******************************************************************************
- default (empty) constructor)
-********************************************************************************/
-URI::URI()
- :
- theState(0),
- thePort(0),
- valid(true)
-{
-}
-
-
-/*******************************************************************************
- destructor
-********************************************************************************/
-URI::~URI()
-{
-}
-
-
-/*******************************************************************************
- copy a uri
-********************************************************************************/
-void URI::initialize(const URI& to_copy)
-{
- theState = to_copy.theState;
- theScheme = to_copy.theScheme;
- theUserInfo = to_copy.theUserInfo;
- theHost = to_copy.theHost;
- thePort = to_copy.thePort;
- theRegBasedAuthority = to_copy.theRegBasedAuthority;
- thePath = to_copy.thePath;
- theQueryString = to_copy.theQueryString;
- theFragment = to_copy.theFragment;
- valid = to_copy.valid;
-}
-
-
-/*******************************************************************************
- Initialize this uri based on a base-uri (i.e. uri resolving) and a (relative)
- uri given as string
-********************************************************************************/
-void URI::initialize(const zstring& uri, bool have_base)
-{
- invalidate_text();
- thePathNotation.clear();
- theScheme.clear();
- theHost.clear();
- theUserInfo.clear();
- theRegBasedAuthority.clear();
- thePath.clear();
- theQueryString.clear();
- theFragment.clear();
-
- // first, we need to normalize the spaces in the uri
- // and only work with the normalized version from this point on
- zstring lTrimmedURI;
- ascii::normalize_whitespace(uri, &lTrimmedURI);
- ascii::trim_whitespace(lTrimmedURI);
-
- zstring::size_type lTrimmedURILength = lTrimmedURI.size();
-
- // index of the current processing state used in this function
- ulong lIndex = 0;
-
- zstring::size_type lColonIdx = lTrimmedURI.find(":");
- zstring::size_type lSlashIdx = lTrimmedURI.find("/");
- zstring::size_type lQueryIdx = lTrimmedURI.find("?");
- zstring::size_type lFragmentIdx = lTrimmedURI.find("#");
-
-#ifdef WIN32
- // on WIN32 we might have a drive specification ("C:")
- // and we don't want to consider this as scheme
- char lLetter = lTrimmedURI[0];
- bool lIsDrive = false;
- if (lColonIdx == 1 &&
- ((lLetter >= 65 && 90 >= lLetter) || (lLetter >= 97 && 122 >= lLetter)))
- {
- lIsDrive = true;
- }
-#endif
-
- /**
- * Scheme
- * must be before `/', '?' or '#'.
- */
- if ((lColonIdx == 0 || lColonIdx == zstring::npos) ||
-#ifdef WIN32
- // avoid interpreting the drive as a scheme
- lIsDrive ||
-#endif
- (lColonIdx > lSlashIdx && lSlashIdx != zstring::npos) ||
- (lColonIdx > lQueryIdx && lQueryIdx != zstring::npos) ||
- (lColonIdx > lFragmentIdx && lFragmentIdx != zstring::npos))
- {
- // A standalone base is a valid URI
- if (valid &&
- (lColonIdx == 0 || (!have_base && lFragmentIdx != zstring::npos)) &&
- lTrimmedURILength > 0)
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( lTrimmedURI, ZED( NoURIScheme ) )
- );
- }
- }
- else
- {
- initializeScheme(lTrimmedURI);
-
- lIndex = (ulong)theScheme.size() + 1;
- }
-
- /**
- * Authority
- * two slashes means generic URI syntax, so we get the authority
- */
- if (lTrimmedURI.compare(lIndex, 2, "//") == 0)
- {
- lIndex += 2;
- if (lIndex >= lTrimmedURILength)
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( lTrimmedURI, ZED( NoURIAuthority ) )
- );
- }
- else
- {
- ulong lStartPos = lIndex;
-
- // get authority
- // (everything up to path, query, fragment or the end of the URI)
- // RFC3986, 3.2, par. 2
- char c;
- while (lIndex < lTrimmedURILength)
- {
- c = lTrimmedURI[lIndex];
-
- if (c == '/' || c == '?' || c == '#')
- break;
-
- ++lIndex;
- }
-
- // if we found authority, parse it out, otherwise we set the
- // host to empty string
- if (lIndex > lStartPos)
- {
- zstring lAuthUri = lTrimmedURI.substr(lStartPos, lIndex - lStartPos);
-
- // For "file" scheme only allow "localhost" as authority.
- // This makes this implementation the same with the file module.
- // If this functionality is changed, please make the same changes
- // in the file module.
- if (ZSTREQ(theScheme, "file") &&
- !ZSTREQ(lAuthUri, "localhost"))
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046,
- ERROR_PARAMS( lTrimmedURI, ZED( BadFileURIAuthority_2 ), lAuthUri )
- );
- }
-
- initializeAuthority(lAuthUri);
- }
- else
- {
- set_host(zstring());
- }
- }
- // do not allow constructs like: file:D:/myFile or http:myFile
- }
- else if (ZSTREQ(theScheme, "file") ||
- ZSTREQ(theScheme, "http") ||
- ZSTREQ(theScheme, "https"))
- {
- if (valid)
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046,
- ERROR_PARAMS( lTrimmedURI, ZED( BadURISyntaxForScheme_3 ), theScheme )
- );
- }
- }
-
- // stop, if we're done here
- if (lIndex > lTrimmedURILength)
- return;
-
- /**
- * Path
- */
- zstring lPathUri = lTrimmedURI.substr(lIndex, lTrimmedURILength - lIndex);
-
- initializePath(lPathUri);
-}
-
-
-/*******************************************************************************
- scheme = alpha *( alpha | digit | "+" | "-" | "." )
-********************************************************************************/
-void URI::initializeScheme(const zstring& uri)
-{
- zstring::size_type lSchemeSeparatorIdx = uri.find_first_of(":/?#", 0,4 );
-
- if ( valid && lSchemeSeparatorIdx == zstring::npos )
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( NoURIScheme ) )
- );
- }
- else
- {
- set_scheme(uri.substr(0, lSchemeSeparatorIdx));
- }
-}
-
-
-/*******************************************************************************
- authority = server | reg_name
-
- reg_name = 1*( unreserved | escaped | "$" | "," |
- ";" | ":" | "@" | "&" | "=" | "+" )
-
- server = [ [ userinfo "@" ] hostport ]
- userinfo = *( unreserved | escaped |
- ";" | ":" | "&" | "=" | "+" | "$" | "," )
-
- hostport = host [ ":" port ]
- host = hostname | IPv4address
- hostname = *( domainlabel "." ) toplabel [ "." ]
- domainlabel = alphanum | alphanum *( alphanum | "-" ) alphanum
- toplabel = alpha | alpha *( alphanum | "-" ) alphanum
- IPv4address = 1*digit "." 1*digit "." 1*digit "." 1*digit
- port = *digit
-********************************************************************************/
-void URI::initializeAuthority(const zstring& uri)
-{
- zstring::size_type lIndex = 0;
- zstring::size_type lStart = 0;
- zstring::size_type lEnd = uri.size();
-
- zstring lUserInfo;
- bool lUserInfoFound;
-
-
- lIndex = uri.find("@");
-
- if ( lIndex != zstring::npos )
- {
- lUserInfo = uri.substr(0, lIndex);
- ++lIndex;
- lStart += lIndex;
- lUserInfoFound = true;
- }
- else
- {
- lUserInfoFound = false;
- }
-
- //
- // hostport = host [ ":" port ]
- // host is everything up to ':', or up to
- // and including ']' if followed by ':'.
- //
- zstring lHost;
- zstring_b lTmp; // used for substrings starting at lStart
-
- lTmp.wrap_memory(uri.c_str() + lStart, lEnd - lStart);
-
- if ( lStart < lEnd && uri[lStart] == '[' )
- {
- lIndex = lTmp.find("]");
-
- if ( lIndex != zstring::npos )
- {
- lIndex = ((lStart + lIndex + 1) < lEnd && uri[lStart + lIndex + 1] == ':' ?
- lIndex + 1 : zstring::npos);
- }
- }
- else
- {
- lIndex = lTmp.find(":");
- }
-
- if ( lIndex != zstring::npos )
- {
- lHost = lTmp.substr(0, lIndex);
-
- ++lIndex; // skip the colon
- lStart += lIndex;
- }
- else
- {
- lHost = lTmp.substr(0, lEnd - lStart);
- lStart = lEnd;
- }
-
- lTmp.wrap_memory(uri.c_str() + lStart, lEnd - lStart);
- int lPort = -1;
-
- if ( ( ! lHost.empty() ) && ( lIndex != zstring::npos ) && ( lStart < lEnd ) )
- {
- zstring lPortString = lTmp.substr(0, lEnd - lStart);
-
- if ( !lPortString.empty() )
- {
- lPort = atoi(lPortString.c_str());
- }
- }
- else if ( lStart >= lEnd && lIndex != zstring::npos )
- {
- lPort = -2;
- }
-
- if (is_valid_server_based_authority(lHost,
- lPort,
- lUserInfo,
- lUserInfoFound))
- {
- theHost = lHost;
- set_state(Host);
-
- if (lPort != -1)
- {
- thePort = lPort;
- set_state(Port);
- }
-
- if (lUserInfoFound)
- {
- set_user_info(lUserInfo);
- }
-
- return;
- }
- set_reg_based_authority(uri);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_valid_server_based_authority(
- const zstring& host,
- const int port,
- const zstring& user_info,
- bool user_info_found)
-{
- if ( !is_well_formed_address(host.c_str(), (ulong)host.size()) )
- {
- return false;
- }
-
- if ( (port > 65535) || ( port < 0 && port != -1) )
- {
- return false;
- }
-
- // TODO check user_info
-
- return true;
-}
-
-
-
-/*******************************************************************************
- hier_part = ( net_path | abs_path ) [ "?" query ]
- opaque_part = uric_no_slash *uric
-
- uric_no_slash = unreserved | escaped | ";" | "?" | ":" | "@" |
- "&" | "=" | "+" | "$" | ","
-
- net_path = "//" authority [ abs_path ]
- abs_path = "/" path_segments
- rel_path = rel_segment [ abs_path ]
-
- rel_segment = 1*( unreserved | escaped |
- ";" | "@" | "&" | "=" | "+" | "$" | "," )
-
- path = [ abs_path | opaque_part ]
- path_segments = segment *( "/" segment )
- segment = *pchar *( ";" param )
- param = *pchar
- pchar = unreserved | escaped |
- ":" | "@" | "&" | "=" | "+" | "$" | ","
-********************************************************************************/
-void URI::initializePath(const zstring& uri)
-{
- checked_vector<uint32_t> lCodepoints;
- utf8::to_codepoints(uri, &lCodepoints);
-
- ulong lIndex = 0;
- ulong lStart = 0;
- ulong lEnd = (ulong)lCodepoints.size();
- uint32_t lCp = 0;
-
- if (uri.empty())
- {
- thePath = uri;
- set_state(Path);
- return;
- }
-
- // path - everything up to query string or fragment
- if ( lStart < lEnd )
- {
- // RFC 2732 only allows '[' and ']' to appear in the opaque part.
- if ( ! is_set(Scheme) || lCodepoints[lStart] == '/')
- {
- // Scan path.
- // abs_path = "/" path_segments
- // rel_path = rel_segment [ abs_path ]
- while ( lIndex < lEnd )
- {
- lCp = lCodepoints[lIndex];
- if ( lCp == '?' || lCp == '#' )
- break;
-
- if ( lCp == '%' )
- {
- if ( lIndex + 2 >= lEnd )
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexSequence ) )
- );
- }
- unicode::code_point lHex1 = lCodepoints[++lIndex];
- if(!ascii::is_xdigit(lHex1))
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexDigit_3 ), lHex1 )
- );
- unicode::code_point lHex2 = lCodepoints[++lIndex];
- if(!ascii::is_xdigit(lHex2))
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexDigit_3 ), lHex2 )
- );
- }
- else if (!is_unreserved_char(lCp) && !is_path_character(lCp) && valid)
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( BadUnicodeChar_3 ), lCp )
- );
- }
- ++lIndex;
- }
- #ifdef WIN32
- if (ZSTREQ(theScheme, "file") &&
- (lCodepoints[lStart] == '/') &&
- (lEnd > (lStart+2)) &&
- ((lCodepoints[lStart+2] == ':') || !uri.compare(lStart+2, 4, "%3A/")))//jump over first '/' of path
- lStart++;
- #endif
- }
- else
- {
- while ( lIndex < lEnd )
- {
- lCp = lCodepoints[lIndex];
- if ( lCp == '?' || lCp == '#' )
- break;
-
- if ( lCp == '%' )
- {
- // TODO check errors
- }
- else if (!is_reservered_or_unreserved_char(lCp) && valid)
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( uri, ZED( BadUnicodeChar_3 ), lCp )
- );
- }
- ++lIndex;
- }
- }
-
- } // lStart < lEnd
-
-
- thePath.clear();
- utf8::append_codepoints(lCodepoints.begin() + lStart,
- lCodepoints.begin() + lIndex,
- &thePath);
-
- set_state(Path);
-
- // query - starts with ? and up to fragment or end
- if ( lCp == '?' )
- {
- ++lIndex;
- lStart = lIndex;
- while ( lIndex < lEnd )
- {
- lCp = lCodepoints[lIndex];
- if ( lCp == '#' )
- break;
-
- // TODO check conformance
- ++lIndex;
- } /* lIndex < lEnd */
-
- theQueryString.clear();
- utf8::append_codepoints(lCodepoints.begin() + lStart,
- lCodepoints.begin() + lIndex,
- &theQueryString);
-
- set_state(QueryString);
- }
-
- // fragment - starts with #
- if ( lCp == '#' )
- {
- ++lIndex;
- lStart = lIndex;
- while ( lIndex < lEnd )
- {
- lCp = lCodepoints[lIndex];
- // TODO check conformance
-
- ++lIndex;
- } /* lIndex < lEnd */
-
- if ( lIndex > lStart)
- {
- theFragment.clear();
- utf8::append_codepoints(lCodepoints.begin() + lStart,
- lCodepoints.begin() + lIndex,
- &theFragment);
- set_state(Fragment);
- }
- else
- {
- // fragment is not set
- }
- }
-
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_scheme(const zstring& new_scheme)
-{
- if ( new_scheme.empty() )
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( "", ZED( NoURIScheme ) )
- );
- }
-
- if ( ! is_conformant_scheme_name(new_scheme) )
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( "", ZED( BadURIScheme_3 ), new_scheme )
- );
- }
-
- theScheme = new_scheme;
- set_state(Scheme);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_host(const zstring& new_host)
-{
- theHost = new_host;
- set_state(Host);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_port(int new_port)
-{
- thePort = new_port;
- set_state(Port);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_user_info(const zstring& new_user_info)
-{
- uri::encode(new_user_info, &theUserInfo, false);
-
- set_state(UserInfo);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_reg_based_authority(const zstring& new_authority)
-{
- if ( new_authority.empty() )
- {
- return;
- }
-
- // TODO check valid registry based authority
-
- theRegBasedAuthority = new_authority;
- set_state(RegBasedAuthority);
-
- unset_state(Host);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::set_path(const zstring& new_path)
-{
- if (new_path.empty())
- {
- thePath = new_path;
- unset_state(Path);
- theQueryString = new_path;
- unset_state(QueryString);
- theFragment = new_path;
- unset_state(Fragment);
- }
- else
- {
- initializePath(new_path);
- }
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::get_user_info(zstring& result) const
-{
- uri::decode(theUserInfo, &result);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::get_reg_based_authority(zstring& result) const
-{
- uri::decode(theRegBasedAuthority, &result);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::get_path(zstring& result) const
-{
- uri::decode(thePath, &result);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::get_query(zstring& result) const
-{
- uri::decode(theQueryString, &result);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::get_fragment(zstring& result) const
-{
- uri::decode(theFragment, &result);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_absolute() const
-{
- return is_set(Scheme) && !theScheme.empty();
-}
-
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::resolve(const URI* base_uri)
-{
- if (is_absolute())
- {
- return;
- }
-
- if ( base_uri == 0 && toString().empty() )
- {
- throw XQUERY_EXCEPTION(
- err::XQST0046, ERROR_PARAMS( "", ZED( ZeroLenURI ) )
- );
- }
-
- if ( toString().empty() )
- {
- // just copy the base uri
- initialize(*base_uri);
- }
-
- zstring::size_type lIndex = 0;
-
- // If the path component is empty and the scheme, authority, and
- // query components are undefined, then it is a reference to the
- // current document and we are done. Otherwise, the reference URI's
- // query and fragment components are defined as found (or not found)
- // within the URI reference and not inherited from the base URI.
- if ( ((!is_set(Path)) || (thePath.empty())) &&
- (!is_set(Scheme) && (!is_set(Host)) && (!is_set(RegBasedAuthority)) ))
- {
- set_scheme(base_uri->get_scheme());
-
- if (base_uri->is_set(UserInfo))
- {
- zstring userInfo;
- base_uri->get_user_info(userInfo);
- set_user_info(userInfo);
- }
-
- if (base_uri->is_set(Host))
- {
- set_host(base_uri->get_host());
- }
-
- if (base_uri->is_set(Port))
- {
- set_port(base_uri->get_port());
- }
-
- if (base_uri->is_set(RegBasedAuthority))
- {
- zstring auth;
- base_uri->get_reg_based_authority(auth);
- set_reg_based_authority(auth);
- }
-
- if (base_uri->is_set(Path))
- {
- // I think this is a bug in xerces because it doesn't remove the last segment
- zstring path;
- base_uri->get_path(path);
-
- zstring::size_type last_slash = path.rfind("/");
- if ( last_slash != zstring::npos )
- thePath = path.substr(0, last_slash+1);
- else
- thePath = path;
-
- set_state(Path);
- }
-
- if ( (! is_set(QueryString)) )
- {
- base_uri->get_query(theQueryString);
-
- set_state(QueryString);
- }
-
- invalidate_text();
-
- return;
- }
-
- // If the scheme component is defined, indicating that the reference
- // starts with a scheme name, then the reference is interpreted as an
- // absolute URI and we are done. Otherwise, the reference URI's
- // scheme is inherited from the base URI's scheme component.
- if ( is_set(Scheme) )
- {
- invalidate_text();
- return;
- }
-
- set_scheme(base_uri->get_scheme());
-
- // If the authority component is defined, then the reference is a
- // network-path and we skip to step 7. Otherwise, the reference
- // URI's authority is inherited from the base URI's authority
- // component, which will also be undefined if the URI scheme does not
- // use an authority component.
- if ( (!is_set(Host)) && (!is_set(RegBasedAuthority)) )
- {
- if (base_uri->is_set(UserInfo))
- {
- base_uri->get_user_info(theUserInfo);
- set_state(UserInfo);
- }
-
- if (base_uri->is_set(Host))
- {
- theHost = base_uri->get_host();
- set_state(Host);
- }
-
- if (base_uri->is_set(Port))
- {
- thePort = base_uri->get_port();
- set_state(Port);
- }
-
- if (base_uri->is_set(RegBasedAuthority))
- {
- base_uri->get_reg_based_authority(theRegBasedAuthority);
- set_state(RegBasedAuthority);
- }
- }
- else
- {
- invalidate_text();
- return;
- }
-
-
- // If the path component begins with a slash character ("/"), then
- // the reference is an absolute-path and we skip to step 7.
- if ( (is_set(Path)) && (thePath[0] =='/') )
- {
- invalidate_text();
- return;
- }
-
- zstring base_path = base_uri->get_encoded_path();
- zstring path;
-
- if ( base_uri->is_set(Path) )
- {
- zstring::size_type last_slash = base_path.rfind("/");
- if ( last_slash != zstring::npos )
- path = base_path.substr(0, last_slash+1);
-// else
-// path = "/";
-
- }
-
- // 6b - append the relative URI path
- path.append(thePath);
-
- // 6c - remove all "./" where "." is a complete path segment
- ascii::replace_all(path, "/./", 3, "/", 1);
-
- // 6d If the buffer string ends with "." as a complete path segment,
- // that "." is removed.
- if (ascii::ends_with(path, "/.", 2))
- {
- path = path.substr(0, path.size() - 1);
- }
-
- // 6e All occurrences of "<segment>/../", where <segment> is a
- // complete path segment not equal to "..", are removed from the
- // buffer string. Removal of these path segments is performed
- // iteratively, removing the leftmost matching pattern on each
- // iteration, until no matching pattern remains.
- zstring::size_type segIndex;
- zstring::size_type offset = 1;
-
- zstring_b tmp_path;
- tmp_path.wrap_memory(const_cast<char*>(path.c_str() + 1), path.size() - 1);
- zstring_b tmp1;
- zstring_b tmp2;
-
- while ((lIndex = tmp_path.find("/../")) != zstring::npos)
- {
- // Undo offset
- lIndex += offset;
-
- // Find start of <segment> within substring ending at found point.
- tmp1.wrap_memory(path.c_str(), lIndex - 1);
-
- segIndex = tmp1.rfind("/");
-
- // Ensure <segment> exists and != ".."
- if (segIndex != zstring::npos &&
- (path[segIndex+1] != '.' ||
- path[segIndex+2] != '.' ||
- segIndex + 3 != lIndex))
- {
- tmp1.wrap_memory(path.c_str(), segIndex);
- tmp2.wrap_memory(path.c_str() + lIndex + 3, path.size() - lIndex - 3);
-
- zstring tmp;
- tmp.reserve(tmp1.size() + tmp2.size());
- tmp += tmp1;
- tmp += tmp2;
- path.swap(tmp);
-
- offset = (segIndex == 0 ? 1 : segIndex);
- }
- else
- {
- offset += 4;
- }
-
- tmp_path.wrap_memory(path.c_str() + offset, path.size() - offset);
- } // while
-
- // 6f) If the buffer string ends with "<segment>/..", where <segment>
- // is a complete path segment not equal to "..", that
- // "<segment>/.." is removed.
- if (ascii::ends_with(path, "/..", 3))
- {
- // Find start of <segment> within substring ending at found point.
- lIndex = path.size() - 3;
- tmp1.wrap_memory(path.c_str(), lIndex - 1);
- segIndex = tmp1.rfind("/");
-
- if (segIndex != zstring::npos &&
- (path[segIndex+1] != '.' ||
- path[segIndex+2] != '.' ||
- segIndex + 3 != lIndex))
- {
- path = path.substr(0, segIndex+1);
- }
- }
-
- thePath = path;
- invalidate_text();
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::relativize(const URI* base_uri)
-{
- if ( base_uri == 0 || base_uri->toString().size() == 0)
- return;
-
- // if the scheme of the base_uri and the current uri are not identical,
- // we return the current uri
- if ( base_uri->get_scheme().compare(get_scheme()) != 0 )
- {
- return;
- }
-
- // if the authority of the base_uri and the current uri are not identical,
- // we return the current uri
- zstring auth;
- zstring base_auth;
- get_reg_based_authority(auth);
- base_uri->get_reg_based_authority(base_auth);
-
- if ( base_auth != auth )
- {
- return;
- }
-
- // if the path of the current uri is not a substring of the path of the base_uri,
- // we return the current uri
- zstring path;
- zstring base_path;
- get_path(path);
- base_uri->get_path(base_path);
-
- if ( path.find(base_path) != 0 )
- {
- return;
- }
-
- // construct a new relative hierarchical URI is constructed with query and
- // fragment components taken from the given URI and with a path component
- // computed by removing this URI's
- // path from the beginning of the given URI's path.
- zstring lNewPath = path.substr(base_path.size());
- set_path(lNewPath);
- // unset remaining stuff
- theScheme.clear();
- unset_state(Scheme);
- theRegBasedAuthority.clear();
- unset_state(RegBasedAuthority);
- theUserInfo.clear();
- unset_state(UserInfo);
- thePort = 0;
- unset_state(Port);
- theHost.clear();
- unset_state(Host);
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-bool URI::is_conformant_scheme_name(const zstring& scheme)
-{
-#if 0
- // start with a-zA-Z
- if ( ! zorba::matches(scheme, "[a-zA-Z]", "" ) )
- return false;
-#endif
-
- for (ulong i = 0; i < scheme.size(); ++i)
- {
- char c = scheme[i];
-
- if ( ! ascii::is_alpha(c) && c != '+' && c != '-' && c != '.')
- {
- return false;
- }
- }
- return true;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-const zstring& URI::toString() const
-{
- if (theURIText.empty())
- {
- build_full_text();
- }
- return theURIText;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-const zstring& URI::toPathNotation() const
-{
- if (thePathNotation.empty())
- {
- build_path_notation();
- }
- return thePathNotation;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-const zstring& URI::toASCIIString() const
-{
- if (theASCIIURIText.empty())
- {
- build_ascii_full_text();
- }
- return theASCIIURIText;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::build_path_notation() const
-{
- std::ostringstream lPathNotation;
-
- std::string lToTokenize;
- if (is_set(Host))
- {
- lToTokenize = theHost.str();
- }
- else
- {
- lToTokenize = theRegBasedAuthority.str();
- }
-
- std::string::size_type lastPos =
- lToTokenize.find_last_not_of(".", lToTokenize.length());
-
- std::string::size_type pos = lToTokenize.find_last_of(".", lastPos);
-
- if (pos == std::string::npos)
- {
- lPathNotation << lToTokenize;
- }
-
- while (std::string::npos != pos)
- {
- lPathNotation << lToTokenize.substr(pos + 1, lastPos - pos) << "/";
-
- lastPos = pos - 1;
- pos = lToTokenize.find_last_of(".", lastPos);
- if (pos == std::string::npos)
- {
- lPathNotation << lToTokenize.substr(0, lastPos+1);
- }
- }
-
- if (is_set(Path))
- {
- if(!thePath.empty() && (thePath[0] != '/') && (thePath[0] != '\\'))
- lPathNotation << "/";
- lPathNotation << thePath;
- }
-
- thePathNotation = lPathNotation.str();
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::build_full_text() const
-{
- std::ostringstream lURI;
-
- // Scheme
- if ( is_set(Scheme) )
- lURI << theScheme << ":";
-
- // Authority
- if ( is_set(Host) || is_set(RegBasedAuthority) )
- {
- lURI << "//";
- if ( is_set(Host) )
- {
- if ( is_set(UserInfo) )
- lURI << theUserInfo << "@";
-
- lURI << theHost;
-
- if ( is_set(Port) )
- lURI << ":" << thePort;
- }
- else
- {
- lURI << theRegBasedAuthority;
- }
- }
-
- if ( is_set(Path) )
- {
- #ifdef WIN32
- if(ZSTREQ(theScheme, "file") && !thePath.empty() && (thePath[0] != '/'))
- lURI << "/";
- #endif
- lURI << thePath;
- }
-
- if ( is_set(QueryString) )
- lURI << "?" << theQueryString;
-
- if ( is_set(Fragment) )
- lURI << "#" << theFragment;
-
- theURIText = lURI.str();
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void URI::build_ascii_full_text() const
-{
- std::ostringstream lURI;
-
- // Scheme
- if ( is_set(Scheme) )
- lURI << theScheme << ":";
-
- // Authority
- if ( is_set(Host) || is_set(RegBasedAuthority) )
- {
- lURI << "//";
-
- if ( is_set(Host) )
- {
- if ( is_set(UserInfo) )
- lURI << theUserInfo << "@";
-
- lURI << theHost;
-
- if ( is_set(Port) )
- lURI << ":" << thePort;
- }
- else
- {
- lURI << theRegBasedAuthority;
- }
- }
-
- if ( is_set(Path) )
- {
- #ifdef WIN32
- if(ZSTREQ(theScheme, "file") && !thePath.empty() && (thePath[0] != '/'))
- lURI << "/";
- #endif
- lURI << thePath;
- }
-
- if ( is_set(QueryString) )
- lURI << "?" << theQueryString;
-
- if ( is_set(Fragment) )
- lURI << "#" << theFragment;
-
- theASCIIURIText = lURI.str();
-}
-
-};
-/* vim:set et sw=2 ts=2: */
+/*
+ * Copyright 2006-2008 The FLWOR Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#include "stdafx.h"
+
+#include "schema_types.h"
+
+#include "diagnostics/xquery_diagnostics.h"
+#include "diagnostics/dict.h"
+#include "diagnostics/assert.h"
+
+#include <zorba/util/path.h>
+
+#include "URI.h"
+
+#include "util/ascii_util.h"
+#include "util/string_util.h"
+#include "util/uri_util.h"
+#include "util/utf8_util.h"
+#include "zorbautils/string_util.h"
+
+
+using namespace std;
+
+namespace zorba {
+
+ /*
+ ---------------------------------------------------------------------------
+ URI-reference = [ absoluteURI | relativeURI ] [ "#" fragment ]
+ absoluteURI = scheme ":" ( hier_part | opaque_part )
+ relativeURI = ( net_path | abs_path | rel_path ) [ "?" query ]
+ ---------------------------------------------------------------------------
+ query = *uric
+
+ fragment = *uric
+---------------------------------------------------------------------------
+ */
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_unreserved_char(uint32_t c)
+{
+ static std::string lMarkCharacter("-_.!~*'{}");
+ return (ascii::is_alnum(c) || (c == ' ') || (c > 127 ) ||
+ ((c<128) && lMarkCharacter.find((char)c) != std::string::npos));
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_path_character(uint32_t c)
+{
+ static std::string lPathChracters(";/\\:@&=+$,");
+ return ((c<128) && lPathChracters.find((char)c) != std::string::npos);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_reservered_or_unreserved_char(uint32_t c)
+{
+ static std::string lMarkOrReservedChars("-_.!~*'();/?:@&=+$,[]");
+ return (ascii::is_alnum(c) ||
+ (c == ' ') ||
+ ((c<128) && lMarkOrReservedChars.find((char)c) != std::string::npos));
+}
+
+
+/*******************************************************************************
+ Note: The encode_file_URI and decode_file_URI methods are hacks. Doing it
+ properly would require boost-filesystem (or equivalent code).
+
+ The decode_file_URI() method takes a file URI and converts it to a filepath
+ in the native OS foramt.
+********************************************************************************/
+void URI::decode_file_URI(const zstring& uri, zstring& filepath)
+{
+ // TODO: file://localhost/
+#ifdef WIN32
+ if (uri.compare(0, 8, "file:///") == 0 &&
+ ((uri.compare(9, 1, ":") == 0) || (uri.compare(9, 4, "%3A/") == 0)))
+ {
+ zstring tmp(uri.c_str() + 8);
+ uri::decode(tmp, &filepath);
+ }
+ else
+#endif
+ if (uri.compare(0, 8, "file:///") == 0)
+ {
+ zstring tmp(uri.c_str() + 7);
+ uri::decode(tmp, &filepath);
+ }
+ else if (uri.compare(0, 17, "file://localhost/") == 0)
+ {
+ zstring tmp(uri.c_str() + 16);
+ uri::decode(tmp, &filepath);
+ }
+ else
+ {
+ // should we raise an unknown host exception?
+ filepath = uri;
+ }
+
+#ifdef WIN32
+ ascii::replace_all(filepath, '/', '\\');
+#endif
+}
+
+
+/*******************************************************************************
+ The encode_file_URI() method takes a filepath and converts it to a file URI.
+
+ Assumes input is absolute path.
+********************************************************************************/
+void URI::encode_file_URI(const zstring& filepath, zstring& uri)
+{
+ if (filepath.find("://", 0, 3) != zstring::npos)
+ {
+ uri = filepath;
+ return;
+ }
+
+#ifdef WIN32
+ uri = "file:///";
+
+ zstring tmp1( filepath );
+ ascii::replace_all( tmp1, '\\', '/' );
+
+ zstring tmp2;
+ uri::encode(tmp1, &tmp2, false);
+
+ uri.append(tmp2);
+
+#else
+ if (filepath[0] == '/')
+ uri = "file://";
+ else
+ uri = "file:///";
+
+ zstring tmp;
+ uri::encode(filepath, &tmp, false);
+
+ uri.append(tmp);
+#endif
+}
+
+
+/*******************************************************************************
+ The encode_file_URI() method takes a filepath and converts it to a file URI.
+
+ Assumes input is absolute path.
+********************************************************************************/
+std::string URI::encode_file_URI(const std::string& filepath)
+{
+ zstring uri;
+ encode_file_URI(filepath, uri);
+ return uri.str();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_well_formed_address(const char* addr, ulong addrLen)
+{
+ if (addrLen == 0)
+ {
+ return false;
+ }
+
+ char c = addr[0];
+
+ if (c == '[')
+ {
+ return is_well_formed_ipv6_reference(addr, addrLen);
+ }
+
+ if ( c == '.' || c == '-' || addr[addrLen-1] == '-')
+ {
+ return false;
+ }
+
+ zstring_b wrap;
+ wrap.wrap_memory(addr, addrLen);
+
+ zstring::size_type lLastPeriodPos = wrap.rfind(".");
+
+ if ( lLastPeriodPos != zstring::npos && lLastPeriodPos + 1 == addrLen )
+ {
+ zstring_b wrap2;
+ wrap2.wrap_memory(addr, lLastPeriodPos);
+ lLastPeriodPos = wrap2.rfind(".");
+
+ if ( lLastPeriodPos != zstring::npos && ascii::is_digit(addr[lLastPeriodPos + 1]) )
+ {
+ return false;
+ }
+ }
+
+ if ( lLastPeriodPos != zstring::npos && ascii::is_digit(addr[lLastPeriodPos + 1]) )
+ {
+ return is_well_formed_ipv4_address(addr, addrLen);
+ }
+ else
+ {
+ if (addrLen > 255)
+ {
+ return false;
+ }
+
+ ulong lLabelCharCount = 0;
+
+ for (ulong i = 0; i < addrLen; ++i)
+ {
+ char c1 = addr[i];
+
+ if ( c1 == '.' )
+ {
+ if ( ( i > 0 && ! ascii::is_alnum(addr[i-1])) ||
+ ( i + 1 < addrLen && ! ascii::is_alnum(addr[i+1])) )
+ {
+ return false;
+ }
+
+ lLabelCharCount = 0;
+ }
+ else if ( ! ascii::is_alnum(c1) && c1 != '-' )
+ {
+ return false;
+ }
+ else if ( ++lLabelCharCount > 63 )
+ {
+ return false;
+ }
+ }
+ }
+
+ return true;
+}
+
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_well_formed_ipv4_address(const char* addr, ulong length)
+{
+ ulong numDots = 0;
+ ulong numDigits = 0;
+
+ for (ulong i = 0; i < length; ++i)
+ {
+ char c = addr[i];
+
+ if (c == '.')
+ {
+ if ( (i == 0) || (i+1 == length) || ! ascii::is_digit(addr[i+1]) )
+ return false;
+ }
+ else if ( ! ascii::is_digit(c) )
+ {
+ return false;
+ }
+ else if (++numDigits > 3)
+ {
+ return false;
+ }
+ else if (numDigits == 3)
+ {
+ char lFirst = addr[i-2];
+ char lSecond = addr[i-1];
+ char lLast = addr[i];
+
+ if ( !(lFirst < '2' ||
+ (lFirst == '2' && (lSecond < '5' || (lSecond == '5' && lLast <= '5')))))
+ return false;
+ }
+ }
+
+ return (numDots == 3);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_well_formed_ipv6_reference(const char* addr, ulong length)
+{
+ long lIndex = 1;
+ long lEnd = length-1;
+
+ // Check if string is a potential match for IPv6reference.
+ if (!(length > 2 && addr[0] == '[' && addr[lEnd] == ']'))
+ {
+ return false;
+ }
+
+ // Counter for the number of 16-bit sections read in the address.
+ long lCounter = 0;
+
+ lIndex = scanHexSequence(addr, lIndex, lEnd, lCounter);
+ if ( lIndex == -1)
+ {
+ return false;
+ }
+
+ // Address must contain 128-bits of information.
+ else if (lIndex == lEnd)
+ {
+ return (lCounter == 8);
+ }
+
+ if (lIndex+1 < lEnd && addr[lIndex] == ':')
+ {
+ if (addr[lIndex+1] == ':')
+ {
+ // '::' represents at least one 16-bit group of zeros.
+ if (++lCounter > 8)
+ {
+ return false;
+ }
+
+ lIndex += 2;
+
+ // Trailing zeros will fill out the rest of the address.
+ if (lIndex == lEnd)
+ {
+ return true;
+ }
+ }
+
+ // If the second character wasn't ':', in order to be valid,
+ // the remainder of the string must match IPv4Address,
+ // and we must have read exactly 6 16-bit groups.
+ else
+ {
+ if (lCounter == 6)
+ {
+ return is_well_formed_ipv4_address(addr + lIndex+1, lEnd - lIndex - 1);
+ }
+ else
+ {
+ return false;
+ }
+ }
+ }
+ else
+ {
+ return false;
+ }
+
+ // 3. Scan hex sequence after '::'.
+ int prevCount = lCounter;
+
+ lIndex = scanHexSequence(addr, lIndex, lEnd, lCounter);
+ if (lIndex == -1)
+ {
+ return false;
+ }
+
+ // If this is the end of the address then
+ // we've got 128-bits of information.
+ else if (lIndex == lEnd)
+ {
+ return true;
+ }
+
+ // The address ends in an IPv4 address, or it is invalid.
+ // scanHexSequence has already made sure that we have the right number of bits.
+ int shiftCount = (lCounter > prevCount) ? lIndex+1 : lIndex;
+
+ return is_well_formed_ipv4_address(addr + shiftCount, lEnd - shiftCount);
+}
+
+
+/*******************************************************************************
+ For use with isWellFormedIPv6Reference only.
+********************************************************************************/
+long URI::scanHexSequence(
+ const char* addr,
+ long index,
+ long end,
+ long& counter)
+{
+ char c;
+ long lNumDigits = 0;
+ long lStart = index;
+
+ // Trying to match the following productions:
+ // hexseq = hex4 *( ":" hex4)
+ // hex4 = 1*4HEXDIG
+ for (; index < end; ++index)
+ {
+ c = addr[index];
+
+ if ( c == ':' )
+ {
+ // IPv6 addresses are 128-bit, so there can be at most eight sections.
+ if (lNumDigits > 0 && ++counter > 8)
+ {
+ return -1;
+ }
+
+ // This could be '::'.
+ if (lNumDigits == 0 || ((index+1 < end) && addr[index+1] == ':'))
+ {
+ return index;
+ }
+
+ lNumDigits = 0;
+ }
+
+ // This might be invalid or an IPv4address. If it's potentially an IPv4address,
+ // backup to just after the last valid character that matches hexseq.
+ else if (!ascii::is_xdigit(c))
+ {
+ if (c == '.' &&
+ lNumDigits < 4 &&
+ lNumDigits > 0 &&
+ counter <= 6)
+ {
+ long lBack = index - lNumDigits - 1;
+ return (lBack >= lStart) ? lBack : lStart;
+ }
+
+ return -1;
+ }
+
+ // There can be at most 4 hex digits per group.
+ else if (++lNumDigits > 4)
+ {
+ return -1;
+ }
+ }
+
+ return (lNumDigits > 0 && ++counter <= 8) ? end : -1;
+}
+
+
+/*******************************************************************************
+ construct a uri
+********************************************************************************/
+URI::URI(const zstring& uri, bool validate)
+ :
+ theState(0),
+ thePort(0),
+ valid(validate)
+{
+ initialize(uri);
+
+ //std::cout << "empty rep 2 = " << std::hex << theScheme.empty_rep() << std::endl;
+}
+
+
+/*******************************************************************************
+ construct a uri and eventually resolve with the given base uri
+********************************************************************************/
+URI::URI(const URI& base_uri, const zstring& uri, bool validate)
+ :
+ theState(0),
+ thePort(0),
+ valid(validate)
+{
+ initialize(uri, true);
+ resolve(&base_uri);
+}
+
+
+/*******************************************************************************
+ constructs a new uri by relativizing the full_uri against the base_uri
+********************************************************************************/
+URI::URI(const URI& full_uri, const URI& base_uri)
+ :
+ theState(0),
+ thePort(0),
+ valid(false)
+{
+ initialize(full_uri.toString(), false);
+ relativize(&base_uri);
+}
+
+
+/*******************************************************************************
+ copy constructor
+********************************************************************************/
+URI::URI(const URI& to_copy)
+{
+ initialize(to_copy);
+}
+
+
+/*******************************************************************************
+ default (empty) constructor)
+********************************************************************************/
+URI::URI()
+ :
+ theState(0),
+ thePort(0),
+ valid(true)
+{
+}
+
+
+/*******************************************************************************
+ destructor
+********************************************************************************/
+URI::~URI()
+{
+}
+
+
+/*******************************************************************************
+ copy a uri
+********************************************************************************/
+void URI::initialize(const URI& to_copy)
+{
+ theState = to_copy.theState;
+ theScheme = to_copy.theScheme;
+ theUserInfo = to_copy.theUserInfo;
+ theHost = to_copy.theHost;
+ thePort = to_copy.thePort;
+ theRegBasedAuthority = to_copy.theRegBasedAuthority;
+ thePath = to_copy.thePath;
+ theQueryString = to_copy.theQueryString;
+ theFragment = to_copy.theFragment;
+ valid = to_copy.valid;
+}
+
+
+/*******************************************************************************
+ Initialize this uri based on a base-uri (i.e. uri resolving) and a (relative)
+ uri given as string
+********************************************************************************/
+void URI::initialize(const zstring& uri, bool have_base)
+{
+ invalidate_text();
+ thePathNotation.clear();
+ theScheme.clear();
+ theHost.clear();
+ theUserInfo.clear();
+ theRegBasedAuthority.clear();
+ thePath.clear();
+ theQueryString.clear();
+ theFragment.clear();
+
+ // first, we need to normalize the spaces in the uri
+ // and only work with the normalized version from this point on
+ zstring lTrimmedURI;
+ ascii::normalize_whitespace(uri, &lTrimmedURI);
+ ascii::trim_whitespace(lTrimmedURI);
+
+ zstring::size_type lTrimmedURILength = lTrimmedURI.size();
+
+ // index of the current processing state used in this function
+ ulong lIndex = 0;
+
+ zstring::size_type lColonIdx = lTrimmedURI.find(":");
+ zstring::size_type lSlashIdx = lTrimmedURI.find("/");
+ zstring::size_type lQueryIdx = lTrimmedURI.find("?");
+ zstring::size_type lFragmentIdx = lTrimmedURI.find("#");
+
+#ifdef WIN32
+ // on WIN32 we might have a drive specification ("C:")
+ // and we don't want to consider this as scheme
+ char lLetter = lTrimmedURI[0];
+ bool lIsDrive = false;
+ if (lColonIdx == 1 &&
+ ((lLetter >= 65 && 90 >= lLetter) || (lLetter >= 97 && 122 >= lLetter)))
+ {
+ lIsDrive = true;
+ }
+#endif
+
+ /**
+ * Scheme
+ * must be before `/', '?' or '#'.
+ */
+ if ((lColonIdx == 0 || lColonIdx == zstring::npos) ||
+#ifdef WIN32
+ // avoid interpreting the drive as a scheme
+ lIsDrive ||
+#endif
+ (lColonIdx > lSlashIdx && lSlashIdx != zstring::npos) ||
+ (lColonIdx > lQueryIdx && lQueryIdx != zstring::npos) ||
+ (lColonIdx > lFragmentIdx && lFragmentIdx != zstring::npos))
+ {
+ // A standalone base is a valid URI
+ if (valid &&
+ (lColonIdx == 0 || (!have_base && lFragmentIdx != zstring::npos)) &&
+ lTrimmedURILength > 0)
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( lTrimmedURI, ZED( NoURIScheme ) )
+ );
+ }
+ }
+ else
+ {
+ initializeScheme(lTrimmedURI);
+
+ lIndex = (ulong)theScheme.size() + 1;
+ }
+
+ /**
+ * Authority
+ * two slashes means generic URI syntax, so we get the authority
+ */
+ if (lTrimmedURI.compare(lIndex, 2, "//") == 0)
+ {
+ lIndex += 2;
+ if (lIndex >= lTrimmedURILength)
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( lTrimmedURI, ZED( NoURIAuthority ) )
+ );
+ }
+ else
+ {
+ ulong lStartPos = lIndex;
+
+ // get authority
+ // (everything up to path, query, fragment or the end of the URI)
+ // RFC3986, 3.2, par. 2
+ char c;
+ while (lIndex < lTrimmedURILength)
+ {
+ c = lTrimmedURI[lIndex];
+
+ if (c == '/' || c == '?' || c == '#')
+ break;
+
+ ++lIndex;
+ }
+
+ // if we found authority, parse it out, otherwise we set the
+ // host to empty string
+ if (lIndex > lStartPos)
+ {
+ zstring lAuthUri = lTrimmedURI.substr(lStartPos, lIndex - lStartPos);
+
+ // For "file" scheme only allow "localhost" as authority.
+ // This makes this implementation the same with the file module.
+ // If this functionality is changed, please make the same changes
+ // in the file module.
+ if (ZSTREQ(theScheme, "file") &&
+ !ZSTREQ(lAuthUri, "localhost"))
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046,
+ ERROR_PARAMS( lTrimmedURI, ZED( BadFileURIAuthority_2 ), lAuthUri )
+ );
+ }
+
+ initializeAuthority(lAuthUri);
+ }
+ else
+ {
+ set_host(zstring());
+ }
+ }
+ // do not allow constructs like: file:D:/myFile or http:myFile
+ }
+ else if (ZSTREQ(theScheme, "file") ||
+ ZSTREQ(theScheme, "http") ||
+ ZSTREQ(theScheme, "https"))
+ {
+ if (valid)
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046,
+ ERROR_PARAMS( lTrimmedURI, ZED( BadURISyntaxForScheme_3 ), theScheme )
+ );
+ }
+ }
+
+ // stop, if we're done here
+ if (lIndex > lTrimmedURILength)
+ return;
+
+ /**
+ * Path
+ */
+ zstring lPathUri = lTrimmedURI.substr(lIndex, lTrimmedURILength - lIndex);
+
+ initializePath(lPathUri);
+}
+
+
+/*******************************************************************************
+ scheme = alpha *( alpha | digit | "+" | "-" | "." )
+********************************************************************************/
+void URI::initializeScheme(const zstring& uri)
+{
+ zstring::size_type lSchemeSeparatorIdx = uri.find_first_of(":/?#", 0,4 );
+
+ if ( valid && lSchemeSeparatorIdx == zstring::npos )
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( NoURIScheme ) )
+ );
+ }
+ else
+ {
+ set_scheme(uri.substr(0, lSchemeSeparatorIdx));
+ }
+}
+
+
+/*******************************************************************************
+ authority = server | reg_name
+
+ reg_name = 1*( unreserved | escaped | "$" | "," |
+ ";" | ":" | "@" | "&" | "=" | "+" )
+
+ server = [ [ userinfo "@" ] hostport ]
+ userinfo = *( unreserved | escaped |
+ ";" | ":" | "&" | "=" | "+" | "$" | "," )
+
+ hostport = host [ ":" port ]
+ host = hostname | IPv4address
+ hostname = *( domainlabel "." ) toplabel [ "." ]
+ domainlabel = alphanum | alphanum *( alphanum | "-" ) alphanum
+ toplabel = alpha | alpha *( alphanum | "-" ) alphanum
+ IPv4address = 1*digit "." 1*digit "." 1*digit "." 1*digit
+ port = *digit
+********************************************************************************/
+void URI::initializeAuthority(const zstring& uri)
+{
+ zstring::size_type lIndex = 0;
+ zstring::size_type lStart = 0;
+ zstring::size_type lEnd = uri.size();
+
+ zstring lUserInfo;
+ bool lUserInfoFound;
+
+
+ lIndex = uri.find("@");
+
+ if ( lIndex != zstring::npos )
+ {
+ lUserInfo = uri.substr(0, lIndex);
+ ++lIndex;
+ lStart += lIndex;
+ lUserInfoFound = true;
+ }
+ else
+ {
+ lUserInfoFound = false;
+ }
+
+ //
+ // hostport = host [ ":" port ]
+ // host is everything up to ':', or up to
+ // and including ']' if followed by ':'.
+ //
+ zstring lHost;
+ zstring_b lTmp; // used for substrings starting at lStart
+
+ lTmp.wrap_memory(uri.c_str() + lStart, lEnd - lStart);
+
+ if ( lStart < lEnd && uri[lStart] == '[' )
+ {
+ lIndex = lTmp.find("]");
+
+ if ( lIndex != zstring::npos )
+ {
+ lIndex = ((lStart + lIndex + 1) < lEnd && uri[lStart + lIndex + 1] == ':' ?
+ lIndex + 1 : zstring::npos);
+ }
+ }
+ else
+ {
+ lIndex = lTmp.find(":");
+ }
+
+ if ( lIndex != zstring::npos )
+ {
+ lHost = lTmp.substr(0, lIndex);
+
+ ++lIndex; // skip the colon
+ lStart += lIndex;
+ }
+ else
+ {
+ lHost = lTmp.substr(0, lEnd - lStart);
+ lStart = lEnd;
+ }
+
+ lTmp.wrap_memory(uri.c_str() + lStart, lEnd - lStart);
+ int lPort = -1;
+
+ if ( ( ! lHost.empty() ) && ( lIndex != zstring::npos ) && ( lStart < lEnd ) )
+ {
+ zstring lPortString = lTmp.substr(0, lEnd - lStart);
+
+ if ( !lPortString.empty() )
+ {
+ lPort = atoi(lPortString.c_str());
+ }
+ }
+ else if ( lStart >= lEnd && lIndex != zstring::npos )
+ {
+ lPort = -2;
+ }
+
+ if (is_valid_server_based_authority(lHost,
+ lPort,
+ lUserInfo,
+ lUserInfoFound))
+ {
+ theHost = lHost;
+ set_state(Host);
+
+ if (lPort != -1)
+ {
+ thePort = lPort;
+ set_state(Port);
+ }
+
+ if (lUserInfoFound)
+ {
+ set_user_info(lUserInfo);
+ }
+
+ return;
+ }
+ set_reg_based_authority(uri);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_valid_server_based_authority(
+ const zstring& host,
+ const int port,
+ const zstring& user_info,
+ bool user_info_found)
+{
+ if ( !is_well_formed_address(host.c_str(), (ulong)host.size()) )
+ {
+ return false;
+ }
+
+ if ( (port > 65535) || ( port < 0 && port != -1) )
+ {
+ return false;
+ }
+
+ // TODO check user_info
+
+ return true;
+}
+
+
+
+/*******************************************************************************
+ hier_part = ( net_path | abs_path ) [ "?" query ]
+ opaque_part = uric_no_slash *uric
+
+ uric_no_slash = unreserved | escaped | ";" | "?" | ":" | "@" |
+ "&" | "=" | "+" | "$" | ","
+
+ net_path = "//" authority [ abs_path ]
+ abs_path = "/" path_segments
+ rel_path = rel_segment [ abs_path ]
+
+ rel_segment = 1*( unreserved | escaped |
+ ";" | "@" | "&" | "=" | "+" | "$" | "," )
+
+ path = [ abs_path | opaque_part ]
+ path_segments = segment *( "/" segment )
+ segment = *pchar *( ";" param )
+ param = *pchar
+ pchar = unreserved | escaped |
+ ":" | "@" | "&" | "=" | "+" | "$" | ","
+********************************************************************************/
+void URI::initializePath(const zstring& uri)
+{
+ checked_vector<uint32_t> lCodepoints;
+ utf8::to_codepoints(uri, &lCodepoints);
+
+ ulong lIndex = 0;
+ ulong lStart = 0;
+ ulong lEnd = (ulong)lCodepoints.size();
+ uint32_t lCp = 0;
+
+ if (uri.empty())
+ {
+ thePath = uri;
+ set_state(Path);
+ return;
+ }
+
+ // path - everything up to query string or fragment
+ if ( lStart < lEnd )
+ {
+ // RFC 2732 only allows '[' and ']' to appear in the opaque part.
+ if ( ! is_set(Scheme) || lCodepoints[lStart] == '/')
+ {
+ // Scan path.
+ // abs_path = "/" path_segments
+ // rel_path = rel_segment [ abs_path ]
+ while ( lIndex < lEnd )
+ {
+ lCp = lCodepoints[lIndex];
+ if ( lCp == '?' || lCp == '#' )
+ break;
+
+ if ( lCp == '%' )
+ {
+ if ( lIndex + 2 >= lEnd )
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexSequence ) )
+ );
+ }
+ unicode::code_point lHex1 = lCodepoints[++lIndex];
+ if(!ascii::is_xdigit(lHex1))
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexDigit_3 ), lHex1 )
+ );
+ unicode::code_point lHex2 = lCodepoints[++lIndex];
+ if(!ascii::is_xdigit(lHex2))
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( BadHexDigit_3 ), lHex2 )
+ );
+ }
+ else if (!is_unreserved_char(lCp) && !is_path_character(lCp) && valid)
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( BadUnicodeChar_3 ), lCp )
+ );
+ }
+ ++lIndex;
+ }
+ #ifdef WIN32
+ if (ZSTREQ(theScheme, "file") &&
+ (lCodepoints[lStart] == '/') &&
+ (lEnd > (lStart+2)) &&
+ ((lCodepoints[lStart+2] == ':') || !uri.compare(lStart+2, 4, "%3A/")))//jump over first '/' of path
+ lStart++;
+ #endif
+ }
+ else
+ {
+ while ( lIndex < lEnd )
+ {
+ lCp = lCodepoints[lIndex];
+ if ( lCp == '?' || lCp == '#' )
+ break;
+
+ if ( lCp == '%' )
+ {
+ // TODO check errors
+ }
+ else if (!is_reservered_or_unreserved_char(lCp) && valid)
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( uri, ZED( BadUnicodeChar_3 ), lCp )
+ );
+ }
+ ++lIndex;
+ }
+ }
+
+ } // lStart < lEnd
+
+
+ thePath.clear();
+ utf8::append_codepoints(lCodepoints.begin() + lStart,
+ lCodepoints.begin() + lIndex,
+ &thePath);
+
+ set_state(Path);
+
+ // query - starts with ? and up to fragment or end
+ if ( lCp == '?' )
+ {
+ ++lIndex;
+ lStart = lIndex;
+ while ( lIndex < lEnd )
+ {
+ lCp = lCodepoints[lIndex];
+ if ( lCp == '#' )
+ break;
+
+ // TODO check conformance
+ ++lIndex;
+ } /* lIndex < lEnd */
+
+ theQueryString.clear();
+ utf8::append_codepoints(lCodepoints.begin() + lStart,
+ lCodepoints.begin() + lIndex,
+ &theQueryString);
+
+ set_state(QueryString);
+ }
+
+ // fragment - starts with #
+ if ( lCp == '#' )
+ {
+ ++lIndex;
+ lStart = lIndex;
+ while ( lIndex < lEnd )
+ {
+ lCp = lCodepoints[lIndex];
+ // TODO check conformance
+
+ ++lIndex;
+ } /* lIndex < lEnd */
+
+ if ( lIndex > lStart)
+ {
+ theFragment.clear();
+ utf8::append_codepoints(lCodepoints.begin() + lStart,
+ lCodepoints.begin() + lIndex,
+ &theFragment);
+ set_state(Fragment);
+ }
+ else
+ {
+ // fragment is not set
+ }
+ }
+
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_scheme(const zstring& new_scheme)
+{
+ if ( new_scheme.empty() )
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( "", ZED( NoURIScheme ) )
+ );
+ }
+
+ if ( ! is_conformant_scheme_name(new_scheme) )
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( "", ZED( BadURIScheme_3 ), new_scheme )
+ );
+ }
+
+ theScheme = new_scheme;
+ set_state(Scheme);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_host(const zstring& new_host)
+{
+ theHost = new_host;
+ set_state(Host);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_port(int new_port)
+{
+ thePort = new_port;
+ set_state(Port);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_user_info(const zstring& new_user_info)
+{
+ uri::encode(new_user_info, &theUserInfo, false);
+
+ set_state(UserInfo);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_reg_based_authority(const zstring& new_authority)
+{
+ if ( new_authority.empty() )
+ {
+ return;
+ }
+
+ // TODO check valid registry based authority
+
+ theRegBasedAuthority = new_authority;
+ set_state(RegBasedAuthority);
+
+ unset_state(Host);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::set_path(const zstring& new_path)
+{
+ if (new_path.empty())
+ {
+ thePath = new_path;
+ unset_state(Path);
+ theQueryString = new_path;
+ unset_state(QueryString);
+ theFragment = new_path;
+ unset_state(Fragment);
+ }
+ else
+ {
+ initializePath(new_path);
+ }
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::get_user_info(zstring& result) const
+{
+ uri::decode(theUserInfo, &result);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::get_reg_based_authority(zstring& result) const
+{
+ uri::decode(theRegBasedAuthority, &result);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::get_path(zstring& result) const
+{
+ uri::decode(thePath, &result);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::get_query(zstring& result) const
+{
+ uri::decode(theQueryString, &result);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::get_fragment(zstring& result) const
+{
+ uri::decode(theFragment, &result);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_absolute() const
+{
+ return is_set(Scheme) && !theScheme.empty();
+}
+
+bool URI::is_absolute_path(zstring &thePath)
+{
+#ifndef WIN32
+ return thePath[0] == '/';
+#else
+ return (thePath.length() > 2) &&
+ ((thePath[1] == ':') ||
+ ((thePath[1] == '%') && (thePath[2] == '3') && (thePath[3] == 'A')));
+#endif
+}
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::resolve(const URI* base_uri)
+{
+ if (is_absolute())
+ {
+ return;
+ }
+
+ if ( base_uri == 0 && toString().empty() )
+ {
+ throw XQUERY_EXCEPTION(
+ err::XQST0046, ERROR_PARAMS( "", ZED( ZeroLenURI ) )
+ );
+ }
+
+ if ( toString().empty() )
+ {
+ // just copy the base uri
+ initialize(*base_uri);
+ }
+
+ zstring::size_type lIndex = 0;
+
+ // If the path component is empty and the scheme, authority, and
+ // query components are undefined, then it is a reference to the
+ // current document and we are done. Otherwise, the reference URI's
+ // query and fragment components are defined as found (or not found)
+ // within the URI reference and not inherited from the base URI.
+ if ( ((!is_set(Path)) || (thePath.empty())) &&
+ (!is_set(Scheme) && (!is_set(Host)) && (!is_set(RegBasedAuthority)) ))
+ {
+ set_scheme(base_uri->get_scheme());
+
+ if (base_uri->is_set(UserInfo))
+ {
+ zstring userInfo;
+ base_uri->get_user_info(userInfo);
+ set_user_info(userInfo);
+ }
+
+ if (base_uri->is_set(Host))
+ {
+ set_host(base_uri->get_host());
+ }
+
+ if (base_uri->is_set(Port))
+ {
+ set_port(base_uri->get_port());
+ }
+
+ if (base_uri->is_set(RegBasedAuthority))
+ {
+ zstring auth;
+ base_uri->get_reg_based_authority(auth);
+ set_reg_based_authority(auth);
+ }
+
+ if (base_uri->is_set(Path))
+ {
+ // I think this is a bug in xerces because it doesn't remove the last segment
+ zstring path;
+ base_uri->get_path(path);
+
+ zstring::size_type last_slash = path.rfind("/");
+ if ( last_slash != zstring::npos )
+ thePath = path.substr(0, last_slash+1);
+ else
+ thePath = path;
+
+ set_state(Path);
+ }
+
+ if ( (! is_set(QueryString)) )
+ {
+ base_uri->get_query(theQueryString);
+
+ set_state(QueryString);
+ }
+
+ invalidate_text();
+
+ return;
+ }
+
+ // If the scheme component is defined, indicating that the reference
+ // starts with a scheme name, then the reference is interpreted as an
+ // absolute URI and we are done. Otherwise, the reference URI's
+ // scheme is inherited from the base URI's scheme component.
+ if ( is_set(Scheme) )
+ {
+ invalidate_text();
+ return;
+ }
+
+ set_scheme(base_uri->get_scheme());
+
+ // If the authority component is defined, then the reference is a
+ // network-path and we skip to step 7. Otherwise, the reference
+ // URI's authority is inherited from the base URI's authority
+ // component, which will also be undefined if the URI scheme does not
+ // use an authority component.
+ if ( (!is_set(Host)) && (!is_set(RegBasedAuthority)) )
+ {
+ if (base_uri->is_set(UserInfo))
+ {
+ base_uri->get_user_info(theUserInfo);
+ set_state(UserInfo);
+ }
+
+ if (base_uri->is_set(Host))
+ {
+ theHost = base_uri->get_host();
+ set_state(Host);
+ }
+
+ if (base_uri->is_set(Port))
+ {
+ thePort = base_uri->get_port();
+ set_state(Port);
+ }
+
+ if (base_uri->is_set(RegBasedAuthority))
+ {
+ base_uri->get_reg_based_authority(theRegBasedAuthority);
+ set_state(RegBasedAuthority);
+ }
+ }
+ else
+ {
+ invalidate_text();
+ return;
+ }
+
+
+ // If the path component begins with a slash character ("/"), then
+ // the reference is an absolute-path and we skip to step 7.
+ if ( is_set(Path) && is_absolute_path(thePath) )
+ {
+ invalidate_text();
+ return;
+ }
+
+ zstring base_path = base_uri->get_encoded_path();
+ zstring path;
+
+ if ( base_uri->is_set(Path) )
+ {
+ if(!is_absolute_path(thePath))
+ {
+ zstring::size_type last_slash = base_path.rfind("/");
+ if ( last_slash != zstring::npos )
+ path = base_path.substr(0, last_slash+1);
+ // else
+ // path = "/";
+ }
+ }
+
+ // 6b - append the relative URI path
+ path.append(thePath);
+
+ // 6c - remove all "./" where "." is a complete path segment
+ ascii::replace_all(path, "/./", 3, "/", 1);
+
+ // 6d If the buffer string ends with "." as a complete path segment,
+ // that "." is removed.
+ if (ascii::ends_with(path, "/.", 2))
+ {
+ path = path.substr(0, path.size() - 1);
+ }
+
+ // 6e All occurrences of "<segment>/../", where <segment> is a
+ // complete path segment not equal to "..", are removed from the
+ // buffer string. Removal of these path segments is performed
+ // iteratively, removing the leftmost matching pattern on each
+ // iteration, until no matching pattern remains.
+ zstring::size_type segIndex;
+ zstring::size_type offset = 1;
+
+ zstring_b tmp_path;
+ tmp_path.wrap_memory(const_cast<char*>(path.c_str() + 1), path.size() - 1);
+ zstring_b tmp1;
+ zstring_b tmp2;
+
+ while ((lIndex = tmp_path.find("/../")) != zstring::npos)
+ {
+ // Undo offset
+ lIndex += offset;
+
+ // Find start of <segment> within substring ending at found point.
+ tmp1.wrap_memory(path.c_str(), lIndex - 1);
+
+ segIndex = tmp1.rfind("/");
+
+ // Ensure <segment> exists and != ".."
+ if (segIndex != zstring::npos &&
+ (path[segIndex+1] != '.' ||
+ path[segIndex+2] != '.' ||
+ segIndex + 3 != lIndex))
+ {
+ tmp1.wrap_memory(path.c_str(), segIndex);
+ tmp2.wrap_memory(path.c_str() + lIndex + 3, path.size() - lIndex - 3);
+
+ zstring tmp;
+ tmp.reserve(tmp1.size() + tmp2.size());
+ tmp += tmp1;
+ tmp += tmp2;
+ path.swap(tmp);
+
+ offset = (segIndex == 0 ? 1 : segIndex);
+ }
+ else
+ {
+ offset += 4;
+ }
+
+ tmp_path.wrap_memory(path.c_str() + offset, path.size() - offset);
+ } // while
+
+ // 6f) If the buffer string ends with "<segment>/..", where <segment>
+ // is a complete path segment not equal to "..", that
+ // "<segment>/.." is removed.
+ if (ascii::ends_with(path, "/..", 3))
+ {
+ // Find start of <segment> within substring ending at found point.
+ lIndex = path.size() - 3;
+ tmp1.wrap_memory(path.c_str(), lIndex - 1);
+ segIndex = tmp1.rfind("/");
+
+ if (segIndex != zstring::npos &&
+ (path[segIndex+1] != '.' ||
+ path[segIndex+2] != '.' ||
+ segIndex + 3 != lIndex))
+ {
+ path = path.substr(0, segIndex+1);
+ }
+ }
+
+ thePath = path;
+ invalidate_text();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::relativize(const URI* base_uri)
+{
+ if ( base_uri == 0 || base_uri->toString().size() == 0)
+ return;
+
+ // if the scheme of the base_uri and the current uri are not identical,
+ // we return the current uri
+ if ( base_uri->get_scheme().compare(get_scheme()) != 0 )
+ {
+ return;
+ }
+
+ // if the authority of the base_uri and the current uri are not identical,
+ // we return the current uri
+ zstring auth;
+ zstring base_auth;
+ get_reg_based_authority(auth);
+ base_uri->get_reg_based_authority(base_auth);
+
+ if ( base_auth != auth )
+ {
+ return;
+ }
+
+ // if the path of the current uri is not a substring of the path of the base_uri,
+ // we return the current uri
+ zstring path;
+ zstring base_path;
+ get_path(path);
+ base_uri->get_path(base_path);
+
+ if ( path.find(base_path) != 0 )
+ {
+ return;
+ }
+
+ // construct a new relative hierarchical URI is constructed with query and
+ // fragment components taken from the given URI and with a path component
+ // computed by removing this URI's
+ // path from the beginning of the given URI's path.
+ zstring lNewPath = path.substr(base_path.size());
+ set_path(lNewPath);
+ // unset remaining stuff
+ theScheme.clear();
+ unset_state(Scheme);
+ theRegBasedAuthority.clear();
+ unset_state(RegBasedAuthority);
+ theUserInfo.clear();
+ unset_state(UserInfo);
+ thePort = 0;
+ unset_state(Port);
+ theHost.clear();
+ unset_state(Host);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+bool URI::is_conformant_scheme_name(const zstring& scheme)
+{
+#if 0
+ // start with a-zA-Z
+ if ( ! zorba::matches(scheme, "[a-zA-Z]", "" ) )
+ return false;
+#endif
+
+ for (ulong i = 0; i < scheme.size(); ++i)
+ {
+ char c = scheme[i];
+
+ if ( ! ascii::is_alpha(c) && c != '+' && c != '-' && c != '.')
+ {
+ return false;
+ }
+ }
+ return true;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+const zstring& URI::toString() const
+{
+ if (theURIText.empty())
+ {
+ build_full_text();
+ }
+ return theURIText;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+const zstring& URI::toPathNotation() const
+{
+ if (thePathNotation.empty())
+ {
+ build_path_notation();
+ }
+ return thePathNotation;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+const zstring& URI::toASCIIString() const
+{
+ if (theASCIIURIText.empty())
+ {
+ build_ascii_full_text();
+ }
+ return theASCIIURIText;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::build_path_notation() const
+{
+ std::ostringstream lPathNotation;
+
+ std::string lToTokenize;
+ if (is_set(Host))
+ {
+ lToTokenize = theHost.str();
+ }
+ else
+ {
+ lToTokenize = theRegBasedAuthority.str();
+ }
+
+ std::string::size_type lastPos =
+ lToTokenize.find_last_not_of(".", lToTokenize.length());
+
+ std::string::size_type pos = lToTokenize.find_last_of(".", lastPos);
+
+ if (pos == std::string::npos)
+ {
+ lPathNotation << lToTokenize;
+ }
+
+ while (std::string::npos != pos)
+ {
+ lPathNotation << lToTokenize.substr(pos + 1, lastPos - pos) << "/";
+
+ lastPos = pos - 1;
+ pos = lToTokenize.find_last_of(".", lastPos);
+ if (pos == std::string::npos)
+ {
+ lPathNotation << lToTokenize.substr(0, lastPos+1);
+ }
+ }
+
+ if (is_set(Path))
+ {
+ if(!thePath.empty() && (thePath[0] != '/') && (thePath[0] != '\\'))
+ lPathNotation << "/";
+ lPathNotation << thePath;
+ }
+
+ thePathNotation = lPathNotation.str();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::build_full_text() const
+{
+ std::ostringstream lURI;
+
+ // Scheme
+ if ( is_set(Scheme) )
+ lURI << theScheme << ":";
+
+ // Authority
+ if ( is_set(Host) || is_set(RegBasedAuthority) )
+ {
+ lURI << "//";
+ if ( is_set(Host) )
+ {
+ if ( is_set(UserInfo) )
+ lURI << theUserInfo << "@";
+
+ lURI << theHost;
+
+ if ( is_set(Port) )
+ lURI << ":" << thePort;
+ }
+ else
+ {
+ lURI << theRegBasedAuthority;
+ }
+ }
+
+ if ( is_set(Path) )
+ {
+ #ifdef WIN32
+ if(ZSTREQ(theScheme, "file") && !thePath.empty() && (thePath[0] != '/'))
+ lURI << "/";
+ #endif
+ lURI << thePath;
+ }
+
+ if ( is_set(QueryString) )
+ lURI << "?" << theQueryString;
+
+ if ( is_set(Fragment) )
+ lURI << "#" << theFragment;
+
+ theURIText = lURI.str();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void URI::build_ascii_full_text() const
+{
+ std::ostringstream lURI;
+
+ // Scheme
+ if ( is_set(Scheme) )
+ lURI << theScheme << ":";
+
+ // Authority
+ if ( is_set(Host) || is_set(RegBasedAuthority) )
+ {
+ lURI << "//";
+
+ if ( is_set(Host) )
+ {
+ if ( is_set(UserInfo) )
+ lURI << theUserInfo << "@";
+
+ lURI << theHost;
+
+ if ( is_set(Port) )
+ lURI << ":" << thePort;
+ }
+ else
+ {
+ lURI << theRegBasedAuthority;
+ }
+ }
+
+ if ( is_set(Path) )
+ {
+ #ifdef WIN32
+ if(ZSTREQ(theScheme, "file") && !thePath.empty() && (thePath[0] != '/'))
+ lURI << "/";
+ #endif
+ lURI << thePath;
+ }
+
+ if ( is_set(QueryString) )
+ lURI << "?" << theQueryString;
+
+ if ( is_set(Fragment) )
+ lURI << "#" << theFragment;
+
+ theASCIIURIText = lURI.str();
+}
+
+};
+/* vim:set et sw=2 ts=2: */
=== modified file 'src/zorbatypes/URI.h'
--- src/zorbatypes/URI.h 2011-06-14 17:26:33 +0000
+++ src/zorbatypes/URI.h 2011-09-22 11:09:58 +0000
@@ -1,279 +1,281 @@
-/*
- * Copyright 2006-2008 The FLWOR Foundation.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-#ifndef ZORBA_ZORBATYPES_URI_H
-#define ZORBA_ZORBATYPES_URI_H
-
-#include <iostream>
-
-#include <zorba/config.h>
-#include "schema_types.h"
-
-namespace zorba
-{
-
-class ZORBA_DLL_PUBLIC URI
-{
-public:
-
- static bool is_unreserved_char(uint32_t c);
-
- static bool is_path_character(uint32_t c);
-
- static bool is_reservered_or_unreserved_char(uint32_t c);
-
- static void decode_file_URI(const zstring& uri, zstring& filepath);
-
- static void encode_file_URI(const zstring& filepath, zstring& uri);
-
- static std::string encode_file_URI(const std::string& filepath);
-
- static bool is_well_formed_address(const char* addr, ulong length);
-
- static bool is_well_formed_ipv6_reference(const char* addr, ulong length);
-
- static bool is_well_formed_ipv4_address(const char* addr, ulong length);
-
- static long scanHexSequence(const char* addr, long idx, long end, long& counter);
-
-protected:
- enum States
- {
- Scheme = 1,
- UserInfo = 2,
- Host = 4,
- Port = 8,
- RegBasedAuthority = 16,
- Path = 32,
- QueryString = 64,
- Fragment = 128
- };
-
- // keep track whether particular components of a uri are defined or undefined
- mutable uint32_t theState;
-
- // the uri text is composed out of the components below it's mutable because
- // get_uri_text is const
- mutable zstring theURIText; // encoded
- mutable zstring theASCIIURIText; // decoded
- mutable zstring thePathNotation;
-
- // The uri components (UserInfo, RegBasedAuthority, Path, QueryString, and
- // Fragment are always encoded)
- zstring theScheme;
- zstring theHost;
- uint32_t thePort;
- zstring theUserInfo;
- zstring theRegBasedAuthority;
- zstring thePath;
- zstring theQueryString;
- zstring theFragment;
-
- // true if the constructed URI is valid
- bool valid;
-
-public:
- URI(const zstring& uri, bool validate = true);
-
- URI(const URI& base_uri, const zstring& uri, bool validate = true);
-
- URI (const URI& full_uri, const URI& base_uri);
-
- URI (const URI& to_copy);
-
- URI();
-
- ~URI();
-
- bool is_absolute() const;
-
- // get the full uri as text
- const zstring& toString() const;
-
- const zstring& toASCIIString() const;
-
- const zstring& toPathNotation() const;
-
- // getters and setters for each component
- bool is_valid() const;
-
- const zstring& get_scheme() const;
-
- void set_scheme(const zstring& new_scheme);
-
- const zstring& get_host() const;
-
- void set_host(const zstring& new_host);
-
- int get_port() const;
-
- void set_port(int new_port);
-
- void get_user_info(zstring& result) const;
-
- const zstring& get_encoded_user_info() const;
-
- void set_user_info(const zstring& new_user_info);
-
- void get_reg_based_authority(zstring& result) const;
-
- const zstring& get_encoded_reg_based_authority() const;
-
- void set_reg_based_authority(const zstring& new_authority);
-
- void get_path(zstring& result) const;
-
- const zstring& get_encoded_path() const;
-
- void set_path(const zstring& new_path);
-
- void get_query(zstring& result) const;
-
- const zstring& get_encoded_query() const;
-
- void set_query(const zstring& new_query_string);
-
- void get_fragment(zstring& result) const;
-
- const zstring& get_encoded_fragment() const;
-
- void set_fragment(const zstring& new_fragment);
-
- void clear_fragment();
-
-protected:
- void build_full_text() const;
-
- void build_ascii_full_text() const;
-
- void build_path_notation() const;
-
- void initialize(const URI& toCopy);
-
- void initialize(const zstring& uri, bool have_base = false);
-
- void initializeScheme(const zstring& uri);
-
- void initializeAuthority(const zstring& uri);
-
- void initializePath(const zstring& uri);
-
- bool is_conformant_scheme_name(const zstring& scheme);
-
- bool is_valid_server_based_authority(
- const zstring& host,
- const int port,
- const zstring& user_info,
- bool user_info_found);
-
- void resolve(const URI* base_uri);
-
- void relativize(const URI* base_uri);
-
- void set_state(uint32_t s) const { theState |= s; }
-
- bool is_set(uint32_t s) const { return ((theState & s) > 0); }
-
- void unset_state(uint32_t s) const { theState &= ~s; }
-
- void invalidate_text() const;
-};
-
-
-inline bool URI::is_valid() const
-{
- return valid;
-}
-
-
-inline const zstring& URI::get_scheme() const
-{
- return theScheme;
-}
-
-
-inline const zstring& URI::get_host() const
-{
- return theHost;
-}
-
-
-inline int URI::get_port() const
-{
- return thePort;
-}
-
-
-inline const zstring& URI::get_encoded_user_info() const
-{
- return theUserInfo;
-}
-
-
-inline const zstring& URI::get_encoded_reg_based_authority() const
-{
- return theRegBasedAuthority;
-}
-
-
-inline const zstring& URI::get_encoded_path() const
-{
- return thePath;
-}
-
-
-inline const zstring& URI::get_encoded_query() const
-{
- return theQueryString;
-}
-
-
-inline const zstring& URI::get_encoded_fragment() const
-{
- return theFragment;
-}
-
-inline void URI::set_fragment(const zstring &new_fragment)
-{
- theFragment = new_fragment;
- invalidate_text();
-}
-
-inline void URI::clear_fragment()
-{
- theFragment.clear();
- unset_state(Fragment);
- invalidate_text();
-}
-
-inline void URI::invalidate_text() const
-{
- theASCIIURIText.clear();
- theURIText.clear();
-}
-
-inline std::ostream& operator<<( std::ostream &o, URI const &uri ) {
- return o << uri.toString();
-}
-
-} // namespace zorba
-#endif /* ZORBA_ZORBATYPES_URI_H */
-/*
- * Local variables:
- * mode: c++
- * End:
- */
-/* vim:set et sw=2 ts=2: */
+/*
+ * Copyright 2006-2008 The FLWOR Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+#ifndef ZORBA_ZORBATYPES_URI_H
+#define ZORBA_ZORBATYPES_URI_H
+
+#include <iostream>
+
+#include <zorba/config.h>
+#include "schema_types.h"
+
+namespace zorba
+{
+
+class ZORBA_DLL_PUBLIC URI
+{
+public:
+
+ static bool is_unreserved_char(uint32_t c);
+
+ static bool is_path_character(uint32_t c);
+
+ static bool is_reservered_or_unreserved_char(uint32_t c);
+
+ static void decode_file_URI(const zstring& uri, zstring& filepath);
+
+ static void encode_file_URI(const zstring& filepath, zstring& uri);
+
+ static std::string encode_file_URI(const std::string& filepath);
+
+ static bool is_well_formed_address(const char* addr, ulong length);
+
+ static bool is_well_formed_ipv6_reference(const char* addr, ulong length);
+
+ static bool is_well_formed_ipv4_address(const char* addr, ulong length);
+
+ static long scanHexSequence(const char* addr, long idx, long end, long& counter);
+
+protected:
+ enum States
+ {
+ Scheme = 1,
+ UserInfo = 2,
+ Host = 4,
+ Port = 8,
+ RegBasedAuthority = 16,
+ Path = 32,
+ QueryString = 64,
+ Fragment = 128
+ };
+
+ // keep track whether particular components of a uri are defined or undefined
+ mutable uint32_t theState;
+
+ // the uri text is composed out of the components below it's mutable because
+ // get_uri_text is const
+ mutable zstring theURIText; // encoded
+ mutable zstring theASCIIURIText; // decoded
+ mutable zstring thePathNotation;
+
+ // The uri components (UserInfo, RegBasedAuthority, Path, QueryString, and
+ // Fragment are always encoded)
+ zstring theScheme;
+ zstring theHost;
+ uint32_t thePort;
+ zstring theUserInfo;
+ zstring theRegBasedAuthority;
+ zstring thePath;
+ zstring theQueryString;
+ zstring theFragment;
+
+ // true if the constructed URI is valid
+ bool valid;
+
+public:
+ URI(const zstring& uri, bool validate = true);
+
+ URI(const URI& base_uri, const zstring& uri, bool validate = true);
+
+ URI (const URI& full_uri, const URI& base_uri);
+
+ URI (const URI& to_copy);
+
+ URI();
+
+ ~URI();
+
+ bool is_absolute() const;
+
+ // get the full uri as text
+ const zstring& toString() const;
+
+ const zstring& toASCIIString() const;
+
+ const zstring& toPathNotation() const;
+
+ // getters and setters for each component
+ bool is_valid() const;
+
+ const zstring& get_scheme() const;
+
+ void set_scheme(const zstring& new_scheme);
+
+ const zstring& get_host() const;
+
+ void set_host(const zstring& new_host);
+
+ int get_port() const;
+
+ void set_port(int new_port);
+
+ void get_user_info(zstring& result) const;
+
+ const zstring& get_encoded_user_info() const;
+
+ void set_user_info(const zstring& new_user_info);
+
+ void get_reg_based_authority(zstring& result) const;
+
+ const zstring& get_encoded_reg_based_authority() const;
+
+ void set_reg_based_authority(const zstring& new_authority);
+
+ void get_path(zstring& result) const;
+
+ const zstring& get_encoded_path() const;
+
+ void set_path(const zstring& new_path);
+
+ void get_query(zstring& result) const;
+
+ const zstring& get_encoded_query() const;
+
+ void set_query(const zstring& new_query_string);
+
+ void get_fragment(zstring& result) const;
+
+ const zstring& get_encoded_fragment() const;
+
+ void set_fragment(const zstring& new_fragment);
+
+ void clear_fragment();
+
+protected:
+ void build_full_text() const;
+
+ void build_ascii_full_text() const;
+
+ void build_path_notation() const;
+
+ void initialize(const URI& toCopy);
+
+ void initialize(const zstring& uri, bool have_base = false);
+
+ void initializeScheme(const zstring& uri);
+
+ void initializeAuthority(const zstring& uri);
+
+ void initializePath(const zstring& uri);
+
+ bool is_conformant_scheme_name(const zstring& scheme);
+
+ bool is_valid_server_based_authority(
+ const zstring& host,
+ const int port,
+ const zstring& user_info,
+ bool user_info_found);
+
+ void resolve(const URI* base_uri);
+
+ void relativize(const URI* base_uri);
+
+ void set_state(uint32_t s) const { theState |= s; }
+
+ bool is_set(uint32_t s) const { return ((theState & s) > 0); }
+
+ void unset_state(uint32_t s) const { theState &= ~s; }
+
+ void invalidate_text() const;
+
+ bool is_absolute_path(zstring &thePath);
+};
+
+
+inline bool URI::is_valid() const
+{
+ return valid;
+}
+
+
+inline const zstring& URI::get_scheme() const
+{
+ return theScheme;
+}
+
+
+inline const zstring& URI::get_host() const
+{
+ return theHost;
+}
+
+
+inline int URI::get_port() const
+{
+ return thePort;
+}
+
+
+inline const zstring& URI::get_encoded_user_info() const
+{
+ return theUserInfo;
+}
+
+
+inline const zstring& URI::get_encoded_reg_based_authority() const
+{
+ return theRegBasedAuthority;
+}
+
+
+inline const zstring& URI::get_encoded_path() const
+{
+ return thePath;
+}
+
+
+inline const zstring& URI::get_encoded_query() const
+{
+ return theQueryString;
+}
+
+
+inline const zstring& URI::get_encoded_fragment() const
+{
+ return theFragment;
+}
+
+inline void URI::set_fragment(const zstring &new_fragment)
+{
+ theFragment = new_fragment;
+ invalidate_text();
+}
+
+inline void URI::clear_fragment()
+{
+ theFragment.clear();
+ unset_state(Fragment);
+ invalidate_text();
+}
+
+inline void URI::invalidate_text() const
+{
+ theASCIIURIText.clear();
+ theURIText.clear();
+}
+
+inline std::ostream& operator<<( std::ostream &o, URI const &uri ) {
+ return o << uri.toString();
+}
+
+} // namespace zorba
+#endif /* ZORBA_ZORBATYPES_URI_H */
+/*
+ * Local variables:
+ * mode: c++
+ * End:
+ */
+/* vim:set et sw=2 ts=2: */
=== modified file 'test/unit/CMakeLists.txt'
--- test/unit/CMakeLists.txt 2011-08-31 13:17:59 +0000
+++ test/unit/CMakeLists.txt 2011-09-22 11:09:58 +0000
@@ -1,121 +1,116 @@
-# Copyright 2006-2008 The FLWOR Foundation.#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-# create the testing file and list of tests
-
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/guestbook_main.xq ${CMAKE_CURRENT_BINARY_DIR}/guestbook_main.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/guestbook.xq ${CMAKE_CURRENT_BINARY_DIR}/guestbook.xq)
-
-#belongs to test external_function.cpp
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_mod.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_mod.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_main.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_main.xq)
-
-#belongs to test no_folding.cpp
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_mod1.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_mod1.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_mod2.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_mod2.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_main.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_main.xq)
-
-#belongs to test ext_in_opt.cpp
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt.xqlib ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt.xqlib)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt2.xqlib ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt2.xqlib)
-
-#belongs to test collection.cpp
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection1.xq ${CMAKE_CURRENT_BINARY_DIR}/collection1.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection2.xq ${CMAKE_CURRENT_BINARY_DIR}/collection2.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection1.xqlib ${CMAKE_CURRENT_BINARY_DIR}/collection1.xqlib)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection2.xqlib ${CMAKE_CURRENT_BINARY_DIR}/collection2.xqlib)
-
-#belongs to test main_sequential
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/main_sequential.xq ${CMAKE_CURRENT_BINARY_DIR}/main_sequential.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/main_sequential.xqlib ${CMAKE_CURRENT_BINARY_DIR}/main_sequential.xqlib)
-
-#belongs to streamable_string
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string_query_1.xq ${CMAKE_CURRENT_BINARY_DIR}/streamable_string_query_1.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string_query_2.xq ${CMAKE_CURRENT_BINARY_DIR}/streamable_string_query_2.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string.cpp ${CMAKE_CURRENT_BINARY_DIR}/streamable_string.cpp)
-
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module1.xq ${CMAKE_CURRENT_BINARY_DIR}/module1.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module2.xq ${CMAKE_CURRENT_BINARY_DIR}/module2.xq)
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module3.xq ${CMAKE_CURRENT_BINARY_DIR}/module3.xq)
-
-SET(UNIT_TESTS_SRCS
- path_resolver.cpp
- multiple_runs.cpp
- plan_serializer.cpp
- call_stack.cpp
- external_function.cpp
- no_folding.cpp
- ordpath_big.cpp
- uri_file_decoding_test.cpp
- ext_in_opt.cpp
- collection.cpp
- test_audit.cpp
- string_instantiate.cpp
- streamable_string.cpp
- string_test.cpp
- unique_ptr.cpp
- main_sequential.cpp
- datetime.cpp
- invoke.cpp
- xquery_functions.cpp
- xmldatamanager.cpp
- staticcollectionmanager.cpp
-)
-
-IF (NOT ZORBA_NO_FULL_TEXT)
- LIST(APPEND UNIT_TESTS_SRCS
- stemmer.cpp
- thesaurus.cpp
- tokenizer.cpp)
-ENDIF (NOT ZORBA_NO_FULL_TEXT)
-
-# multithread_simple.cpp
-# multithread_stress_test.cpp
-
-IF(ZORBA_WITH_DEBUGGER)
- LIST(APPEND SPEC_FILES "debug_iter_serialization.cpp")
-ENDIF(ZORBA_WITH_DEBUGGER)
-
-IF(WIN32)
- # SF#3191791
- LIST(REMOVE_ITEM UNIT_TESTS_SRCS "string_test.cpp")
-ENDIF(WIN32)
-
-CREATE_TEST_SOURCELIST(UnitTests
- UnitTests.cpp
- ${UNIT_TESTS_SRCS}
-)
-
-# add the executable
-ZORBA_GENERATE_EXE(UnitTests "${UnitTests}" "" "" "")
-
-# remove the test driver source file
-SET (TestsToRun ${UnitTests})
-REMOVE (TestsToRun UnitTests.cpp)
-
-MESSAGE(STATUS "Adding unit tests for CTest")
-
-# add all the ADD_TEST for each testing
-FOREACH (test ${TestsToRun})
- GET_FILENAME_COMPONENT(TName ${test} NAME_WE)
- SET (TestName "test/unit/${TName}")
- ZORBA_ADD_TEST(${TestName} UnitTests ${TName})
-ENDFOREACH(test)
-
-# Add lib-internal unit tests
-ZORBA_GENERATE_EXE(LibUnitTest lib_unit_test.cpp "" "" "")
-
-# ADD NEW UNIT TESTS HERE
-ZORBA_ADD_TEST("test/libunit/uri" LibUnitTest uri)
-EXPECTED_FAILURE(test/libunit/uri 3118348)
+# Copyright 2006-2008 The FLWOR Foundation.#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# create the testing file and list of tests
+
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/guestbook_main.xq ${CMAKE_CURRENT_BINARY_DIR}/guestbook_main.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/guestbook.xq ${CMAKE_CURRENT_BINARY_DIR}/guestbook.xq)
+
+#belongs to test external_function.cpp
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_mod.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_mod.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_main.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_main.xq)
+
+#belongs to test no_folding.cpp
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_mod1.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_mod1.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_mod2.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_mod2.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/fold_main.xq ${CMAKE_CURRENT_BINARY_DIR}/fold_main.xq)
+
+#belongs to test ext_in_opt.cpp
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt.xq ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt.xqlib ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt.xqlib)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/ext_in_opt2.xqlib ${CMAKE_CURRENT_BINARY_DIR}/ext_in_opt2.xqlib)
+
+#belongs to test collection.cpp
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection1.xq ${CMAKE_CURRENT_BINARY_DIR}/collection1.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection2.xq ${CMAKE_CURRENT_BINARY_DIR}/collection2.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection1.xqlib ${CMAKE_CURRENT_BINARY_DIR}/collection1.xqlib)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/collection2.xqlib ${CMAKE_CURRENT_BINARY_DIR}/collection2.xqlib)
+
+#belongs to test main_sequential
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/main_sequential.xq ${CMAKE_CURRENT_BINARY_DIR}/main_sequential.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/main_sequential.xqlib ${CMAKE_CURRENT_BINARY_DIR}/main_sequential.xqlib)
+
+#belongs to streamable_string
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string_query_1.xq ${CMAKE_CURRENT_BINARY_DIR}/streamable_string_query_1.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string_query_2.xq ${CMAKE_CURRENT_BINARY_DIR}/streamable_string_query_2.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/streamable_string.cpp ${CMAKE_CURRENT_BINARY_DIR}/streamable_string.cpp)
+
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module1.xq ${CMAKE_CURRENT_BINARY_DIR}/module1.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module2.xq ${CMAKE_CURRENT_BINARY_DIR}/module2.xq)
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/module3.xq ${CMAKE_CURRENT_BINARY_DIR}/module3.xq)
+
+SET(UNIT_TESTS_SRCS
+ path_resolver.cpp
+ multiple_runs.cpp
+ plan_serializer.cpp
+ call_stack.cpp
+ external_function.cpp
+ no_folding.cpp
+ ordpath_big.cpp
+ uri_file_decoding_test.cpp
+ ext_in_opt.cpp
+ collection.cpp
+ test_audit.cpp
+ string_instantiate.cpp
+ streamable_string.cpp
+ string_test.cpp
+ unique_ptr.cpp
+ main_sequential.cpp
+ datetime.cpp
+ invoke.cpp
+ xquery_functions.cpp
+ xmldatamanager.cpp
+ staticcollectionmanager.cpp
+)
+
+IF (NOT ZORBA_NO_FULL_TEXT)
+ LIST(APPEND UNIT_TESTS_SRCS
+ stemmer.cpp
+ thesaurus.cpp
+ tokenizer.cpp)
+ENDIF (NOT ZORBA_NO_FULL_TEXT)
+
+# multithread_simple.cpp
+# multithread_stress_test.cpp
+
+IF(ZORBA_WITH_DEBUGGER)
+ LIST(APPEND SPEC_FILES "debug_iter_serialization.cpp")
+ENDIF(ZORBA_WITH_DEBUGGER)
+
+CREATE_TEST_SOURCELIST(UnitTests
+ UnitTests.cpp
+ ${UNIT_TESTS_SRCS}
+)
+
+# add the executable
+ZORBA_GENERATE_EXE(UnitTests "${UnitTests}" "" "" "")
+
+# remove the test driver source file
+SET (TestsToRun ${UnitTests})
+REMOVE (TestsToRun UnitTests.cpp)
+
+MESSAGE(STATUS "Adding unit tests for CTest")
+
+# add all the ADD_TEST for each testing
+FOREACH (test ${TestsToRun})
+ GET_FILENAME_COMPONENT(TName ${test} NAME_WE)
+ SET (TestName "test/unit/${TName}")
+ ZORBA_ADD_TEST(${TestName} UnitTests ${TName})
+ENDFOREACH(test)
+
+# Add lib-internal unit tests
+ZORBA_GENERATE_EXE(LibUnitTest lib_unit_test.cpp "" "" "")
+
+# ADD NEW UNIT TESTS HERE
+ZORBA_ADD_TEST("test/libunit/uri" LibUnitTest uri)
+EXPECTED_FAILURE(test/libunit/uri 3118348)
Follow ups