leptris 1.9.418.1 → 1.9.419.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Rakefile +1 -1
- data/ext/leptris/native/native.c +38 -0
- data/lib/leptris/vendor/aarch64-linux/libleptris.so +0 -0
- data/lib/leptris/vendor/aarch64-linux-musl/libleptris.so +0 -0
- data/lib/leptris/vendor/arm-linux/libleptris.so +0 -0
- data/lib/leptris/vendor/arm-linux-musl/libleptris.so +0 -0
- data/lib/leptris/vendor/arm64-darwin/libleptris.dylib +0 -0
- data/lib/leptris/vendor/ppc64le-linux/libleptris.so +0 -0
- data/lib/leptris/vendor/s390x-linux-musl/libleptris.so +0 -0
- data/lib/leptris/vendor/x86_64-darwin/libleptris.dylib +0 -0
- data/lib/leptris/vendor/x86_64-linux/libleptris.so +0 -0
- data/lib/leptris/vendor/x86_64-linux-musl/libleptris.so +0 -0
- data/lib/leptris/version.rb +1 -1
- data/vendor-src/README.md +1 -1
- data/vendor-src/libleptris/CHANGELOG.md +13 -0
- data/vendor-src/libleptris/CMakeLists.txt +1 -1
- data/vendor-src/libleptris/TODO.max-perf/15-c-face-vs-pugixml.md +73 -0
- data/vendor-src/libleptris/src/leptris/xsd/compile.c +56 -30
- data/vendor-src/libleptris/src/leptris/xsd/validate.c +72 -0
- data/vendor-src/libleptris/src/leptris/xsd/xsd_internal.h +3 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a-11.xsd +16 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a.xml +1 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a.xsd +16 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014b.xml +1 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014b.xsd +16 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873.xsd +122 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873_imp.xsd +15 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873b.xml +3 -0
- data/vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873c.xml +3 -0
- data/vendor-src/libleptris/test/xsd/test_xsd_compile.cpp +95 -0
- data/vendor-src/libleptris/vcpkg.json +1 -1
- metadata +10 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: af2b87b2aaec36ee96f0572566b19678f06da068a2bd8fac00b086585a69dbd3
|
|
4
|
+
data.tar.gz: f0be350c456f6097e500488ade498cd5a14454461f3cb7476c79a19e5d4b8e30
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: edb18348f5b49be7967e570f50b88a5038d6b3525734a4f8f8e86929546663c53b1b73386168f089c040fe7757906ba9174144469d5f88af032a3103911ba7cb
|
|
7
|
+
data.tar.gz: 91d9cc505d079ade08cd8b0c68bcee95b5f7f26413dd5a7b753acf3707662634a17f03cb79d03b9d1bad33412fe3657eb7632ecaa79a93fa8d92975c1c5fbbd4
|
data/Rakefile
CHANGED
|
@@ -8,7 +8,7 @@ RSpec::Core::RakeTask.new(:spec)
|
|
|
8
8
|
# Pin for `rake compile` and the platform-gem builds. Keep in lockstep
|
|
9
9
|
# with .github/workflows/build.yml (which calls `rake compile`) and the
|
|
10
10
|
# CHANGELOG when libleptris releases.
|
|
11
|
-
LIBLEPTRIS_VERSION = "1.9.
|
|
11
|
+
LIBLEPTRIS_VERSION = "1.9.419"
|
|
12
12
|
# Vendored alongside libleptris for fn:normalize-unicode (TODO
|
|
13
13
|
# .restructure/20): built per platform with a RELOCATABLE @rpath
|
|
14
14
|
# install name, loaded by ffi.rb before libleptris so the
|
data/ext/leptris/native/native.c
CHANGED
|
@@ -1681,6 +1681,42 @@ static VALUE nn_set_root(VALUE klass, VALUE document, VALUE element)
|
|
|
1681
1681
|
return element;
|
|
1682
1682
|
}
|
|
1683
1683
|
|
|
1684
|
+
/* TODO.perf/39(a) (leptris-ruby#622 ask 1): hot readers
|
|
1685
|
+
* parameterized by subclass. Consumers whose wrapper classes SUBCLASS
|
|
1686
|
+
* NativeNode (klass injection, #340) shadow these C methods with
|
|
1687
|
+
* included Ruby modules — every shadowed read pays an
|
|
1688
|
+
* UnboundMethod#bind_call frame (~the whole difference between the
|
|
1689
|
+
* facade's ~331ns reads and the binding's ~160ns seam). This entry
|
|
1690
|
+
* defines the SAME C functions (same bodies, same walk-memos, same
|
|
1691
|
+
* TypedData type) DIRECTLY on the consumer's subclass, so lookup
|
|
1692
|
+
* answers in C with no module shadow in the chain.
|
|
1693
|
+
*
|
|
1694
|
+
* The consumer decides which classes get the hot surface: a
|
|
1695
|
+
* per-document klass map (#340) can route entity-bearing documents
|
|
1696
|
+
* to contract classes and clean documents to hot classes, keeping
|
|
1697
|
+
* any Ruby-side value post-processing exactly where it is still
|
|
1698
|
+
* needed.
|
|
1699
|
+
*
|
|
1700
|
+
* Re-defining a method that already exists on the class replaces it
|
|
1701
|
+
* (Ruby semantics); calling twice is harmless. The class must be the
|
|
1702
|
+
* consumer's NativeNode subclass or NativeNode itself — a non-
|
|
1703
|
+
* TypedData class would crash on first read, so the type is checked
|
|
1704
|
+
* here against the registry. */
|
|
1705
|
+
static VALUE nf_define_hot_readers(VALUE self, VALUE klass)
|
|
1706
|
+
{
|
|
1707
|
+
(void)self;
|
|
1708
|
+
if (!RB_TYPE_P(klass, T_CLASS))
|
|
1709
|
+
rb_raise(rb_eTypeError, "expected a class");
|
|
1710
|
+
if (klass != c_native_node &&
|
|
1711
|
+
rb_class_inherited_p(klass, c_native_node) != Qtrue)
|
|
1712
|
+
rb_raise(rb_eTypeError,
|
|
1713
|
+
"the class must subclass Leptris::XML::NativeNode");
|
|
1714
|
+
rb_define_method(klass, "name", nn_name, 0);
|
|
1715
|
+
rb_define_method(klass, "content", nn_content, 0);
|
|
1716
|
+
rb_define_method(klass, "attribute", nn_attribute, 1);
|
|
1717
|
+
return Qtrue;
|
|
1718
|
+
}
|
|
1719
|
+
|
|
1684
1720
|
/* NativeNode surface completion (TODO.perf/05): bulk attribute
|
|
1685
1721
|
* hash (name => value, one C walk, no per-attr Ruby frames) and
|
|
1686
1722
|
* the position readers. */
|
|
@@ -4350,6 +4386,8 @@ static void leptris_native_setup(void)
|
|
|
4350
4386
|
nf_append_binding_child, 3);
|
|
4351
4387
|
rb_define_module_function(m_native, "set_binding_attribute",
|
|
4352
4388
|
nf_set_binding_attribute, 4);
|
|
4389
|
+
rb_define_module_function(m_native, "define_hot_readers",
|
|
4390
|
+
nf_define_hot_readers, 1);
|
|
4353
4391
|
rb_define_module_function(m_native, "insert_binding_child",
|
|
4354
4392
|
nf_insert_binding_child, 4);
|
|
4355
4393
|
rb_define_module_function(m_native, "at_xpath_first",
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
data/lib/leptris/version.rb
CHANGED
data/vendor-src/README.md
CHANGED
|
@@ -1,5 +1,18 @@
|
|
|
1
1
|
## [Unreleased]
|
|
2
2
|
|
|
3
|
+
## [1.9.419] - 2026-11-12
|
|
4
|
+
### Fixed
|
|
5
|
+
|
|
6
|
+
- **xsd: wildcards ride attributeGroup refs across units** (leptris-rs#72, W3C wildZ013b/c). The #1964 deep capture left two holes: the extension branch still scanned shallow, so a wildcard living inside a REFERENCED attributeGroup under the extension element was invisible (strict admission rejected attributes the composed union admits); and a wildcard found in a group from ANOTHER unit (a namespace-less import) resolved against the CONSUMING schema's targetNamespace instead of its declaring unit's — `##other` flipped meaning across the boundary and the union collapsed to admitting only half the instance's attribute namespaces. The capture now follows refs in the extension branch and carries the declaring group's own unit tns (absent for the import).
|
|
7
|
+
|
|
8
|
+
- **xsd: a bare `<xs:anyAttribute />` is a live ##any wildcard** (leptris-rs#73, W3C attZ014a/b). Absent @namespace means ##any (the moxml#460 posture) — the capture mapped it to NULL, an invisible wildcard, so wildcard-admitted attributes fell to strict rejection for the wrong reason. With admission live, XSD 1.0's one-ID-per-element rule fires: an element assessed with more than one ID-typed attribute (declared rows AND wildcard-admitted names whose global declaration is ID-derived) is invalid; XSD 1.1 lifted the constraint and reads the same shape valid. The rule is version-gated (`xsd_schema_version_11`).
|
|
9
|
+
|
|
10
|
+
## Tests
|
|
11
|
+
|
|
12
|
+
- wildZ013b/c + attZ014a/b fixtures vendored from w3c/xsdtests (msData/wildcards, msData/attribute); attZ014a also pinned under `@version="1.1"` (valid). Falsified: an always-false ID test failed exactly the two 1.0 pins and passed the 1.1 reading.
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
3
16
|
## [1.9.418] - 2026-11-12
|
|
4
17
|
## Fixed
|
|
5
18
|
|
|
@@ -405,3 +405,76 @@ the loop-body surgery slice — it inherits the region-wrap probe
|
|
|
405
405
|
|
|
406
406
|
RANKED CUT #1 therefore moves to the loop-surgery slice with the
|
|
407
407
|
scan-merge as its first step. Nothing ships from the kernel alone.
|
|
408
|
+
|
|
409
|
+
## Track D addendum 9 — the inline text-scan cut REJECTED by CI (PR #2018, closed)
|
|
410
|
+
|
|
411
|
+
The ranked-#1 cut (inline 32-byte scalar prefix scan for short text
|
|
412
|
+
runs, kernel for the remainder) went through the full gate: round 1
|
|
413
|
+
caught the restart-at-run-start flaw (the kernel rescanned the
|
|
414
|
+
scalar prefix — every leg regressed), round 2 fixed that (kernel
|
|
415
|
+
from the prefix end) and STILL regressed on all three legs vs the
|
|
416
|
+
A3d baselines (macos -39-46%, ubuntu-arm -26-27%, ubuntu-x86 -37-45%
|
|
417
|
+
vs its AVX2 run). Cause: the bench-class run lengths (33-64B) sit
|
|
418
|
+
exactly where the cut loses — 32 branchy scalar bytes plus a kernel
|
|
419
|
+
pass over a 1-32B remainder exceeds the kernel alone, and runs
|
|
420
|
+
<=32B are too few in these shapes to carry it.
|
|
421
|
+
|
|
422
|
+
THE MISSING DATUM: the run-length distribution of the real fixtures
|
|
423
|
+
and the scoreboard corpus. The next session's opening instrument =
|
|
424
|
+
a run-length histogram (one counting pass per fixture, reusable),
|
|
425
|
+
which decides whether the scan-merge has a paying window at all —
|
|
426
|
+
and at what threshold. Until then the kernel stands unchanged; the
|
|
427
|
+
PR closed with the full data (three legs, two rounds, CI artifacts).
|
|
428
|
+
|
|
429
|
+
## Track D addendum 10 — the scan-merge slice CLOSED (PR #2020, closed unmerged)
|
|
430
|
+
|
|
431
|
+
The 64-byte window (histogram-driven) went through the full gate and
|
|
432
|
+
regressed WORSE than the 32-byte attempt: macos -45/-39/-46%, arm
|
|
433
|
+
-32/-32/-29%, x86 -53/-53/-50% (vs the AVX2 run) — even for runs
|
|
434
|
+
fully inside the window. THE VERDICT: the branchy scalar loop
|
|
435
|
+
(~3-5 ops/byte) loses to the SIMD kernel (~1 op/byte) at every run
|
|
436
|
+
length on every platform; the kernel's per-run fixed cost is small
|
|
437
|
+
next to its per-byte advantage. The scan-merge slice is structurally
|
|
438
|
+
dead — two windows, two full CI runs, one consistent verdict.
|
|
439
|
+
|
|
440
|
+
THE TEXT-ROW LEVER REDIRECTS to the kernel's own per-byte
|
|
441
|
+
throughput: the text_scan_run NEON kernel processes ~1 byte/op
|
|
442
|
+
while pugixml's scanner sustains 2.1-2.7 GB/s — the Track A scanner
|
|
443
|
+
class. The next concrete candidate: process 32B chunks (NEON
|
|
444
|
+
registers ×2) per iteration instead of 16B, halving the reduction
|
|
445
|
+
frequency; and the parser's text-branch call overhead already
|
|
446
|
+
measures separably (the scalar wrapper at 2.2%).
|
|
447
|
+
|
|
448
|
+
The histogram instrument (probe/run-histogram) remains in the repo
|
|
449
|
+
history on probe/run-histogram; both rejected cut branches carry
|
|
450
|
+
their full data.
|
|
451
|
+
|
|
452
|
+
## Track D addendum 11 — the 32B kernel window measured-NEGATIVE (PR #2022, closed unmerged)
|
|
453
|
+
|
|
454
|
+
The addendum-10 candidate (NEON text_scan_run at 32B windows — two
|
|
455
|
+
uint8x16 registers, term masks OR-combined before ONE vmaxvq, halving
|
|
456
|
+
the horizontal-reduction frequency) passed the full CI suite but the
|
|
457
|
+
CI split was poisoned by fleet variance (x86 +31% on code the diff
|
|
458
|
+
does not touch). The decisive instrument was a same-machine
|
|
459
|
+
interleaved A/B on Apple silicon (Release+LTO, 3 rounds ABBA, pugixml
|
|
460
|
+
side flat ~2370/1800 MB/s across rounds — machine verified stable):
|
|
461
|
+
|
|
462
|
+
| shape | 16B (main) | 32B (PR) | delta |
|
|
463
|
+
|-------|-----------|----------|-------|
|
|
464
|
+
| 1.5MB | ~1341 MB/s | ~1144 MB/s | −15% |
|
|
465
|
+
| 5MB | ~1332 MB/s | ~1135 MB/s | −15% |
|
|
466
|
+
| 13MB | ~1029 MB/s | ~913 MB/s | −11% |
|
|
467
|
+
|
|
468
|
+
THE INVARIANT: horizontal-reduction frequency is NOT the binding term
|
|
469
|
+
in text_scan_run on M-series. The accumulator chain is — two extra
|
|
470
|
+
cmpeq+orr per register per window lengthen the dependency chain and
|
|
471
|
+
raise live-register pressure (9+ Q registers) without removing any
|
|
472
|
+
real per-byte work. Widening the window cannot pay; the kernel's
|
|
473
|
+
per-byte op count is already minimal for its contract (first-term
|
|
474
|
+
scan + f1/f2 seen-flags).
|
|
475
|
+
|
|
476
|
+
TEXT-ROW STATUS after three measured closures (scan-merge 32B,
|
|
477
|
+
scan-merge 64B, kernel-width 32B): the kernel is at its floor. The
|
|
478
|
+
remaining text-row gap to pugixml is the parser's text-branch call
|
|
479
|
+
overhead (the scalar wrapper measures separably at 2.2% — the only
|
|
480
|
+
untried lever in this class), not the kernel.
|
|
@@ -128,9 +128,9 @@ static char* xsd_capture_unit_tns(LeptrisElement e);
|
|
|
128
128
|
static void xsd_resolve_qname(LeptrisElement e, const char* qname,
|
|
129
129
|
char* uri, size_t urisz, char* local,
|
|
130
130
|
size_t localsz);
|
|
131
|
-
static char* xsd_capture_any_attr_ns(LeptrisElement container);
|
|
132
131
|
static char* xsd_capture_any_attr_ns_deep(
|
|
133
|
-
struct leptris_xsd_schema* s, LeptrisElement container, int depth
|
|
132
|
+
struct leptris_xsd_schema* s, LeptrisElement container, int depth,
|
|
133
|
+
char** out_unit);
|
|
134
134
|
static char* xsd_capture_any_attr_not_qname(LeptrisElement container);
|
|
135
135
|
|
|
136
136
|
/* #1626: prefixed QName refs (type="w:CT_Border") resolve by local
|
|
@@ -3257,13 +3257,26 @@ static XsdCm* xsd_capture_complex_model(struct leptris_xsd_schema* s,
|
|
|
3257
3257
|
/* XSD 1.1: asserts nested under the derivation */
|
|
3258
3258
|
if (s->version_11)
|
|
3259
3259
|
xsd_capture_assert_children(s, dq, root);
|
|
3260
|
-
if (!any_attr_ns)
|
|
3260
|
+
if (!any_attr_ns) {
|
|
3261
3261
|
if (!any_attr_unit_ns)
|
|
3262
3262
|
any_attr_unit_ns = xsd_capture_unit_tns(dq);
|
|
3263
|
-
|
|
3263
|
+
/* leptris-rs#72: the extension's wildcard rides
|
|
3264
|
+
* attributeGroup refs too — the shallow scan
|
|
3265
|
+
* misses attgD019/wildZ013 shapes. Cross-unit
|
|
3266
|
+
* found-groups carry their own tns. */
|
|
3267
|
+
char* deep_unit = NULL;
|
|
3268
|
+
any_attr_ns = xsd_capture_any_attr_ns_deep(
|
|
3269
|
+
s, dq, 0, &deep_unit);
|
|
3270
|
+
if (any_attr_ns && deep_unit) {
|
|
3271
|
+
free(any_attr_unit_ns);
|
|
3272
|
+
any_attr_unit_ns = deep_unit;
|
|
3273
|
+
} else {
|
|
3274
|
+
free(deep_unit);
|
|
3275
|
+
}
|
|
3264
3276
|
if (!any_attr_not_qname)
|
|
3265
3277
|
any_attr_not_qname =
|
|
3266
3278
|
xsd_capture_any_attr_not_qname(dq);
|
|
3279
|
+
}
|
|
3267
3280
|
}
|
|
3268
3281
|
} else if (strcmp(local, "simpleContent") == 0) {
|
|
3269
3282
|
for (LeptrisNodeRef q = leptris_node_first_child(
|
|
@@ -3344,8 +3357,19 @@ static XsdCm* xsd_capture_complex_model(struct leptris_xsd_schema* s,
|
|
|
3344
3357
|
if (!attrs) attrs = xsd_capture_attr_rows(s, ct, 0);
|
|
3345
3358
|
if (!any_attr_unit_ns)
|
|
3346
3359
|
any_attr_unit_ns = xsd_capture_unit_tns(ct);
|
|
3347
|
-
if (!any_attr_ns)
|
|
3348
|
-
|
|
3360
|
+
if (!any_attr_ns) {
|
|
3361
|
+
char* deep_unit = NULL;
|
|
3362
|
+
any_attr_ns = xsd_capture_any_attr_ns_deep(s, ct, 0,
|
|
3363
|
+
&deep_unit);
|
|
3364
|
+
if (any_attr_ns && deep_unit) {
|
|
3365
|
+
/* the wildcard lives in a REFERENCED group from
|
|
3366
|
+
* another unit — its declaring tns wins */
|
|
3367
|
+
free(any_attr_unit_ns);
|
|
3368
|
+
any_attr_unit_ns = deep_unit;
|
|
3369
|
+
} else {
|
|
3370
|
+
free(deep_unit);
|
|
3371
|
+
}
|
|
3372
|
+
}
|
|
3349
3373
|
if (!any_attr_not_qname)
|
|
3350
3374
|
any_attr_not_qname = xsd_capture_any_attr_not_qname(ct);
|
|
3351
3375
|
}
|
|
@@ -3455,7 +3479,9 @@ XsdGroupDef* xsd_find_group(struct leptris_xsd_schema* s,
|
|
|
3455
3479
|
return NULL;
|
|
3456
3480
|
}
|
|
3457
3481
|
|
|
3458
|
-
|
|
3482
|
+
/* leptris-rs#73: the global attribute declaration for a local name
|
|
3483
|
+
* (the ID-count pass resolves wildcard-admitted names against it). */
|
|
3484
|
+
const XsdAttrDecl* xsd_find_top_attr(
|
|
3459
3485
|
struct leptris_xsd_schema* s, const char* name) {
|
|
3460
3486
|
if (!s || !name) return NULL;
|
|
3461
3487
|
for (XsdAttrDecl* a = s->top_attrs; a; a = a->next)
|
|
@@ -3686,7 +3712,7 @@ static char* xsd_capture_unit_tns(LeptrisElement e) {
|
|
|
3686
3712
|
* (depth-bounded); the group's OWN element is the walk root. */
|
|
3687
3713
|
static char* xsd_capture_any_attr_ns_deep(
|
|
3688
3714
|
struct leptris_xsd_schema* s, LeptrisElement container,
|
|
3689
|
-
int depth) {
|
|
3715
|
+
int depth, char** out_unit) {
|
|
3690
3716
|
if (depth > 8) return NULL;
|
|
3691
3717
|
for (LeptrisNodeRef ac = leptris_node_first_child(
|
|
3692
3718
|
leptris_element_as_node(container));
|
|
@@ -3697,9 +3723,14 @@ static char* xsd_capture_any_attr_ns_deep(
|
|
|
3697
3723
|
const char* al = NULL, *au = NULL;
|
|
3698
3724
|
leptris_element_expanded_name(ae, &al, NULL, &au);
|
|
3699
3725
|
if (!al || (au && strcmp(au, XSD_NS) != 0)) continue;
|
|
3700
|
-
if (strcmp(al, "anyAttribute") == 0)
|
|
3701
|
-
|
|
3702
|
-
|
|
3726
|
+
if (strcmp(al, "anyAttribute") == 0) {
|
|
3727
|
+
/* leptris-rs#73: absent @namespace means ##any — a
|
|
3728
|
+
* bare <xs:anyAttribute /> is a live wildcard, not an
|
|
3729
|
+
* invisible one. */
|
|
3730
|
+
const char* ns =
|
|
3731
|
+
leptris_element_attribute(ae, "namespace");
|
|
3732
|
+
return xsd_strdup(ns ? ns : "##any");
|
|
3733
|
+
}
|
|
3703
3734
|
if (strcmp(al, "attributeGroup") == 0) {
|
|
3704
3735
|
const char* ref = xsd_local_name(
|
|
3705
3736
|
leptris_element_attribute(ae, "ref"));
|
|
@@ -3708,31 +3739,26 @@ static char* xsd_capture_any_attr_ns_deep(
|
|
|
3708
3739
|
for (; g; g = g->next)
|
|
3709
3740
|
if (strcmp(g->name, ref) == 0) break;
|
|
3710
3741
|
if (g && g->elem) {
|
|
3711
|
-
char*
|
|
3712
|
-
|
|
3713
|
-
|
|
3742
|
+
char* inner_unit = NULL;
|
|
3743
|
+
char* r = xsd_capture_any_attr_ns_deep(
|
|
3744
|
+
s, g->elem, depth + 1, &inner_unit);
|
|
3745
|
+
if (r) {
|
|
3746
|
+
/* leptris-rs#72: the wildcard resolves against
|
|
3747
|
+
* its DECLARING unit's tns — the group's own
|
|
3748
|
+
* unit ("" for a namespace-less import), which
|
|
3749
|
+
* may differ from the consuming type's. */
|
|
3750
|
+
if (out_unit)
|
|
3751
|
+
*out_unit = inner_unit
|
|
3752
|
+
? inner_unit
|
|
3753
|
+
: xsd_capture_unit_tns(g->elem);
|
|
3754
|
+
return r;
|
|
3755
|
+
}
|
|
3714
3756
|
}
|
|
3715
3757
|
}
|
|
3716
3758
|
}
|
|
3717
3759
|
return NULL;
|
|
3718
3760
|
}
|
|
3719
3761
|
|
|
3720
|
-
static char* xsd_capture_any_attr_ns(LeptrisElement container) {
|
|
3721
|
-
for (LeptrisNodeRef ac = leptris_node_first_child(
|
|
3722
|
-
leptris_element_as_node(container));
|
|
3723
|
-
ac; ac = leptris_node_next_sibling(ac)) {
|
|
3724
|
-
if (leptris_node_get_type(ac) != LEPTRIS_NODE_TYPE_ELEMENT)
|
|
3725
|
-
continue;
|
|
3726
|
-
LeptrisElement ae = (LeptrisElement)ac;
|
|
3727
|
-
const char* al = NULL;
|
|
3728
|
-
leptris_element_expanded_name(ae, &al, NULL, NULL);
|
|
3729
|
-
if (al && strcmp(al, "anyAttribute") == 0)
|
|
3730
|
-
return xsd_strdup(
|
|
3731
|
-
leptris_element_attribute(ae, "namespace"));
|
|
3732
|
-
}
|
|
3733
|
-
return NULL;
|
|
3734
|
-
}
|
|
3735
|
-
|
|
3736
3762
|
/* moxml#460: the anyAttribute's XSD 1.1 @notQName (same walk as the
|
|
3737
3763
|
* namespace capture). NULL when absent. */
|
|
3738
3764
|
static char* xsd_capture_any_attr_not_qname(LeptrisElement container) {
|
|
@@ -832,6 +832,11 @@ static int attr_fixed_matches(struct leptris_xsd_schema* s,
|
|
|
832
832
|
return strcmp(norm_v, norm_f) == 0;
|
|
833
833
|
}
|
|
834
834
|
|
|
835
|
+
/* leptris-rs#73: xs:ID itself or a user simpleType whose restriction
|
|
836
|
+
* chain roots at xs:ID. */
|
|
837
|
+
static int attr_type_is_id(struct leptris_xsd_schema* s,
|
|
838
|
+
const char* type);
|
|
839
|
+
|
|
835
840
|
static void validate_attributes(struct xsd_validator* v,
|
|
836
841
|
struct leptris_xsd_schema* s,
|
|
837
842
|
LeptrisElement elem,
|
|
@@ -962,6 +967,73 @@ static void validate_attributes(struct xsd_validator* v,
|
|
|
962
967
|
verrf_atk(v, elem, "attribute-use", local, "attribute", local,
|
|
963
968
|
"not declared (strict)");
|
|
964
969
|
}
|
|
970
|
+
/* leptris-rs#73 (W3C attZ014, XSD 1.0): an element assessed with
|
|
971
|
+
* more than one ID-typed attribute is invalid — declared rows
|
|
972
|
+
* AND wildcard-admitted attributes whose GLOBAL declaration is
|
|
973
|
+
* ID-derived both count. 1.1 lifted the constraint. */
|
|
974
|
+
if (!xsd_schema_version_11(s)) {
|
|
975
|
+
int id_count = 0;
|
|
976
|
+
for (XsdAttrDecl* a = ta->attrs; a; a = a->next)
|
|
977
|
+
if (attr_type_is_id(s, a->type)) id_count++;
|
|
978
|
+
for (LeptrisAttribute at = leptris_element_first_attribute(elem);
|
|
979
|
+
at && id_count < 2; at = leptris_attribute_next(at)) {
|
|
980
|
+
const char* qn = leptris_attribute_get_name(at);
|
|
981
|
+
if (!qn || strncmp(qn, "xmlns", 5) == 0) continue;
|
|
982
|
+
const char* colon = strchr(qn, ':');
|
|
983
|
+
const char* local = colon ? colon + 1 : qn;
|
|
984
|
+
int declared = 0;
|
|
985
|
+
for (XsdAttrDecl* a = ta->attrs; a && !declared; a = a->next)
|
|
986
|
+
if (strcmp(a->name, local) == 0 ||
|
|
987
|
+
strcmp(a->name, qn) == 0)
|
|
988
|
+
declared = 1;
|
|
989
|
+
if (declared) continue;
|
|
990
|
+
const char* auri = leptris_attribute_namespace_uri(at);
|
|
991
|
+
if (auri && strcmp(auri,
|
|
992
|
+
"http://www.w3.org/2001/XMLSchema-instance")
|
|
993
|
+
== 0)
|
|
994
|
+
continue;
|
|
995
|
+
if (ta->any_attr_not_qname &&
|
|
996
|
+
attr_not_qname_hits(ta->any_attr_not_qname, s, local))
|
|
997
|
+
continue;
|
|
998
|
+
int admitted =
|
|
999
|
+
((ta->any_attr_ns || ta->any_attr_not_qname) &&
|
|
1000
|
+
any_attr_matches(ta->any_attr_ns, auri,
|
|
1001
|
+
ta->any_attr_unit_ns
|
|
1002
|
+
? ta->any_attr_unit_ns
|
|
1003
|
+
: xsd_target_ns(s))) ||
|
|
1004
|
+
(ta->any_attr_base_ns &&
|
|
1005
|
+
any_attr_matches(ta->any_attr_base_ns, auri,
|
|
1006
|
+
ta->any_attr_base_unit_ns
|
|
1007
|
+
? ta->any_attr_base_unit_ns
|
|
1008
|
+
: xsd_target_ns(s)));
|
|
1009
|
+
if (!admitted) continue;
|
|
1010
|
+
const XsdAttrDecl* g =
|
|
1011
|
+
xsd_find_top_attr(s, local);
|
|
1012
|
+
if (g && attr_type_is_id(s, g->type)) id_count++;
|
|
1013
|
+
}
|
|
1014
|
+
if (id_count > 1)
|
|
1015
|
+
verrf_atk(v, elem, "attribute-use", "ID", "attribute",
|
|
1016
|
+
"ID",
|
|
1017
|
+
"more than one ID-typed attribute (XSD 1.0 "
|
|
1018
|
+
"one-ID-per-element)");
|
|
1019
|
+
}
|
|
1020
|
+
}
|
|
1021
|
+
|
|
1022
|
+
/* leptris-rs#73: xs:ID itself or a user simpleType whose restriction
|
|
1023
|
+
* chain roots at xs:ID. */
|
|
1024
|
+
static int attr_type_is_id(struct leptris_xsd_schema* s,
|
|
1025
|
+
const char* type) {
|
|
1026
|
+
if (!type) return 0;
|
|
1027
|
+
if (strcmp(type, "xs:ID") == 0 || strcmp(type, "xsd:ID") == 0)
|
|
1028
|
+
return 1;
|
|
1029
|
+
const XsdSimple* st = xsd_find_simple_ns_pub(s, type, NULL);
|
|
1030
|
+
for (int hops = 0; st && st->base && hops < 8; hops++) {
|
|
1031
|
+
if (strcmp(st->base, "xs:ID") == 0 ||
|
|
1032
|
+
strcmp(st->base, "xsd:ID") == 0)
|
|
1033
|
+
return 1;
|
|
1034
|
+
st = xsd_find_simple_pub(s, st->base);
|
|
1035
|
+
}
|
|
1036
|
+
return 0;
|
|
965
1037
|
}
|
|
966
1038
|
|
|
967
1039
|
static void validate_element(struct xsd_validator* v,
|
|
@@ -87,6 +87,9 @@ int xsd_element_name_defined(struct leptris_xsd_schema* s,
|
|
|
87
87
|
const char* local, const char* uri);
|
|
88
88
|
int xsd_attr_name_defined(struct leptris_xsd_schema* s,
|
|
89
89
|
const char* local);
|
|
90
|
+
struct xsd_attr_decl;
|
|
91
|
+
const struct xsd_attr_decl* xsd_find_top_attr(
|
|
92
|
+
struct leptris_xsd_schema* s, const char* local);
|
|
90
93
|
|
|
91
94
|
/* One validation finding (slice 4). text is malloc'd; kind and
|
|
92
95
|
* component are BORROWED (static names / schema-owned component
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
<xsd:schema version="1.1" elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
|
|
2
|
+
<xsd:complexType name="base">
|
|
3
|
+
<xsd:attribute name="att1" type="xsd:string"/>
|
|
4
|
+
<xsd:attribute name="att2" type="xsd:string"/>
|
|
5
|
+
<xsd:anyAttribute />
|
|
6
|
+
</xsd:complexType>
|
|
7
|
+
|
|
8
|
+
<xsd:simpleType name="st">
|
|
9
|
+
<xsd:restriction base="xsd:ID"/>
|
|
10
|
+
</xsd:simpleType>
|
|
11
|
+
|
|
12
|
+
<xsd:element name="doc" type="base" />
|
|
13
|
+
|
|
14
|
+
<xsd:attribute name="a" type="xsd:ID"/>
|
|
15
|
+
<xsd:attribute name="b" type="st"/>
|
|
16
|
+
</xsd:schema>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<doc att1="a" att2="a" a="a" b="b"/>
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
|
|
2
|
+
<xsd:complexType name="base">
|
|
3
|
+
<xsd:attribute name="att1" type="xsd:string"/>
|
|
4
|
+
<xsd:attribute name="att2" type="xsd:string"/>
|
|
5
|
+
<xsd:anyAttribute />
|
|
6
|
+
</xsd:complexType>
|
|
7
|
+
|
|
8
|
+
<xsd:simpleType name="st">
|
|
9
|
+
<xsd:restriction base="xsd:ID"/>
|
|
10
|
+
</xsd:simpleType>
|
|
11
|
+
|
|
12
|
+
<xsd:element name="doc" type="base" />
|
|
13
|
+
|
|
14
|
+
<xsd:attribute name="a" type="xsd:ID"/>
|
|
15
|
+
<xsd:attribute name="b" type="st"/>
|
|
16
|
+
</xsd:schema>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
<doc att1="a" att2="a" b="b"/>
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
<xsd:schema elementFormDefault="qualified" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
|
|
2
|
+
<xsd:complexType name="base">
|
|
3
|
+
<xsd:attribute name="att1" type="xsd:string"/>
|
|
4
|
+
<xsd:attribute name="att2" type="xsd:ID"/>
|
|
5
|
+
<xsd:anyAttribute />
|
|
6
|
+
</xsd:complexType>
|
|
7
|
+
|
|
8
|
+
<xsd:simpleType name="st">
|
|
9
|
+
<xsd:restriction base="xsd:ID"/>
|
|
10
|
+
</xsd:simpleType>
|
|
11
|
+
|
|
12
|
+
<xsd:element name="doc" type="base" />
|
|
13
|
+
|
|
14
|
+
<xsd:attribute name="a" type="xsd:ID"/>
|
|
15
|
+
<xsd:attribute name="b" type="st"/>
|
|
16
|
+
</xsd:schema>
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
<xs:schema elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema" targetNamespace="a" xmlns:a="a" xmlns:b="b">
|
|
2
|
+
<xs:import schemaLocation="test328873_imp.xsd"/>
|
|
3
|
+
|
|
4
|
+
<xs:element name="doc" type="a:derived"/>
|
|
5
|
+
<xs:element name="sub" type="a:derived2" />
|
|
6
|
+
<xs:element name="sub2" type="a:derived3" />
|
|
7
|
+
<xs:element name="sub3" type="a:derived4" />
|
|
8
|
+
<xs:element name="sub4" type="a:derived5" />
|
|
9
|
+
<xs:element name="sub5" type="a:intersection1" />
|
|
10
|
+
<xs:element name="sub6" type="a:intersection2" />
|
|
11
|
+
<xs:complexType name="base">
|
|
12
|
+
<xs:sequence>
|
|
13
|
+
<xs:element name="sub" type="a:derived2" minOccurs="0"/>
|
|
14
|
+
<xs:element name="sub2" type="a:derived3" minOccurs="0"/>
|
|
15
|
+
<xs:element name="sub3" type="a:derived4" minOccurs="0"/>
|
|
16
|
+
<xs:element name="sub4" type="a:derived5" minOccurs="0"/>
|
|
17
|
+
<xs:element name="sub5" type="a:intersection1" minOccurs="0"/>
|
|
18
|
+
<xs:element name="sub6" type="a:intersection2" minOccurs="0"/>
|
|
19
|
+
</xs:sequence>
|
|
20
|
+
<xs:attributeGroup ref="a:attG-a1"/>
|
|
21
|
+
</xs:complexType>
|
|
22
|
+
|
|
23
|
+
<xs:complexType name="derived">
|
|
24
|
+
<xs:complexContent>
|
|
25
|
+
<xs:extension base="a:base">
|
|
26
|
+
<xs:sequence />
|
|
27
|
+
<xs:attributeGroup ref="a:attG-a2"/>
|
|
28
|
+
</xs:extension>
|
|
29
|
+
</xs:complexContent>
|
|
30
|
+
</xs:complexType>
|
|
31
|
+
|
|
32
|
+
<xs:complexType name="base2">
|
|
33
|
+
<xs:sequence />
|
|
34
|
+
<xs:attributeGroup ref="a:attG1-54"/>
|
|
35
|
+
</xs:complexType>
|
|
36
|
+
|
|
37
|
+
<xs:complexType name="derived2">
|
|
38
|
+
<xs:complexContent>
|
|
39
|
+
<xs:extension base="a:base2">
|
|
40
|
+
<xs:sequence />
|
|
41
|
+
<xs:attributeGroup ref="a:attG2-54"/>
|
|
42
|
+
</xs:extension>
|
|
43
|
+
</xs:complexContent>
|
|
44
|
+
</xs:complexType>
|
|
45
|
+
|
|
46
|
+
<xs:complexType name="base3">
|
|
47
|
+
<xs:sequence />
|
|
48
|
+
<xs:attributeGroup ref="a:attG1-51"/>
|
|
49
|
+
</xs:complexType>
|
|
50
|
+
|
|
51
|
+
<xs:complexType name="derived3">
|
|
52
|
+
<xs:complexContent>
|
|
53
|
+
<xs:extension base="a:base3">
|
|
54
|
+
<xs:sequence />
|
|
55
|
+
<xs:attributeGroup ref="a:attG2-51"/>
|
|
56
|
+
</xs:extension>
|
|
57
|
+
</xs:complexContent>
|
|
58
|
+
</xs:complexType>
|
|
59
|
+
|
|
60
|
+
<xs:complexType name="base4">
|
|
61
|
+
<xs:sequence />
|
|
62
|
+
<xs:attributeGroup ref="attG1-61"/>
|
|
63
|
+
</xs:complexType>
|
|
64
|
+
|
|
65
|
+
<xs:complexType name="derived4">
|
|
66
|
+
<xs:complexContent>
|
|
67
|
+
<xs:extension base="a:base4">
|
|
68
|
+
<xs:sequence />
|
|
69
|
+
<xs:attributeGroup ref="attG2-61"/> <!-- resultant wildcard is any -->
|
|
70
|
+
</xs:extension>
|
|
71
|
+
</xs:complexContent>
|
|
72
|
+
</xs:complexType>
|
|
73
|
+
|
|
74
|
+
<xs:complexType name="derived5">
|
|
75
|
+
<xs:complexContent>
|
|
76
|
+
<xs:extension base="a:base4">
|
|
77
|
+
<xs:sequence />
|
|
78
|
+
<xs:attributeGroup ref="attG3-61"/> <!-- resultant wildcard is not(absent) -->
|
|
79
|
+
</xs:extension>
|
|
80
|
+
</xs:complexContent>
|
|
81
|
+
</xs:complexType>
|
|
82
|
+
|
|
83
|
+
<xs:complexType name="intersection1">
|
|
84
|
+
<xs:attributeGroup ref="a:attG-a1"/>
|
|
85
|
+
<xs:attributeGroup ref="a:attG2-3"/> <!-- resultant wildcard is set(b, c) -->
|
|
86
|
+
</xs:complexType>
|
|
87
|
+
|
|
88
|
+
<xs:complexType name="intersection2">
|
|
89
|
+
<xs:attributeGroup ref="a:attG-a1"/>
|
|
90
|
+
<xs:attributeGroup ref="attG1-61"/> <!-- resultant wildcard is not(a) -->
|
|
91
|
+
</xs:complexType>
|
|
92
|
+
|
|
93
|
+
<xs:attribute name="attA"/>
|
|
94
|
+
<xs:attributeGroup name="attG-a1">
|
|
95
|
+
<xs:anyAttribute namespace="##other" processContents="lax"/>
|
|
96
|
+
</xs:attributeGroup>
|
|
97
|
+
|
|
98
|
+
<xs:attributeGroup name="attG2-3">
|
|
99
|
+
<xs:anyAttribute namespace="##local b c" processContents="lax"/>
|
|
100
|
+
</xs:attributeGroup>
|
|
101
|
+
|
|
102
|
+
<xs:attributeGroup name="attG-a2">
|
|
103
|
+
<xs:anyAttribute namespace="##targetNamespace b c" processContents="lax"/>
|
|
104
|
+
</xs:attributeGroup>
|
|
105
|
+
|
|
106
|
+
<xs:attributeGroup name="attG1-54">
|
|
107
|
+
<xs:anyAttribute namespace="##other" processContents="lax"/>
|
|
108
|
+
</xs:attributeGroup>
|
|
109
|
+
|
|
110
|
+
<xs:attributeGroup name="attG2-54">
|
|
111
|
+
<xs:anyAttribute namespace="b c" processContents="lax"/>
|
|
112
|
+
</xs:attributeGroup>
|
|
113
|
+
|
|
114
|
+
<xs:attributeGroup name="attG1-51">
|
|
115
|
+
<xs:anyAttribute namespace="##other" processContents="lax"/>
|
|
116
|
+
</xs:attributeGroup>
|
|
117
|
+
|
|
118
|
+
<xs:attributeGroup name="attG2-51">
|
|
119
|
+
<xs:anyAttribute namespace="##targetNamespace ##local b c" processContents="lax"/>
|
|
120
|
+
</xs:attributeGroup>
|
|
121
|
+
|
|
122
|
+
</xs:schema>
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
<xs:schema elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
|
|
2
|
+
|
|
3
|
+
<xs:attributeGroup name="attG1-61">
|
|
4
|
+
<xs:anyAttribute namespace="##other" processContents="lax"/> <!-- not(absent) -->
|
|
5
|
+
</xs:attributeGroup>
|
|
6
|
+
|
|
7
|
+
<xs:attributeGroup name="attG2-61">
|
|
8
|
+
<xs:anyAttribute namespace="##local b c" processContents="lax"/>
|
|
9
|
+
</xs:attributeGroup>
|
|
10
|
+
|
|
11
|
+
<xs:attributeGroup name="attG3-61">
|
|
12
|
+
<xs:anyAttribute namespace="b c" processContents="lax"/>
|
|
13
|
+
</xs:attributeGroup>
|
|
14
|
+
|
|
15
|
+
</xs:schema>
|
|
@@ -1331,6 +1331,101 @@ TEST(XsdValidate, SchG2RoundtripUnitAAlone) {
|
|
|
1331
1331
|
leptris_xsd_free(s);
|
|
1332
1332
|
}
|
|
1333
1333
|
|
|
1334
|
+
// leptris-rs#72 (W3C wildZ013b, msData/wildcards, expected VALID):
|
|
1335
|
+
// the extension's wildcard lives inside a REFERENCED attributeGroup
|
|
1336
|
+
// (attG2-51 under the extension element) — the deep capture must
|
|
1337
|
+
// ride group refs in the extension branch too. The composed union
|
|
1338
|
+
// (base ##other ∪ extension ##targetNamespace ##local b c) admits
|
|
1339
|
+
// all five instance attribute namespaces.
|
|
1340
|
+
TEST(XsdValidate, WildZ013bExtensionGroupRefWildcardValid) {
|
|
1341
|
+
LeptrisStatus st = LEPTRIS_OK;
|
|
1342
|
+
LeptrisXsdSchema s = leptris_xsd_compile_file(
|
|
1343
|
+
LEPTRIS_XSD_CASES_DIR "/wildZ013-set/test328873.xsd", &st);
|
|
1344
|
+
ASSERT_NE(s, (LeptrisXsdSchema)0) << "status " << (int)st;
|
|
1345
|
+
LeptrisDocument d = leptris_parse_file(
|
|
1346
|
+
LEPTRIS_XSD_CASES_DIR "/wildZ013-set/test328873b.xml", &st);
|
|
1347
|
+
ASSERT_NE(d, nullptr) << "status " << (int)st;
|
|
1348
|
+
EXPECT_EQ(leptris_xsd_validate(s, d), 1)
|
|
1349
|
+
<< leptris_xsd_error_at(s, 0);
|
|
1350
|
+
for (size_t i = 0; i < leptris_xsd_error_count(s); i++)
|
|
1351
|
+
ADD_FAILURE() << leptris_xsd_error_at(s, i);
|
|
1352
|
+
leptris_document_free(d);
|
|
1353
|
+
leptris_xsd_free(s);
|
|
1354
|
+
}
|
|
1355
|
+
|
|
1356
|
+
// leptris-rs#72 (W3C wildZ013c): BOTH wildcards live in the
|
|
1357
|
+
// namespace-less IMPORT (attG1-61/attG2-61). Each resolves against
|
|
1358
|
+
// its DECLARING unit's tns (absent), not the consuming schema's —
|
|
1359
|
+
// ##other@absent ∪ {absent, b, c}@absent = ##any.
|
|
1360
|
+
TEST(XsdValidate, WildZ013cCrossUnitImportUnionValid) {
|
|
1361
|
+
LeptrisStatus st = LEPTRIS_OK;
|
|
1362
|
+
LeptrisXsdSchema s = leptris_xsd_compile_file(
|
|
1363
|
+
LEPTRIS_XSD_CASES_DIR "/wildZ013-set/test328873.xsd", &st);
|
|
1364
|
+
ASSERT_NE(s, (LeptrisXsdSchema)0) << "status " << (int)st;
|
|
1365
|
+
LeptrisDocument d = leptris_parse_file(
|
|
1366
|
+
LEPTRIS_XSD_CASES_DIR "/wildZ013-set/test328873c.xml", &st);
|
|
1367
|
+
ASSERT_NE(d, nullptr) << "status " << (int)st;
|
|
1368
|
+
EXPECT_EQ(leptris_xsd_validate(s, d), 1)
|
|
1369
|
+
<< leptris_xsd_error_at(s, 0);
|
|
1370
|
+
for (size_t i = 0; i < leptris_xsd_error_count(s); i++)
|
|
1371
|
+
ADD_FAILURE() << leptris_xsd_error_at(s, i);
|
|
1372
|
+
leptris_document_free(d);
|
|
1373
|
+
leptris_xsd_free(s);
|
|
1374
|
+
}
|
|
1375
|
+
|
|
1376
|
+
// leptris-rs#73 (W3C attZ014a, version-contested): <xs:anyAttribute />
|
|
1377
|
+
// without @namespace is a LIVE ##any (absent @namespace means ##any,
|
|
1378
|
+
// the moxml#460 posture) — a and b admit through it and resolve
|
|
1379
|
+
// against their global ID-typed declarations. XSD 1.0's
|
|
1380
|
+
// one-ID-per-element rule then makes the instance INVALID (two
|
|
1381
|
+
// ID-typed attributes on one element); XSD 1.1 lifted the rule.
|
|
1382
|
+
TEST(XsdValidate, AttZ014aIdCountInvalid10) {
|
|
1383
|
+
LeptrisStatus st = LEPTRIS_OK;
|
|
1384
|
+
LeptrisXsdSchema s = leptris_xsd_compile_file(
|
|
1385
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014a.xsd", &st);
|
|
1386
|
+
ASSERT_NE(s, (LeptrisXsdSchema)0) << "status " << (int)st;
|
|
1387
|
+
LeptrisDocument d = leptris_parse_file(
|
|
1388
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014a.xml", &st);
|
|
1389
|
+
ASSERT_NE(d, nullptr) << "status " << (int)st;
|
|
1390
|
+
EXPECT_EQ(leptris_xsd_validate(s, d), 0);
|
|
1391
|
+
leptris_document_free(d);
|
|
1392
|
+
leptris_xsd_free(s);
|
|
1393
|
+
}
|
|
1394
|
+
|
|
1395
|
+
// leptris-rs#73 (attZ014b): the declared att2 row is xs:ID and the
|
|
1396
|
+
// wildcard-admitted b resolves to a global restriction of xs:ID —
|
|
1397
|
+
// still two ID-typed attributes on the element. INVALID in 1.0.
|
|
1398
|
+
TEST(XsdValidate, AttZ014bDeclaredAndAdmittedIdInvalid10) {
|
|
1399
|
+
LeptrisStatus st = LEPTRIS_OK;
|
|
1400
|
+
LeptrisXsdSchema s = leptris_xsd_compile_file(
|
|
1401
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014b.xsd", &st);
|
|
1402
|
+
ASSERT_NE(s, (LeptrisXsdSchema)0) << "status " << (int)st;
|
|
1403
|
+
LeptrisDocument d = leptris_parse_file(
|
|
1404
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014b.xml", &st);
|
|
1405
|
+
ASSERT_NE(d, nullptr) << "status " << (int)st;
|
|
1406
|
+
EXPECT_EQ(leptris_xsd_validate(s, d), 0);
|
|
1407
|
+
leptris_document_free(d);
|
|
1408
|
+
leptris_xsd_free(s);
|
|
1409
|
+
}
|
|
1410
|
+
|
|
1411
|
+
// leptris-rs#73 (1.1 reading): the same shape under @version="1.1"
|
|
1412
|
+
// is VALID — 1.1 lifted the one-ID-per-element constraint.
|
|
1413
|
+
TEST(XsdValidate, AttZ014aVersion11ReadingIsValid) {
|
|
1414
|
+
LeptrisStatus st = LEPTRIS_OK;
|
|
1415
|
+
LeptrisXsdSchema s = leptris_xsd_compile_file(
|
|
1416
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014a-11.xsd", &st);
|
|
1417
|
+
ASSERT_NE(s, (LeptrisXsdSchema)0) << "status " << (int)st;
|
|
1418
|
+
LeptrisDocument d = leptris_parse_file(
|
|
1419
|
+
LEPTRIS_XSD_CASES_DIR "/attZ014-set/attZ014a.xml", &st);
|
|
1420
|
+
ASSERT_NE(d, nullptr) << "status " << (int)st;
|
|
1421
|
+
EXPECT_EQ(leptris_xsd_validate(s, d), 1)
|
|
1422
|
+
<< leptris_xsd_error_at(s, 0);
|
|
1423
|
+
for (size_t i = 0; i < leptris_xsd_error_count(s); i++)
|
|
1424
|
+
ADD_FAILURE() << leptris_xsd_error_at(s, i);
|
|
1425
|
+
leptris_document_free(d);
|
|
1426
|
+
leptris_xsd_free(s);
|
|
1427
|
+
}
|
|
1428
|
+
|
|
1334
1429
|
TEST(XsdValidate, ValidDocumentPasses) {
|
|
1335
1430
|
EXPECT_EQ(validate_doc(k_v_schema,
|
|
1336
1431
|
"<rows version=\"2\" status=\"ok\">"
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"$schema": "https://raw.githubusercontent.com/microsoft/vcpkg/master/scripts/vcpkg.schema.json",
|
|
3
3
|
"name": "leptris",
|
|
4
|
-
"version": "1.9.
|
|
4
|
+
"version": "1.9.419",
|
|
5
5
|
"description": "High-performance XML parser and XPath 1.0 engine in C (libleptris)",
|
|
6
6
|
"homepage": "https://github.com/leptris/leptris",
|
|
7
7
|
"license": "MIT",
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: leptris
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.9.
|
|
4
|
+
version: 1.9.419.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Ribose Inc.
|
|
@@ -1285,6 +1285,11 @@ files:
|
|
|
1285
1285
|
- vendor-src/libleptris/test/xsd/libxml2-cases/anyAttr.importB.1_0.xsd
|
|
1286
1286
|
- vendor-src/libleptris/test/xsd/libxml2-cases/anyAttr1_0.xml
|
|
1287
1287
|
- vendor-src/libleptris/test/xsd/libxml2-cases/anyAttr1_0.xsd
|
|
1288
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a-11.xsd
|
|
1289
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a.xml
|
|
1290
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014a.xsd
|
|
1291
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014b.xml
|
|
1292
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/attZ014-set/attZ014b.xsd
|
|
1288
1293
|
- vendor-src/libleptris/test/xsd/libxml2-cases/attgD019-set/attgD019.xsd
|
|
1289
1294
|
- vendor-src/libleptris/test/xsd/libxml2-cases/attgD019-set/attgD019a.xsd
|
|
1290
1295
|
- vendor-src/libleptris/test/xsd/libxml2-cases/attr0_0.xml
|
|
@@ -1630,6 +1635,10 @@ files:
|
|
|
1630
1635
|
- vendor-src/libleptris/test/xsd/libxml2-cases/vdv-first5_0.xml
|
|
1631
1636
|
- vendor-src/libleptris/test/xsd/libxml2-cases/vdv-first5_0.xsd
|
|
1632
1637
|
- vendor-src/libleptris/test/xsd/libxml2-cases/vdv-simpleTypes.xsd
|
|
1638
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873.xsd
|
|
1639
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873_imp.xsd
|
|
1640
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873b.xml
|
|
1641
|
+
- vendor-src/libleptris/test/xsd/libxml2-cases/wildZ013-set/test328873c.xml
|
|
1633
1642
|
- vendor-src/libleptris/test/xsd/libxml2-cases/xml.xsd
|
|
1634
1643
|
- vendor-src/libleptris/test/xsd/libxml2-cases/xns_type_refs/main.xsd
|
|
1635
1644
|
- vendor-src/libleptris/test/xsd/libxml2-cases/xns_type_refs/root.xsd
|