[ 
https://issues.apache.org/jira/browse/DAFFODIL-2550?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17413311#comment-17413311
 ] 

Steve Lawrence edited comment on DAFFODIL-2550 at 9/10/21, 5:55 PM:
--------------------------------------------------------------------

Okay, did some more digging. Here's the smallest example that I can reproduce 
this with.
{code:xml}
  <xs:element name="root1">
    <xs:complexType>
      <xs:sequence>
        <xs:group ref="ex:group1" />
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:element name="root2">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="a">
          <xs:complexType>
            <xs:group ref="ex:group2" />
          </xs:complexType>
        </xs:element>
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:group name="group1">
    <xs:sequence>
      <xs:element name="b">
        <xs:complexType>
          <xs:sequence>
            <xs:element name="c">
              <xs:complexType>
                <xs:group ref="ex:group2" />
              </xs:complexType>
            </xs:element>
          </xs:sequence>
        </xs:complexType>
      </xs:element>
    </xs:sequence>
  </xs:group>

  <xs:group name="group2">
    <xs:sequence>
      <xs:element name="d" type="xs:string" />
    </xs:sequence>
  </xs:group>
{code}

Let's say we are parsing root1. So we have two global elements defs, but root2 
is "dead code". But note that both global elements defs share group2. Based on 
my understanding of the issue, I think the nested groups shouldn't be needed, 
but this is partially dependent on ordering somehow, so things need to be very 
precise to trigger that ordering.

The issue occurs when Daffodil tries to figure out the minimized scope of the 
"d" element. Note that the "d" element has two enclosing elements depending on 
context--either element "a" or element "c". When calculating minimized scope 
(or really myParentNSPairs/parentMinimizedScope), Daffodil doesn't take into 
account where the parent based on the root element (I"m not sure if even can). 
So it just currently calls this (note the comment) 
{code:scala}
val ee = enclosingElements.headOption // FIXME: DAFFODIL-2282 works only if 
there is no difference among usages.
{code}
So it just picks the first enclosingElement, with the assumption that they 
should be the same. In our case, they should be the same--elements "a" and "c" 
have the same namespace, so which one we pick shouldn't matter.

If headOption results in element "a", then we ask it about its scope. But in 
order for "a" to give us an answer about its scope, it needs to know about its 
parents scope. So "a" asks about its enclosingElements. And this is where we 
hit the issue mentioned above. The enclosing elements of "a" returns an empty 
list because there is no Term/Element enclosing element "a". Only a 
GlobalElementDecl with no associated ElementRef/Term. This messes up the 
calculation of minimized scope, since that requires having accurate 
enclosingElement information. Had we instead picked element "c", we would have 
found are way all the way up to root1, found the Root/ElementRef/Term for 
root1, and figured things out correctly.

Note that if I remove elements "b" and "c" to simplify the schema some, I don't 
see this issue. But I think this is because the ordering of enclosingElements. 
If I change the headOption to tailOption when accessing enclosingElements, then 
we do get the "a" element, and it results in the issue.


was (Author: slawrence):
Okay, did some more digging. Here's the smallest example that I can reproduce 
this with.
{code:xml}
  <xs:element name="root1">
    <xs:complexType>
      <xs:sequence>
        <xs:group ref="ex:group1" />
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:element name="root2">
    <xs:complexType>
      <xs:sequence>
        <xs:element name="a">
          <xs:complexType>
            <xs:group ref="ex:group2" />
          </xs:complexType>
        </xs:element>
      </xs:sequence>
    </xs:complexType>
  </xs:element>

  <xs:group name="group1">
    <xs:sequence>
      <xs:element name="b">
        <xs:complexType>
          <xs:sequence>
            <xs:element name="c">
              <xs:complexType>
                <xs:group ref="ex:group2" />
              </xs:complexType>
            </xs:element>
          </xs:sequence>
        </xs:complexType>
      </xs:element>
    </xs:sequence>
  </xs:group>

  <xs:group name="group2">
    <xs:sequence>
      <xs:element name="d" type="xs:string" />
    </xs:sequence>
  </xs:group>
{code}

Let's say we are parsing root1. So we have two global group defs, but root2 is 
"dead code". But note that both global group defs share group2. Based on my 
understanding of the issue, I think the nested groups shouldn't be needed, but 
this is partially dependent on ordering somehow, so things need to be very 
precise to trigger that ordering.

The issue occurs when Daffodil tries to figure out the minimized scope of the 
"d" element. Note that the "d" element has two enclosing elements depending on 
context--either element "a" or element "c". When calculating minimized scope 
(or really myParentNSPairs/parentMinimizedScope), Daffodil doesn't take into 
account where the parent based on the root element (I"m not sure if even can). 
So it just currently calls this (note the comment) 
{code:scala}
val ee = enclosingElements.headOption // FIXME: DAFFODIL-2282 works only if 
there is no difference among usages.
{code}
So it just picks the first enclosingElement, with the assumption that they 
should be the same. In our case, they should be the same--elements "a" and "c" 
have the same namespace, so which one we pick shouldn't matter.

If headOption results in element "a", then we ask it about its scope. But in 
order for "a" to give us an answer about its scope, it needs to know about its 
parents scope. So "a" asks about its enclosingElements. And this is where we 
hit the issue mentioned above. The enclosing elements of "a" returns an empty 
list because there is no Term/Element enclosing element "a". Only a 
GlobalElementDecl with no associated ElementRef/Term. This messes up the 
calculation of minimized scope, since that requires having accurate 
enclosingElement information. Had we instead picked element "c", we would have 
found are way all the way up to root1, found the Root/ElementRef/Term for 
root1, and figured things out correctly.

Note that if I remove elements "b" and "c" to simplify the schema some, I don't 
see this issue. But I think this is because the ordering of enclosingElements. 
If I change the headOption to tailOption when accessing enclosingElements, then 
we do get the "a" element, and it results in the issue.

> xmlns="" not minimized away in two CLI tests.
> ---------------------------------------------
>
>                 Key: DAFFODIL-2550
>                 URL: https://issues.apache.org/jira/browse/DAFFODIL-2550
>             Project: Daffodil
>          Issue Type: Bug
>          Components: Middle &quot;End&quot;
>    Affects Versions: 3.2.0
>            Reporter: Mike Beckerle
>            Assignee: Steve Lawrence
>            Priority: Major
>
> Changes in [https://github.com/apache/daffodil/pull/600] clean up things a 
> lot, but there is one mystery change in behavior.
> Two CLI tests now add an xmlns="" to an inner locally-declared element which 
> has a unqualified name. 
> This seems like incorrect namespace binding minimization, possibly. 
> Rather than hold up the merge of PR 600 (which is a big change set, so needs 
> to be merged real soon now) this ticket is to investigate this issue of the 
> two CLI tests and the xmlns="" that seems unnecessary. 
> Note that we've suspected there could be bugs in namespace binding 
> minimization for a while now. 
> The two CLI tests are:
> * test_CLI_Debugger_InfoHidden_1
> * test_CLI_Debugger_InfoHidden_2
>  
>  
>  
>  



--
This message was sent by Atlassian Jira
(v8.3.4#803005)

Reply via email to