// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#include "xfa/fxfa/parser/xfa_script_resolveprocessor.h"

#include "core/fxcrt/include/fx_ext.h"
#include "xfa/fxfa/fm2js/xfa_fm2jsapi.h"
#include "xfa/fxfa/parser/xfa_docdata.h"
#include "xfa/fxfa/parser/xfa_doclayout.h"
#include "xfa/fxfa/parser/xfa_document.h"
#include "xfa/fxfa/parser/xfa_localemgr.h"
#include "xfa/fxfa/parser/xfa_object.h"
#include "xfa/fxfa/parser/xfa_parser.h"
#include "xfa/fxfa/parser/xfa_script.h"
#include "xfa/fxfa/parser/xfa_script_imp.h"
#include "xfa/fxfa/parser/xfa_script_nodehelper.h"
#include "xfa/fxfa/parser/xfa_utils.h"

CXFA_ResolveProcessor::CXFA_ResolveProcessor(void)
    : m_pNodeHelper(NULL), m_iCurStart(0) {
  m_pNodeHelper = new CXFA_NodeHelper;
}
CXFA_ResolveProcessor::~CXFA_ResolveProcessor(void) {
  if (m_pNodeHelper) {
    delete m_pNodeHelper;
    m_pNodeHelper = NULL;
  }
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes(CXFA_ResolveNodesData& rnd) {
  if (rnd.m_CurNode == NULL) {
    return -1;
  }
  if (!rnd.m_CurNode->IsNode()) {
    if (rnd.m_dwStyles & XFA_RESOLVENODE_Attributes) {
      return XFA_ResolveNodes_ForAttributeRs(rnd.m_CurNode, rnd, rnd.m_wsName);
    }
    return 0;
  }
  if (rnd.m_dwStyles & XFA_RESOLVENODE_AnyChild) {
    return XFA_ResolveNodes_AnyChild(rnd);
  }
  FX_WCHAR wch = rnd.m_wsName.GetAt(0);
  switch (wch) {
    case '$':
      return XFA_ResolveNodes_Dollar(rnd);
    case '!':
      return XFA_ResolveNodes_Excalmatory(rnd);
    case '#':
      return XFA_ResolveNodes_NumberSign(rnd);
    case '*':
      return XFA_ResolveNodes_Asterisk(rnd);
    // TODO(dsinclair@chromium.org): We could probably remove this.
    case '.':
      return XFA_ResolveNodes_AnyChild(rnd);
    default:
      break;
  }
  if (rnd.m_uHashName == XFA_HASHCODE_This && rnd.m_nLevel == 0) {
    rnd.m_Nodes.Add(rnd.m_pSC->GetThisObject());
    return 1;
  } else if (rnd.m_CurNode->GetClassID() == XFA_ELEMENT_Xfa) {
    CXFA_Object* pObjNode =
        rnd.m_pSC->GetDocument()->GetXFAObject(rnd.m_uHashName);
    if (pObjNode) {
      rnd.m_Nodes.Add(pObjNode);
    } else if (rnd.m_uHashName == XFA_HASHCODE_Xfa) {
      rnd.m_Nodes.Add(rnd.m_CurNode);
    } else if ((rnd.m_dwStyles & XFA_RESOLVENODE_Attributes) &&
               XFA_ResolveNodes_ForAttributeRs(rnd.m_CurNode, rnd,
                                               rnd.m_wsName)) {
      return 1;
    }
    if (rnd.m_Nodes.GetSize() > 0) {
      XFA_ResolveNode_FilterCondition(rnd, rnd.m_wsCondition);
    }
    return rnd.m_Nodes.GetSize();
  }
  int32_t nRet = XFA_ResolveNodes_Normal(rnd);
  if (nRet < 1 && rnd.m_uHashName == XFA_HASHCODE_Xfa) {
    rnd.m_Nodes.Add(rnd.m_pSC->GetDocument()->GetRoot());
  }
  return rnd.m_Nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_AnyChild(
    CXFA_ResolveNodesData& rnd) {
  CFX_WideString wsName = rnd.m_wsName;
  CFX_WideString wsCondition = rnd.m_wsCondition;
  CXFA_Node* findNode = NULL;
  CXFA_NodeArray siblings;
  FX_BOOL bClassName = FALSE;
  if (wsName.GetAt(0) == '#') {
    bClassName = TRUE;
    wsName = wsName.Right(wsName.GetLength() - 1);
  }
  findNode = m_pNodeHelper->XFA_ResolveNodes_GetOneChild(ToNode(rnd.m_CurNode),
                                                         wsName, bClassName);
  if (findNode == NULL) {
    return 0;
  }
  if (wsCondition.IsEmpty()) {
    rnd.m_Nodes.Add(findNode);
    return rnd.m_Nodes.GetSize();
  }
  m_pNodeHelper->XFA_CountSiblings(findNode, XFA_LOGIC_Transparent,
                                   (CXFA_NodeArray*)&rnd.m_Nodes, bClassName);
  XFA_ResolveNode_FilterCondition(rnd, wsCondition);
  return rnd.m_Nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_Dollar(
    CXFA_ResolveNodesData& rnd) {
  CXFA_ObjArray& nodes = rnd.m_Nodes;
  CFX_WideString wsName = rnd.m_wsName;
  CFX_WideString wsCondition = rnd.m_wsCondition;
  int32_t iNameLen = wsName.GetLength();
  if (iNameLen == 1) {
    nodes.Add(rnd.m_CurNode);
    return 1;
  }
  if (rnd.m_nLevel > 0) {
    return -1;
  }
  FX_DWORD dwNameHash =
      FX_HashCode_String_GetW((const FX_WCHAR*)wsName + 1, iNameLen - 1);
  if (dwNameHash == XFA_HASHCODE_Xfa) {
    nodes.Add(rnd.m_pSC->GetDocument()->GetRoot());
  } else {
    CXFA_Object* pObjNode = rnd.m_pSC->GetDocument()->GetXFAObject(dwNameHash);
    if (pObjNode) {
      rnd.m_Nodes.Add(pObjNode);
    }
  }
  if (rnd.m_Nodes.GetSize() > 0) {
    XFA_ResolveNode_FilterCondition(rnd, wsCondition);
  }
  return rnd.m_Nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_Excalmatory(
    CXFA_ResolveNodesData& rnd) {
  if (rnd.m_nLevel > 0) {
    return 0;
  }
  CXFA_Node* datasets =
      ToNode(rnd.m_pSC->GetDocument()->GetXFAObject(XFA_HASHCODE_Datasets));
  if (!datasets) {
    return 0;
  }
  CXFA_ResolveNodesData rndFind;
  rndFind.m_pSC = rnd.m_pSC;
  rndFind.m_CurNode = datasets;
  rndFind.m_wsName = rnd.m_wsName.Right(rnd.m_wsName.GetLength() - 1);
  rndFind.m_uHashName =
      FX_HashCode_String_GetW(rndFind.m_wsName, rndFind.m_wsName.GetLength());
  rndFind.m_nLevel = rnd.m_nLevel + 1;
  rndFind.m_dwStyles = XFA_RESOLVENODE_Children;
  rndFind.m_wsCondition = rnd.m_wsCondition;
  XFA_ResolveNodes(rndFind);
  if (rndFind.m_Nodes.GetSize() > 0) {
    rnd.m_Nodes.Append(rndFind.m_Nodes);
    rndFind.m_Nodes.RemoveAll();
  }
  return rnd.m_Nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_NumberSign(
    CXFA_ResolveNodesData& rnd) {
  CFX_WideString wsName = rnd.m_wsName.Right(rnd.m_wsName.GetLength() - 1);
  CFX_WideString wsCondition = rnd.m_wsCondition;
  CXFA_Node* curNode = ToNode(rnd.m_CurNode);
  if (XFA_ResolveNodes_ForAttributeRs(curNode, rnd, wsName)) {
    return 1;
  }
  CXFA_ResolveNodesData rndFind;
  rndFind.m_pSC = rnd.m_pSC;
  rndFind.m_nLevel = rnd.m_nLevel + 1;
  rndFind.m_dwStyles = rnd.m_dwStyles;
  rndFind.m_dwStyles |= XFA_RESOLVENODE_TagName;
  rndFind.m_dwStyles &= ~XFA_RESOLVENODE_Attributes;
  rndFind.m_wsName = wsName;
  rndFind.m_uHashName =
      FX_HashCode_String_GetW(rndFind.m_wsName, rndFind.m_wsName.GetLength());
  rndFind.m_wsCondition = wsCondition;
  rndFind.m_CurNode = curNode;
  XFA_ResolveNodes_Normal(rndFind);
  if (rndFind.m_Nodes.GetSize() > 0) {
    if (wsCondition.GetLength() == 0 && rndFind.m_Nodes.Find(curNode) >= 0) {
      rnd.m_Nodes.Add(curNode);
    } else {
      rnd.m_Nodes.Append(rndFind.m_Nodes);
      rndFind.m_Nodes.RemoveAll();
    }
  }
  return rnd.m_Nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_ForAttributeRs(
    CXFA_Object* curNode,
    CXFA_ResolveNodesData& rnd,
    const CFX_WideStringC& strAttr) {
  const XFA_SCRIPTATTRIBUTEINFO* lpScriptAttribute =
      XFA_GetScriptAttributeByName(curNode->GetClassID(), strAttr);
  if (lpScriptAttribute) {
    rnd.m_pScriptAttribute = lpScriptAttribute;
    rnd.m_Nodes.Add(curNode);
    rnd.m_dwFlag = XFA_RESOVENODE_RSTYPE_Attribute;
    return 1;
  }
  return 0;
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_Normal(
    CXFA_ResolveNodesData& rnd) {
  if (rnd.m_nLevel > 32) {
    return 0;
  }
  if (!rnd.m_CurNode->IsNode()) {
    return 0;
  }
  CXFA_Node* curNode = ToNode(rnd.m_CurNode);
  CXFA_ObjArray& nodes = rnd.m_Nodes;
  int32_t nNum = nodes.GetSize();
  FX_DWORD dwStyles = rnd.m_dwStyles;
  CFX_WideString& wsName = rnd.m_wsName;
  uint32_t uNameHash = rnd.m_uHashName;
  CFX_WideString& wsCondition = rnd.m_wsCondition;
  CXFA_ResolveNodesData rndFind;
  rndFind.m_wsName = rnd.m_wsName;
  rndFind.m_wsCondition = rnd.m_wsCondition;
  rndFind.m_pSC = rnd.m_pSC;
  rndFind.m_nLevel = rnd.m_nLevel + 1;
  rndFind.m_uHashName = uNameHash;
  CXFA_NodeArray children;
  CXFA_NodeArray properties;
  CXFA_Node* pVariablesNode = NULL;
  CXFA_Node* pPageSetNode = NULL;
  CXFA_Node* pChild = curNode->GetNodeItem(XFA_NODEITEM_FirstChild);
  while (pChild) {
    if (pChild->GetClassID() == XFA_ELEMENT_Variables) {
      pVariablesNode = pChild;
      pChild = pChild->GetNodeItem(XFA_NODEITEM_NextSibling);
      continue;
    } else if (pChild->GetClassID() == XFA_ELEMENT_PageSet) {
      pPageSetNode = pChild;
      pChild = pChild->GetNodeItem(XFA_NODEITEM_NextSibling);
      continue;
    } else {
      const XFA_PROPERTY* pPropert = XFA_GetPropertyOfElement(
          curNode->GetClassID(), pChild->GetClassID(), XFA_XDPPACKET_UNKNOWN);
      if (pPropert) {
        properties.Add(pChild);
      } else {
        children.Add(pChild);
      }
    }
    pChild = pChild->GetNodeItem(XFA_NODEITEM_NextSibling);
  }
  if ((dwStyles & XFA_RESOLVENODE_Properties) && pVariablesNode) {
    uint32_t uPropHash = pVariablesNode->GetClassHashCode();
    if (uPropHash == uNameHash) {
      nodes.Add(pVariablesNode);
    } else {
      rndFind.m_CurNode = pVariablesNode;
      XFA_ResolveNodes_SetStylesForChild(dwStyles, rndFind);
      CFX_WideString wsSaveCondition = rndFind.m_wsCondition;
      rndFind.m_wsCondition.Empty();
      XFA_ResolveNodes_Normal(rndFind);
      rndFind.m_wsCondition = wsSaveCondition;
      if (rndFind.m_Nodes.GetSize() > 0) {
        nodes.Append(rndFind.m_Nodes);
        rndFind.m_Nodes.RemoveAll();
      }
    }
    if (nodes.GetSize() > nNum) {
      XFA_ResolveNode_FilterCondition(rnd, wsCondition);
      if (nodes.GetSize() > 0) {
        return 1;
      }
      return 0;
    }
  }
  if (dwStyles & XFA_RESOLVENODE_Children) {
    FX_BOOL bSetFlag = FALSE;
    if (pPageSetNode && (dwStyles & XFA_RESOLVENODE_Properties)) {
      children.Add(pPageSetNode);
    }
    for (int32_t i = 0; i < children.GetSize(); i++) {
      CXFA_Node* child = children[i];
      if (dwStyles & XFA_RESOLVENODE_TagName) {
        if (child->GetClassHashCode() == uNameHash) {
          nodes.Add(child);
        }
      } else if (child->GetNameHash() == uNameHash) {
        nodes.Add(child);
      }
      if (m_pNodeHelper->XFA_NodeIsTransparent(child) &&
          child->GetClassID() != XFA_ELEMENT_PageSet) {
        if (!bSetFlag) {
          XFA_ResolveNodes_SetStylesForChild(dwStyles, rndFind);
          bSetFlag = TRUE;
        }
        rndFind.m_CurNode = child;
        CFX_WideString wsSaveCondition = rndFind.m_wsCondition;
        rndFind.m_wsCondition.Empty();
        XFA_ResolveNodes_Normal(rndFind);
        rndFind.m_wsCondition = wsSaveCondition;
        if (rndFind.m_Nodes.GetSize() > 0) {
          nodes.Append(rndFind.m_Nodes);
          rndFind.m_Nodes.RemoveAll();
        }
      }
    }
    if (nodes.GetSize() > nNum) {
      if (!(dwStyles & XFA_RESOLVENODE_ALL)) {
        CXFA_NodeArray upArrayNodes;
        if (m_pNodeHelper->XFA_NodeIsTransparent(ToNode(curNode))) {
          m_pNodeHelper->XFA_CountSiblings(
              ToNode(nodes[0]), XFA_LOGIC_Transparent, &upArrayNodes,
              !!(dwStyles & XFA_RESOLVENODE_TagName));
        }
        if (upArrayNodes.GetSize() > nodes.GetSize()) {
          upArrayNodes[0] = ToNode(nodes[0]);
          nodes.RemoveAll();
          nodes.Append((CXFA_ObjArray&)upArrayNodes);
          upArrayNodes.RemoveAll();
        }
      }
      XFA_ResolveNode_FilterCondition(rnd, wsCondition);
      if (nodes.GetSize() > 0) {
        return 1;
      }
      return 0;
    }
  }
  if (dwStyles & XFA_RESOLVENODE_Attributes) {
    if (XFA_ResolveNodes_ForAttributeRs(curNode, rnd, wsName)) {
      return 1;
    }
  }
  if (dwStyles & XFA_RESOLVENODE_Properties) {
    for (int32_t i = 0; i < properties.GetSize(); i++) {
      CXFA_Node* childProperty = properties[i];
      if (childProperty->IsUnnamed()) {
        uint32_t uPropHash = childProperty->GetClassHashCode();
        if (uPropHash == uNameHash) {
          nodes.Add(childProperty);
        }
      } else if (childProperty->GetNameHash() == uNameHash &&
                 childProperty->GetClassID() != XFA_ELEMENT_Extras &&
                 childProperty->GetClassID() != XFA_ELEMENT_Items) {
        nodes.Add(childProperty);
      }
    }
    if (nodes.GetSize() > nNum) {
      XFA_ResolveNode_FilterCondition(rnd, wsCondition);
      if (nodes.GetSize() > 0) {
        return 1;
      }
      return 0;
    }
    CXFA_Node* pProp = NULL;
    if (XFA_ELEMENT_Subform == curNode->GetClassID() &&
        XFA_HASHCODE_Occur == uNameHash) {
      CXFA_Node* pInstanceManager =
          curNode->AsNode()->GetInstanceMgrOfSubform();
      if (pInstanceManager) {
        pProp = pInstanceManager->GetProperty(0, XFA_ELEMENT_Occur, TRUE);
      }
    } else {
      const XFA_ELEMENTINFO* pElement = XFA_GetElementByName(wsName);
      if (pElement) {
        pProp = curNode->AsNode()->GetProperty(
            0, pElement->eName, pElement->eName != XFA_ELEMENT_PageSet);
      }
    }
    if (pProp) {
      nodes.Add(pProp);
      return nodes.GetSize();
    }
  }
  CXFA_Node* parentNode = m_pNodeHelper->XFA_ResolveNodes_GetParent(
      curNode->AsNode(), XFA_LOGIC_NoTransparent);
  uint32_t uCurClassHash = curNode->GetClassHashCode();
  if (!parentNode) {
    if (uCurClassHash == uNameHash) {
      nodes.Add(curNode->AsNode());
      XFA_ResolveNode_FilterCondition(rnd, wsCondition);
      if (nodes.GetSize() > 0) {
        return 1;
      }
    }
    return 0;
  }
  if (dwStyles & XFA_RESOLVENODE_Siblings) {
    CXFA_Node* child = parentNode->GetNodeItem(XFA_NODEITEM_FirstChild);
    FX_DWORD dwSubStyles =
        XFA_RESOLVENODE_Children | XFA_RESOLVENODE_Properties;
    if (dwStyles & XFA_RESOLVENODE_TagName) {
      dwSubStyles |= XFA_RESOLVENODE_TagName;
    }
    if (dwStyles & XFA_RESOLVENODE_ALL) {
      dwSubStyles |= XFA_RESOLVENODE_ALL;
    }
    rndFind.m_dwStyles = dwSubStyles;
    while (child) {
      if (child == curNode) {
        if (dwStyles & XFA_RESOLVENODE_TagName) {
          if (uCurClassHash == uNameHash) {
            nodes.Add(curNode);
          }
        } else {
          if (child->GetNameHash() == uNameHash) {
            nodes.Add(curNode);
            if (rnd.m_nLevel == 0 && wsCondition.GetLength() == 0) {
              nodes.RemoveAll();
              nodes.Add(curNode);
              return 1;
            }
          }
        }
        child = child->GetNodeItem(XFA_NODEITEM_NextSibling);
        continue;
      }
      if (dwStyles & XFA_RESOLVENODE_TagName) {
        if (child->GetClassHashCode() == uNameHash) {
          nodes.Add(child);
        }
      } else if (child->GetNameHash() == uNameHash) {
        nodes.Add(child);
      }
      const XFA_PROPERTY* pPropert = XFA_GetPropertyOfElement(
          parentNode->GetClassID(), child->GetClassID(), XFA_XDPPACKET_UNKNOWN);
      FX_BOOL bInnerSearch = FALSE;
      if (pPropert) {
        if ((child->GetClassID() == XFA_ELEMENT_Variables ||
             child->GetClassID() == XFA_ELEMENT_PageSet)) {
          bInnerSearch = TRUE;
        }
      } else {
        if (m_pNodeHelper->XFA_NodeIsTransparent(child)) {
          bInnerSearch = TRUE;
        }
      }
      if (bInnerSearch) {
        rndFind.m_CurNode = child;
        CFX_WideString wsOriginCondition = rndFind.m_wsCondition;
        rndFind.m_wsCondition.Empty();
        FX_DWORD dwOriginStyle = rndFind.m_dwStyles;
        rndFind.m_dwStyles = dwOriginStyle | XFA_RESOLVENODE_ALL;
        XFA_ResolveNodes_Normal(rndFind);
        rndFind.m_dwStyles = dwOriginStyle;
        rndFind.m_wsCondition = wsOriginCondition;
        if (rndFind.m_Nodes.GetSize() > 0) {
          nodes.Append(rndFind.m_Nodes);
          rndFind.m_Nodes.RemoveAll();
        }
      }
      child = child->GetNodeItem(XFA_NODEITEM_NextSibling);
    }
    if (nodes.GetSize() > nNum) {
      if (m_pNodeHelper->XFA_NodeIsTransparent(parentNode)) {
        CXFA_NodeArray upArrayNodes;
        m_pNodeHelper->XFA_CountSiblings(
            ToNode(nodes[0]), XFA_LOGIC_Transparent, &upArrayNodes,
            !!(dwStyles & XFA_RESOLVENODE_TagName));
        if (upArrayNodes.GetSize() > nodes.GetSize()) {
          upArrayNodes[0] = ToNode(nodes[0]);
          nodes.RemoveAll();
          nodes.Append((CXFA_ObjArray&)upArrayNodes);
          upArrayNodes.RemoveAll();
        }
      }
      XFA_ResolveNode_FilterCondition(rnd, wsCondition);
      if (nodes.GetSize() > 0) {
        return 1;
      }
      return 0;
    }
  }
  if (dwStyles & XFA_RESOLVENODE_Parent) {
    FX_DWORD dwSubStyles = XFA_RESOLVENODE_Siblings | XFA_RESOLVENODE_Parent |
                           XFA_RESOLVENODE_Properties;
    if (dwStyles & XFA_RESOLVENODE_TagName) {
      dwSubStyles |= XFA_RESOLVENODE_TagName;
    }
    if (dwStyles & XFA_RESOLVENODE_ALL) {
      dwSubStyles |= XFA_RESOLVENODE_ALL;
    }
    rndFind.m_dwStyles = dwSubStyles;
    rndFind.m_CurNode = parentNode;
    CXFA_NodeArray& array = rnd.m_pSC->GetUpObjectArray();
    array.Add(parentNode);
    XFA_ResolveNodes_Normal(rndFind);
    if (rndFind.m_Nodes.GetSize() > 0) {
      nodes.Append(rndFind.m_Nodes);
      rndFind.m_Nodes.RemoveAll();
    }
    if (nodes.GetSize() > nNum) {
      return 1;
    }
  }
  return 0;
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_Asterisk(
    CXFA_ResolveNodesData& rnd) {
  CXFA_Node* curNode = ToNode(rnd.m_CurNode);
  CXFA_ObjArray& nodes = rnd.m_Nodes;
  CXFA_NodeArray array;
  curNode->GetNodeList(array,
                       XFA_NODEFILTER_Children | XFA_NODEFILTER_Properties);
  nodes.Append((CXFA_ObjArray&)array);
  return nodes.GetSize();
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_PopStack(
    CFX_Int32Array& stack) {
  int32_t nType = -1;
  int32_t iSize = stack.GetSize() - 1;
  if (iSize > -1) {
    nType = stack[iSize];
    stack.RemoveAt(iSize, 1);
  }
  return nType;
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNodes_GetFilter(
    const CFX_WideStringC& wsExpression,
    int32_t nStart,
    CXFA_ResolveNodesData& rnd) {
  FXSYS_assert(nStart > -1);
  int32_t iLength = wsExpression.GetLength();
  if (nStart >= iLength) {
    return 0;
  }
  CFX_WideString& wsName = rnd.m_wsName;
  CFX_WideString& wsCondition = rnd.m_wsCondition;
  FX_WCHAR* pNameBuf = wsName.GetBuffer(iLength - nStart);
  FX_WCHAR* pConditionBuf = wsCondition.GetBuffer(iLength - nStart);
  int32_t nNameCount = 0;
  int32_t nConditionCount = 0;
  CFX_Int32Array stack;
  int32_t nType = -1;
  const FX_WCHAR* pSrc = wsExpression.GetPtr();
  FX_WCHAR wPrev = 0, wCur;
  FX_BOOL bIsCondition = FALSE;
  while (nStart < iLength) {
    wCur = pSrc[nStart++];
    if (wCur == '.') {
      if (wPrev == '\\') {
        pNameBuf[nNameCount - 1] = wPrev = '.';
        continue;
      }
      if (nNameCount == 0) {
        rnd.m_dwStyles |= XFA_RESOLVENODE_AnyChild;
        continue;
      }
      FX_WCHAR wLookahead = nStart < iLength ? pSrc[nStart] : 0;
      if (wLookahead != '[' && wLookahead != '(') {
        if (nType < 0) {
          break;
        }
      }
    }
    if (wCur == '[' || wCur == '(') {
      bIsCondition = TRUE;
    } else if (wCur == '.' && nStart < iLength &&
               (pSrc[nStart] == '[' || pSrc[nStart] == '(')) {
      bIsCondition = TRUE;
    }
    if (bIsCondition) {
      pConditionBuf[nConditionCount++] = wCur;
    } else {
      pNameBuf[nNameCount++] = wCur;
    }
    FX_BOOL bRecursive = TRUE;
    switch (nType) {
      case 0:
        if (wCur == ']') {
          nType = XFA_ResolveNodes_PopStack(stack);
          bRecursive = FALSE;
        }
        break;
      case 1:
        if (wCur == ')') {
          nType = XFA_ResolveNodes_PopStack(stack);
          bRecursive = FALSE;
        }
        break;
      case 2:
        if (wCur == '"') {
          nType = XFA_ResolveNodes_PopStack(stack);
          bRecursive = FALSE;
        }
        break;
    }
    if (bRecursive) {
      switch (wCur) {
        case '[':
          stack.Add(nType);
          nType = 0;
          break;
        case '(':
          stack.Add(nType);
          nType = 1;
          break;
        case '"':
          stack.Add(nType);
          nType = 2;
          break;
      }
    }
    wPrev = wCur;
  }
  if (stack.GetSize() > 0) {
    return -1;
  }
  wsName.ReleaseBuffer(nNameCount);
  wsName.TrimLeft();
  wsName.TrimRight();
  wsCondition.ReleaseBuffer(nConditionCount);
  wsCondition.TrimLeft();
  wsCondition.TrimRight();
  rnd.m_uHashName = FX_HashCode_String_GetW(wsName, wsName.GetLength());
  return nStart;
}
void CXFA_ResolveProcessor::XFA_ResolveNode_ConditionArray(
    int32_t iCurIndex,
    CFX_WideString wsCondition,
    int32_t iFoundCount,
    CXFA_ResolveNodesData& rnd) {
  CXFA_NodeArray& findNodes = (CXFA_NodeArray&)rnd.m_Nodes;
  int32_t iLen = wsCondition.GetLength();
  FX_BOOL bRelative = FALSE;
  FX_BOOL bAll = FALSE;
  int32_t i = 1;
  for (; i < iLen; ++i) {
    FX_WCHAR ch = wsCondition[i];
    if (ch == ' ') {
      continue;
    }
    if (ch == '+' || ch == '-') {
      bRelative = TRUE;
      break;
    } else if (ch == '*') {
      bAll = TRUE;
      break;
    } else {
      break;
    }
  }
  if (bAll) {
    if (rnd.m_dwStyles & XFA_RESOLVENODE_CreateNode) {
      if (rnd.m_dwStyles & XFA_RESOLVENODE_Bind) {
        m_pNodeHelper->m_pCreateParent = ToNode(rnd.m_CurNode);
        m_pNodeHelper->m_iCreateCount = 1;
        findNodes.RemoveAll();
        m_pNodeHelper->m_iCurAllStart = -1;
        m_pNodeHelper->m_pAllStartParent = NULL;
      } else {
        if (m_pNodeHelper->m_iCurAllStart == -1) {
          m_pNodeHelper->m_iCurAllStart = m_iCurStart;
          m_pNodeHelper->m_pAllStartParent = ToNode(rnd.m_CurNode);
        }
      }
    } else if (rnd.m_dwStyles & XFA_RESOLVENODE_BindNew) {
      if (m_pNodeHelper->m_iCurAllStart == -1) {
        m_pNodeHelper->m_iCurAllStart = m_iCurStart;
      }
    }
    return;
  }
  if (iFoundCount == 1 && !iLen) {
    return;
  }
  CFX_WideString wsIndex;
  wsIndex = wsCondition.Mid(i, iLen - 1 - i);
  int32_t iIndex = wsIndex.GetInteger();
  if (bRelative) {
    iIndex += iCurIndex;
  }
  if (iFoundCount <= iIndex || iIndex < 0) {
    if (rnd.m_dwStyles & XFA_RESOLVENODE_CreateNode) {
      m_pNodeHelper->m_pCreateParent = ToNode(rnd.m_CurNode);
      m_pNodeHelper->m_iCreateCount = iIndex - iFoundCount + 1;
    }
    findNodes.RemoveAll();
  } else {
    CXFA_Node* ret = findNodes[iIndex];
    findNodes.RemoveAll();
    findNodes.Add(ret);
  }
}
void CXFA_ResolveProcessor::XFA_ResolveNode_DoPredicateFilter(
    int32_t iCurIndex,
    CFX_WideString wsCondition,
    int32_t iFoundCount,
    CXFA_ResolveNodesData& rnd) {
  CXFA_NodeArray& findNodes = (CXFA_NodeArray&)rnd.m_Nodes;
  FXSYS_assert(iFoundCount == findNodes.GetSize());
  CFX_WideString wsExpression;
  IXFA_ScriptContext* pContext = NULL;
  XFA_SCRIPTLANGTYPE eLangType = XFA_SCRIPTLANGTYPE_Unkown;
  if (wsCondition.Left(2) == FX_WSTRC(L".[") &&
      wsCondition.Right(1) == FX_WSTRC(L"]")) {
    eLangType = XFA_SCRIPTLANGTYPE_Formcalc;
  } else if (wsCondition.Left(2) == FX_WSTRC(L".(") &&
             wsCondition.Right(1) == FX_WSTRC(L")")) {
    eLangType = XFA_SCRIPTLANGTYPE_Javascript;
  } else {
    return;
  }
  pContext = rnd.m_pSC;
  wsExpression = wsCondition.Mid(2, wsCondition.GetLength() - 3);
  for (int32_t i = iFoundCount - 1; i >= 0; i--) {
    CXFA_Object* node = findNodes[i];
    FX_BOOL bRet = FALSE;
    FXJSE_HVALUE pRetValue = FXJSE_Value_Create(rnd.m_pSC->GetRuntime());
    bRet = pContext->RunScript(eLangType, wsExpression, pRetValue, node);
    if (!bRet || !FXJSE_Value_ToBoolean(pRetValue)) {
      findNodes.RemoveAt(i);
    }
    FXJSE_Value_Release(pRetValue);
  }
}

void CXFA_ResolveProcessor::XFA_ResolveNode_FilterCondition(
    CXFA_ResolveNodesData& rnd,
    CFX_WideString wsCondition) {
  CXFA_NodeArray& findNodes = (CXFA_NodeArray&)rnd.m_Nodes;
  int32_t iCurrIndex = 0;
  const CXFA_NodeArray& array = rnd.m_pSC->GetUpObjectArray();
  int32_t iSize = array.GetSize();
  if (iSize) {
    CXFA_Node* curNode = array[iSize - 1];
    FX_BOOL bIsProperty = m_pNodeHelper->XFA_NodeIsProperty(curNode);
    if (curNode->IsUnnamed() ||
        (bIsProperty && curNode->GetClassID() != XFA_ELEMENT_PageSet)) {
      iCurrIndex = m_pNodeHelper->XFA_GetIndex(curNode, XFA_LOGIC_Transparent,
                                               bIsProperty, TRUE);
    } else {
      iCurrIndex = m_pNodeHelper->XFA_GetIndex(curNode, XFA_LOGIC_Transparent,
                                               bIsProperty, FALSE);
    }
  }
  int32_t iFoundCount = findNodes.GetSize();
  wsCondition.TrimLeft();
  wsCondition.TrimRight();
  int32_t iLen = wsCondition.GetLength();
  if (!iLen) {
    if (rnd.m_dwStyles & XFA_RESOLVENODE_ALL) {
      return;
    }
    if (iFoundCount == 1) {
      return;
    }
    if (iFoundCount <= iCurrIndex) {
      if (rnd.m_dwStyles & XFA_RESOLVENODE_CreateNode) {
        m_pNodeHelper->m_pCreateParent = ToNode(rnd.m_CurNode);
        m_pNodeHelper->m_iCreateCount = iCurrIndex - iFoundCount + 1;
      }
      findNodes.RemoveAll();
      return;
    } else {
      CXFA_Node* ret = findNodes[iCurrIndex];
      findNodes.RemoveAll();
      findNodes.Add(ret);
      return;
    }
  }
  FX_WCHAR wTypeChar = wsCondition[0];
  switch (wTypeChar) {
    case '[':
      XFA_ResolveNode_ConditionArray(iCurrIndex, wsCondition, iFoundCount, rnd);
      return;
    case '(':
      return;
    case '"':
      return;
    case '.':
      if (iLen > 1 && (wsCondition[1] == '[' || wsCondition[1] == '(')) {
        XFA_ResolveNode_DoPredicateFilter(iCurrIndex, wsCondition, iFoundCount,
                                          rnd);
      }
    default:
      return;
  }
}
void CXFA_ResolveProcessor::XFA_ResolveNodes_SetStylesForChild(
    FX_DWORD dwParentStyles,
    CXFA_ResolveNodesData& rnd) {
  FX_DWORD dwSubStyles = XFA_RESOLVENODE_Children;
  if (dwParentStyles & XFA_RESOLVENODE_TagName) {
    dwSubStyles |= XFA_RESOLVENODE_TagName;
  }
  dwSubStyles &= ~XFA_RESOLVENODE_Parent;
  dwSubStyles &= ~XFA_RESOLVENODE_Siblings;
  dwSubStyles &= ~XFA_RESOLVENODE_Properties;
  dwSubStyles |= XFA_RESOLVENODE_ALL;
  rnd.m_dwStyles = dwSubStyles;
}
int32_t CXFA_ResolveProcessor::XFA_ResolveNode_SetResultCreateNode(
    XFA_RESOLVENODE_RS& resolveNodeRS,
    CFX_WideString& wsLastCondition) {
  if (m_pNodeHelper->m_pCreateParent) {
    resolveNodeRS.nodes.Add(m_pNodeHelper->m_pCreateParent);
  } else {
    m_pNodeHelper->XFA_CreateNode_ForCondition(wsLastCondition);
  }
  resolveNodeRS.dwFlags = m_pNodeHelper->m_iCreateFlag;
  if (resolveNodeRS.dwFlags == XFA_RESOLVENODE_RSTYPE_CreateNodeOne) {
    if (m_pNodeHelper->m_iCurAllStart != -1) {
      resolveNodeRS.dwFlags = XFA_RESOLVENODE_RSTYPE_CreateNodeMidAll;
    }
  }
  return resolveNodeRS.nodes.GetSize();
}
void CXFA_ResolveProcessor::XFA_ResolveNode_SetIndexDataBind(
    CFX_WideString& wsNextCondition,
    int32_t& iIndex,
    int32_t iCount) {
  if (m_pNodeHelper->XFA_CreateNode_ForCondition(wsNextCondition)) {
    if (m_pNodeHelper->m_eLastCreateType == XFA_ELEMENT_DataGroup) {
      iIndex = 0;
    } else {
      iIndex = iCount - 1;
    }
  } else {
    iIndex = iCount - 1;
  }
}
