Saxon seems to use only a single index for multiple keys
This isn't something I've been able to duplicate in anything but the original stylesheet, so I'm attaching the stylesheet, Main.xsl, along with its dependencies and an input file that shows the issue.
There's a bunch of indirect stuff happening via table lookups and function dispatch in this stylesheet, but when I try to replicate everything in a smaller stylesheet, everything seems to work correctly.
The specific issue here is that while there are a number of keys defined, when it hits the key-with-fallback function defined on line 2098, instead of using the specified table (which is coming from a table lookup itself), it seems to only use the key for coverage-option-codes-list, so in the output you get
<LegalEntityCd>Incl</LegalEntityCd> on line 15, when it should be "IN", and same for BillingMethodCd on line 25 ("P" instead of "CPB"), etc. This only seems to happen in Saxon 9.9, and in Saxon 9.8, we get the correct lookup values returned.
My initial workaround was to use saxon:key-map() and add saxon:range-key="yes" to the key declarations. This causes the correct behavior in Saxon 126.96.36.199 but in Saxon 188.8.131.52, it raises an internal error.
With the attached version of the stylesheet, I've also tried to use xsl:message to check the values of the variables, params, and the result of the call to key() in the key-with-fallback function, but as soon as I do this, everything works properly.
I haven't been able to isolate a specific trigger for this, unfortunately, but I was thinking some kind of caching issue was happening, and on the mailing list you mentioned that the behavior points to an issue happening during optimization. I haven't had the opportunity to try with and without optimization, however.
#1 Updated by Michael Kay about 1 year ago
- Category set to XSLT conformance
- Assignee set to Michael Kay
- Priority changed from Low to Normal
I have confirmed that 9.9 and 9.8 give different results, and that 10.0 gives the same result as 9.9.
Understanding what's going on will take a little longer...
#3 Updated by Michael Kay about 1 year ago
System functions that maintain information on behalf of a specific caller are supposed to implement the interface
StatefulSystemFunction, and to have a copy() method that copies this information when the calling expression is copied (which can happen during function inlining etc). Without this copy, two different inlinings of the same system function on behalf of different callers will not have separate copies of this information.
KeyFn maintains such information (it does a static lookup of the key name in the common case where it is supplied as a string literal), but it does not implement
StatefulSystemFunction and does not have a
Please register to edit this issue