| OLD | NEW | 
 | (Empty) | 
|    1 // Copyright 2014 PDFium Authors. All rights reserved. |  | 
|    2 // Use of this source code is governed by a BSD-style license that can be |  | 
|    3 // found in the LICENSE file. |  | 
|    4  |  | 
|    5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com |  | 
|    6  |  | 
|    7 #include "xfa/fxfa/parser/xfa_utils.h" |  | 
|    8  |  | 
|    9 #include "core/fxcrt/include/fx_ext.h" |  | 
|   10 #include "xfa/fde/xml/fde_xml_imp.h" |  | 
|   11 #include "xfa/fxfa/parser/cxfa_document.h" |  | 
|   12 #include "xfa/fxfa/parser/cxfa_measurement.h" |  | 
|   13 #include "xfa/fxfa/parser/xfa_basic_data.h" |  | 
|   14 #include "xfa/fxfa/parser/xfa_localemgr.h" |  | 
|   15 #include "xfa/fxfa/parser/xfa_localevalue.h" |  | 
|   16 #include "xfa/fxfa/parser/xfa_object.h" |  | 
|   17  |  | 
|   18 namespace { |  | 
|   19  |  | 
|   20 const FX_DOUBLE fraction_scales[] = {0.1, |  | 
|   21                                      0.01, |  | 
|   22                                      0.001, |  | 
|   23                                      0.0001, |  | 
|   24                                      0.00001, |  | 
|   25                                      0.000001, |  | 
|   26                                      0.0000001, |  | 
|   27                                      0.00000001, |  | 
|   28                                      0.000000001, |  | 
|   29                                      0.0000000001, |  | 
|   30                                      0.00000000001, |  | 
|   31                                      0.000000000001, |  | 
|   32                                      0.0000000000001, |  | 
|   33                                      0.00000000000001, |  | 
|   34                                      0.000000000000001, |  | 
|   35                                      0.0000000000000001}; |  | 
|   36  |  | 
|   37 FX_DOUBLE WideStringToDouble(const CFX_WideString& wsStringVal) { |  | 
|   38   CFX_WideString wsValue = wsStringVal; |  | 
|   39   wsValue.TrimLeft(); |  | 
|   40   wsValue.TrimRight(); |  | 
|   41   int64_t nIntegral = 0; |  | 
|   42   uint32_t dwFractional = 0; |  | 
|   43   int32_t nExponent = 0; |  | 
|   44   int32_t cc = 0; |  | 
|   45   bool bNegative = false; |  | 
|   46   bool bExpSign = false; |  | 
|   47   const FX_WCHAR* str = wsValue.c_str(); |  | 
|   48   int32_t len = wsValue.GetLength(); |  | 
|   49   if (str[0] == '+') { |  | 
|   50     cc++; |  | 
|   51   } else if (str[0] == '-') { |  | 
|   52     bNegative = true; |  | 
|   53     cc++; |  | 
|   54   } |  | 
|   55   int32_t nIntegralLen = 0; |  | 
|   56   while (cc < len) { |  | 
|   57     if (str[cc] == '.' || str[cc] == 'E' || str[cc] == 'e' || |  | 
|   58         nIntegralLen > 17) { |  | 
|   59       break; |  | 
|   60     } |  | 
|   61     if (!FXSYS_isDecimalDigit(str[cc])) { |  | 
|   62       return 0; |  | 
|   63     } |  | 
|   64     nIntegral = nIntegral * 10 + str[cc] - '0'; |  | 
|   65     cc++; |  | 
|   66     nIntegralLen++; |  | 
|   67   } |  | 
|   68   nIntegral = bNegative ? -nIntegral : nIntegral; |  | 
|   69   int32_t scale = 0; |  | 
|   70   FX_DOUBLE fraction = 0.0; |  | 
|   71   if (cc < len && str[cc] == '.') { |  | 
|   72     cc++; |  | 
|   73     while (cc < len) { |  | 
|   74       fraction += fraction_scales[scale] * (str[cc] - '0'); |  | 
|   75       scale++; |  | 
|   76       cc++; |  | 
|   77       if (cc == len) { |  | 
|   78         break; |  | 
|   79       } |  | 
|   80       if (scale == sizeof(fraction_scales) / sizeof(FX_DOUBLE) || |  | 
|   81           str[cc] == 'E' || str[cc] == 'e') { |  | 
|   82         break; |  | 
|   83       } |  | 
|   84       if (!FXSYS_isDecimalDigit(str[cc])) { |  | 
|   85         return 0; |  | 
|   86       } |  | 
|   87     } |  | 
|   88     dwFractional = (uint32_t)(fraction * 4294967296.0); |  | 
|   89   } |  | 
|   90   if (cc < len && (str[cc] == 'E' || str[cc] == 'e')) { |  | 
|   91     cc++; |  | 
|   92     if (cc < len) { |  | 
|   93       if (str[cc] == '+') { |  | 
|   94         cc++; |  | 
|   95       } else if (str[cc] == '-') { |  | 
|   96         bExpSign = true; |  | 
|   97         cc++; |  | 
|   98       } |  | 
|   99     } |  | 
|  100     while (cc < len) { |  | 
|  101       if (str[cc] == '.' || !FXSYS_isDecimalDigit(str[cc])) { |  | 
|  102         return 0; |  | 
|  103       } |  | 
|  104       nExponent = nExponent * 10 + str[cc] - '0'; |  | 
|  105       cc++; |  | 
|  106     } |  | 
|  107     nExponent = bExpSign ? -nExponent : nExponent; |  | 
|  108   } |  | 
|  109   FX_DOUBLE dValue = (dwFractional / 4294967296.0); |  | 
|  110   dValue = nIntegral + (nIntegral >= 0 ? dValue : -dValue); |  | 
|  111   if (nExponent != 0) { |  | 
|  112     dValue *= FXSYS_pow(10, (FX_FLOAT)nExponent); |  | 
|  113   } |  | 
|  114   return dValue; |  | 
|  115 } |  | 
|  116  |  | 
|  117 }  // namespace |  | 
|  118  |  | 
|  119 CXFA_LocaleValue XFA_GetLocaleValue(CXFA_WidgetData* pWidgetData) { |  | 
|  120   CXFA_Node* pNodeValue = |  | 
|  121       pWidgetData->GetNode()->GetChild(0, XFA_Element::Value); |  | 
|  122   if (!pNodeValue) { |  | 
|  123     return CXFA_LocaleValue(); |  | 
|  124   } |  | 
|  125   CXFA_Node* pValueChild = pNodeValue->GetNodeItem(XFA_NODEITEM_FirstChild); |  | 
|  126   if (!pValueChild) { |  | 
|  127     return CXFA_LocaleValue(); |  | 
|  128   } |  | 
|  129   int32_t iVTType = XFA_VT_NULL; |  | 
|  130   switch (pValueChild->GetElementType()) { |  | 
|  131     case XFA_Element::Decimal: |  | 
|  132       iVTType = XFA_VT_DECIMAL; |  | 
|  133       break; |  | 
|  134     case XFA_Element::Float: |  | 
|  135       iVTType = XFA_VT_FLOAT; |  | 
|  136       break; |  | 
|  137     case XFA_Element::Date: |  | 
|  138       iVTType = XFA_VT_DATE; |  | 
|  139       break; |  | 
|  140     case XFA_Element::Time: |  | 
|  141       iVTType = XFA_VT_TIME; |  | 
|  142       break; |  | 
|  143     case XFA_Element::DateTime: |  | 
|  144       iVTType = XFA_VT_DATETIME; |  | 
|  145       break; |  | 
|  146     case XFA_Element::Boolean: |  | 
|  147       iVTType = XFA_VT_BOOLEAN; |  | 
|  148       break; |  | 
|  149     case XFA_Element::Integer: |  | 
|  150       iVTType = XFA_VT_INTEGER; |  | 
|  151       break; |  | 
|  152     case XFA_Element::Text: |  | 
|  153       iVTType = XFA_VT_TEXT; |  | 
|  154       break; |  | 
|  155     default: |  | 
|  156       iVTType = XFA_VT_NULL; |  | 
|  157       break; |  | 
|  158   } |  | 
|  159   return CXFA_LocaleValue(iVTType, pWidgetData->GetRawValue(), |  | 
|  160                           pWidgetData->GetNode()->GetDocument()->GetLocalMgr()); |  | 
|  161 } |  | 
|  162 void XFA_GetPlainTextFromRichText(CFDE_XMLNode* pXMLNode, |  | 
|  163                                   CFX_WideString& wsPlainText) { |  | 
|  164   if (!pXMLNode) { |  | 
|  165     return; |  | 
|  166   } |  | 
|  167   switch (pXMLNode->GetType()) { |  | 
|  168     case FDE_XMLNODE_Element: { |  | 
|  169       CFDE_XMLElement* pXMLElement = static_cast<CFDE_XMLElement*>(pXMLNode); |  | 
|  170       CFX_WideString wsTag; |  | 
|  171       pXMLElement->GetLocalTagName(wsTag); |  | 
|  172       uint32_t uTag = FX_HashCode_GetW(wsTag.AsStringC(), true); |  | 
|  173       if (uTag == 0x0001f714) { |  | 
|  174         wsPlainText += L"\n"; |  | 
|  175       } else if (uTag == 0x00000070) { |  | 
|  176         if (!wsPlainText.IsEmpty()) { |  | 
|  177           wsPlainText += L"\n"; |  | 
|  178         } |  | 
|  179       } else if (uTag == 0xa48ac63) { |  | 
|  180         if (!wsPlainText.IsEmpty() && |  | 
|  181             wsPlainText[wsPlainText.GetLength() - 1] != '\n') { |  | 
|  182           wsPlainText += L"\n"; |  | 
|  183         } |  | 
|  184       } |  | 
|  185     } break; |  | 
|  186     case FDE_XMLNODE_Text: { |  | 
|  187       CFX_WideString wsContent; |  | 
|  188       static_cast<CFDE_XMLText*>(pXMLNode)->GetText(wsContent); |  | 
|  189       wsPlainText += wsContent; |  | 
|  190     } break; |  | 
|  191     case FDE_XMLNODE_CharData: { |  | 
|  192       CFX_WideString wsCharData; |  | 
|  193       static_cast<CFDE_XMLCharData*>(pXMLNode)->GetCharData(wsCharData); |  | 
|  194       wsPlainText += wsCharData; |  | 
|  195     } break; |  | 
|  196     default: |  | 
|  197       break; |  | 
|  198   } |  | 
|  199   for (CFDE_XMLNode* pChildXML = |  | 
|  200            pXMLNode->GetNodeItem(CFDE_XMLNode::FirstChild); |  | 
|  201        pChildXML; |  | 
|  202        pChildXML = pChildXML->GetNodeItem(CFDE_XMLNode::NextSibling)) { |  | 
|  203     XFA_GetPlainTextFromRichText(pChildXML, wsPlainText); |  | 
|  204   } |  | 
|  205 } |  | 
|  206  |  | 
|  207 FX_BOOL XFA_FieldIsMultiListBox(CXFA_Node* pFieldNode) { |  | 
|  208   FX_BOOL bRet = FALSE; |  | 
|  209   if (!pFieldNode) |  | 
|  210     return bRet; |  | 
|  211  |  | 
|  212   CXFA_Node* pUIChild = pFieldNode->GetChild(0, XFA_Element::Ui); |  | 
|  213   if (pUIChild) { |  | 
|  214     CXFA_Node* pFirstChild = pUIChild->GetNodeItem(XFA_NODEITEM_FirstChild); |  | 
|  215     if (pFirstChild && |  | 
|  216         pFirstChild->GetElementType() == XFA_Element::ChoiceList) { |  | 
|  217       bRet = pFirstChild->GetEnum(XFA_ATTRIBUTE_Open) == |  | 
|  218              XFA_ATTRIBUTEENUM_MultiSelect; |  | 
|  219     } |  | 
|  220   } |  | 
|  221   return bRet; |  | 
|  222 } |  | 
|  223  |  | 
|  224 FX_DOUBLE XFA_ByteStringToDouble(const CFX_ByteStringC& szStringVal) { |  | 
|  225   CFX_WideString wsValue = CFX_WideString::FromUTF8(szStringVal); |  | 
|  226   return WideStringToDouble(wsValue); |  | 
|  227 } |  | 
|  228  |  | 
|  229 int32_t XFA_MapRotation(int32_t nRotation) { |  | 
|  230   nRotation = nRotation % 360; |  | 
|  231   nRotation = nRotation < 0 ? nRotation + 360 : nRotation; |  | 
|  232   return nRotation; |  | 
|  233 } |  | 
|  234  |  | 
|  235 const XFA_SCRIPTATTRIBUTEINFO* XFA_GetScriptAttributeByName( |  | 
|  236     XFA_Element eElement, |  | 
|  237     const CFX_WideStringC& wsAttributeName) { |  | 
|  238   if (wsAttributeName.IsEmpty()) |  | 
|  239     return nullptr; |  | 
|  240  |  | 
|  241   int32_t iElementIndex = static_cast<int32_t>(eElement); |  | 
|  242   while (iElementIndex != -1) { |  | 
|  243     const XFA_SCRIPTHIERARCHY* scriptIndex = g_XFAScriptIndex + iElementIndex; |  | 
|  244     int32_t icount = scriptIndex->wAttributeCount; |  | 
|  245     if (icount == 0) { |  | 
|  246       iElementIndex = scriptIndex->wParentIndex; |  | 
|  247       continue; |  | 
|  248     } |  | 
|  249     uint32_t uHash = FX_HashCode_GetW(wsAttributeName, false); |  | 
|  250     int32_t iStart = scriptIndex->wAttributeStart, iEnd = iStart + icount - 1; |  | 
|  251     do { |  | 
|  252       int32_t iMid = (iStart + iEnd) / 2; |  | 
|  253       const XFA_SCRIPTATTRIBUTEINFO* pInfo = g_SomAttributeData + iMid; |  | 
|  254       if (uHash == pInfo->uHash) |  | 
|  255         return pInfo; |  | 
|  256       if (uHash < pInfo->uHash) |  | 
|  257         iEnd = iMid - 1; |  | 
|  258       else |  | 
|  259         iStart = iMid + 1; |  | 
|  260     } while (iStart <= iEnd); |  | 
|  261     iElementIndex = scriptIndex->wParentIndex; |  | 
|  262   } |  | 
|  263   return nullptr; |  | 
|  264 } |  | 
|  265  |  | 
|  266 const XFA_NOTSUREATTRIBUTE* XFA_GetNotsureAttribute(XFA_Element eElement, |  | 
|  267                                                     XFA_ATTRIBUTE eAttribute, |  | 
|  268                                                     XFA_ATTRIBUTETYPE eType) { |  | 
|  269   int32_t iStart = 0, iEnd = g_iXFANotsureCount - 1; |  | 
|  270   do { |  | 
|  271     int32_t iMid = (iStart + iEnd) / 2; |  | 
|  272     const XFA_NOTSUREATTRIBUTE* pAttr = g_XFANotsureAttributes + iMid; |  | 
|  273     if (eElement == pAttr->eElement) { |  | 
|  274       if (pAttr->eAttribute == eAttribute) { |  | 
|  275         if (eType == XFA_ATTRIBUTETYPE_NOTSURE || eType == pAttr->eType) |  | 
|  276           return pAttr; |  | 
|  277         return nullptr; |  | 
|  278       } |  | 
|  279       int32_t iBefore = iMid - 1; |  | 
|  280       if (iBefore >= 0) { |  | 
|  281         pAttr = g_XFANotsureAttributes + iBefore; |  | 
|  282         while (eElement == pAttr->eElement) { |  | 
|  283           if (pAttr->eAttribute == eAttribute) { |  | 
|  284             if (eType == XFA_ATTRIBUTETYPE_NOTSURE || eType == pAttr->eType) |  | 
|  285               return pAttr; |  | 
|  286             return nullptr; |  | 
|  287           } |  | 
|  288           iBefore--; |  | 
|  289           if (iBefore < 0) |  | 
|  290             break; |  | 
|  291  |  | 
|  292           pAttr = g_XFANotsureAttributes + iBefore; |  | 
|  293         } |  | 
|  294       } |  | 
|  295  |  | 
|  296       int32_t iAfter = iMid + 1; |  | 
|  297       if (iAfter <= g_iXFANotsureCount - 1) { |  | 
|  298         pAttr = g_XFANotsureAttributes + iAfter; |  | 
|  299         while (eElement == pAttr->eElement) { |  | 
|  300           if (pAttr->eAttribute == eAttribute) { |  | 
|  301             if (eType == XFA_ATTRIBUTETYPE_NOTSURE || eType == pAttr->eType) |  | 
|  302               return pAttr; |  | 
|  303             return nullptr; |  | 
|  304           } |  | 
|  305           iAfter++; |  | 
|  306           if (iAfter > g_iXFANotsureCount - 1) |  | 
|  307             break; |  | 
|  308  |  | 
|  309           pAttr = g_XFANotsureAttributes + iAfter; |  | 
|  310         } |  | 
|  311       } |  | 
|  312       return nullptr; |  | 
|  313     } |  | 
|  314  |  | 
|  315     if (eElement < pAttr->eElement) |  | 
|  316       iEnd = iMid - 1; |  | 
|  317     else |  | 
|  318       iStart = iMid + 1; |  | 
|  319   } while (iStart <= iEnd); |  | 
|  320   return nullptr; |  | 
|  321 } |  | 
|  322  |  | 
|  323 const XFA_PROPERTY* XFA_GetPropertyOfElement(XFA_Element eElement, |  | 
|  324                                              XFA_Element eProperty, |  | 
|  325                                              uint32_t dwPacket) { |  | 
|  326   int32_t iCount = 0; |  | 
|  327   const XFA_PROPERTY* pProperties = XFA_GetElementProperties(eElement, iCount); |  | 
|  328   if (!pProperties || iCount < 1) |  | 
|  329     return nullptr; |  | 
|  330  |  | 
|  331   auto it = std::find_if(pProperties, pProperties + iCount, |  | 
|  332                          [eProperty](const XFA_PROPERTY& prop) { |  | 
|  333                            return prop.eName == eProperty; |  | 
|  334                          }); |  | 
|  335   if (it == pProperties + iCount) |  | 
|  336     return nullptr; |  | 
|  337  |  | 
|  338   const XFA_ELEMENTINFO* pInfo = XFA_GetElementByID(eProperty); |  | 
|  339   ASSERT(pInfo); |  | 
|  340   if (dwPacket != XFA_XDPPACKET_UNKNOWN && !(dwPacket & pInfo->dwPackets)) |  | 
|  341     return nullptr; |  | 
|  342   return it; |  | 
|  343 } |  | 
|  344  |  | 
|  345 const XFA_PROPERTY* XFA_GetElementProperties(XFA_Element eElement, |  | 
|  346                                              int32_t& iCount) { |  | 
|  347   if (eElement == XFA_Element::Unknown) |  | 
|  348     return nullptr; |  | 
|  349  |  | 
|  350   const XFA_ELEMENTHIERARCHY* pElement = |  | 
|  351       g_XFAElementPropertyIndex + static_cast<int32_t>(eElement); |  | 
|  352   iCount = pElement->wCount; |  | 
|  353   return g_XFAElementPropertyData + pElement->wStart; |  | 
|  354 } |  | 
|  355  |  | 
|  356 const uint8_t* XFA_GetElementAttributes(XFA_Element eElement, int32_t& iCount) { |  | 
|  357   if (eElement == XFA_Element::Unknown) |  | 
|  358     return nullptr; |  | 
|  359  |  | 
|  360   const XFA_ELEMENTHIERARCHY* pElement = |  | 
|  361       g_XFAElementAttributeIndex + static_cast<int32_t>(eElement); |  | 
|  362   iCount = pElement->wCount; |  | 
|  363   return g_XFAElementAttributeData + pElement->wStart; |  | 
|  364 } |  | 
|  365  |  | 
|  366 const XFA_ELEMENTINFO* XFA_GetElementByID(XFA_Element eName) { |  | 
|  367   return eName != XFA_Element::Unknown |  | 
|  368              ? g_XFAElementData + static_cast<int32_t>(eName) |  | 
|  369              : nullptr; |  | 
|  370 } |  | 
|  371  |  | 
|  372 XFA_Element XFA_GetElementTypeForName(const CFX_WideStringC& wsName) { |  | 
|  373   if (wsName.IsEmpty()) |  | 
|  374     return XFA_Element::Unknown; |  | 
|  375  |  | 
|  376   uint32_t uHash = FX_HashCode_GetW(wsName, false); |  | 
|  377   const XFA_ELEMENTINFO* pEnd = g_XFAElementData + g_iXFAElementCount; |  | 
|  378   auto pInfo = std::lower_bound(g_XFAElementData, pEnd, uHash, |  | 
|  379                                 [](const XFA_ELEMENTINFO& info, uint32_t hash) { |  | 
|  380                                   return info.uHash < hash; |  | 
|  381                                 }); |  | 
|  382   if (pInfo < pEnd && pInfo->uHash == uHash) |  | 
|  383     return pInfo->eName; |  | 
|  384   return XFA_Element::Unknown; |  | 
|  385 } |  | 
|  386  |  | 
|  387 CXFA_Measurement XFA_GetAttributeDefaultValue_Measure(XFA_Element eElement, |  | 
|  388                                                       XFA_ATTRIBUTE eAttribute, |  | 
|  389                                                       uint32_t dwPacket) { |  | 
|  390   void* pValue; |  | 
|  391   if (XFA_GetAttributeDefaultValue(pValue, eElement, eAttribute, |  | 
|  392                                    XFA_ATTRIBUTETYPE_Measure, dwPacket)) { |  | 
|  393     return *(CXFA_Measurement*)pValue; |  | 
|  394   } |  | 
|  395   return CXFA_Measurement(); |  | 
|  396 } |  | 
|  397  |  | 
|  398 FX_BOOL XFA_GetAttributeDefaultValue(void*& pValue, |  | 
|  399                                      XFA_Element eElement, |  | 
|  400                                      XFA_ATTRIBUTE eAttribute, |  | 
|  401                                      XFA_ATTRIBUTETYPE eType, |  | 
|  402                                      uint32_t dwPacket) { |  | 
|  403   const XFA_ATTRIBUTEINFO* pInfo = XFA_GetAttributeByID(eAttribute); |  | 
|  404   if (!pInfo) |  | 
|  405     return FALSE; |  | 
|  406   if (dwPacket && (dwPacket & pInfo->dwPackets) == 0) |  | 
|  407     return FALSE; |  | 
|  408   if (pInfo->eType == eType) { |  | 
|  409     pValue = pInfo->pDefValue; |  | 
|  410     return TRUE; |  | 
|  411   } |  | 
|  412   if (pInfo->eType == XFA_ATTRIBUTETYPE_NOTSURE) { |  | 
|  413     const XFA_NOTSUREATTRIBUTE* pAttr = |  | 
|  414         XFA_GetNotsureAttribute(eElement, eAttribute, eType); |  | 
|  415     if (pAttr) { |  | 
|  416       pValue = pAttr->pValue; |  | 
|  417       return TRUE; |  | 
|  418     } |  | 
|  419   } |  | 
|  420   return FALSE; |  | 
|  421 } |  | 
|  422  |  | 
|  423 const XFA_ATTRIBUTEINFO* XFA_GetAttributeByName(const CFX_WideStringC& wsName) { |  | 
|  424   if (wsName.IsEmpty()) |  | 
|  425     return nullptr; |  | 
|  426  |  | 
|  427   uint32_t uHash = FX_HashCode_GetW(wsName, false); |  | 
|  428   int32_t iStart = 0; |  | 
|  429   int32_t iEnd = g_iXFAAttributeCount - 1; |  | 
|  430   do { |  | 
|  431     int32_t iMid = (iStart + iEnd) / 2; |  | 
|  432     const XFA_ATTRIBUTEINFO* pInfo = g_XFAAttributeData + iMid; |  | 
|  433     if (uHash == pInfo->uHash) |  | 
|  434       return pInfo; |  | 
|  435     if (uHash < pInfo->uHash) |  | 
|  436       iEnd = iMid - 1; |  | 
|  437     else |  | 
|  438       iStart = iMid + 1; |  | 
|  439   } while (iStart <= iEnd); |  | 
|  440   return nullptr; |  | 
|  441 } |  | 
|  442  |  | 
|  443 const XFA_ATTRIBUTEINFO* XFA_GetAttributeByID(XFA_ATTRIBUTE eName) { |  | 
|  444   return (eName < g_iXFAAttributeCount) ? (g_XFAAttributeData + eName) |  | 
|  445                                         : nullptr; |  | 
|  446 } |  | 
|  447  |  | 
|  448 const XFA_ATTRIBUTEENUMINFO* XFA_GetAttributeEnumByName( |  | 
|  449     const CFX_WideStringC& wsName) { |  | 
|  450   if (wsName.IsEmpty()) |  | 
|  451     return nullptr; |  | 
|  452  |  | 
|  453   uint32_t uHash = FX_HashCode_GetW(wsName, false); |  | 
|  454   int32_t iStart = 0; |  | 
|  455   int32_t iEnd = g_iXFAEnumCount - 1; |  | 
|  456   do { |  | 
|  457     int32_t iMid = (iStart + iEnd) / 2; |  | 
|  458     const XFA_ATTRIBUTEENUMINFO* pInfo = g_XFAEnumData + iMid; |  | 
|  459     if (uHash == pInfo->uHash) |  | 
|  460       return pInfo; |  | 
|  461     if (uHash < pInfo->uHash) |  | 
|  462       iEnd = iMid - 1; |  | 
|  463     else |  | 
|  464       iStart = iMid + 1; |  | 
|  465   } while (iStart <= iEnd); |  | 
|  466   return nullptr; |  | 
|  467 } |  | 
|  468  |  | 
|  469 const XFA_PACKETINFO* XFA_GetPacketByIndex(XFA_PACKET ePacket) { |  | 
|  470   return g_XFAPacketData + ePacket; |  | 
|  471 } |  | 
|  472  |  | 
|  473 const XFA_PACKETINFO* XFA_GetPacketByID(uint32_t dwPacket) { |  | 
|  474   int32_t iStart = 0, iEnd = g_iXFAPacketCount - 1; |  | 
|  475   do { |  | 
|  476     int32_t iMid = (iStart + iEnd) / 2; |  | 
|  477     uint32_t dwFind = (g_XFAPacketData + iMid)->eName; |  | 
|  478     if (dwPacket == dwFind) |  | 
|  479       return g_XFAPacketData + iMid; |  | 
|  480     if (dwPacket < dwFind) |  | 
|  481       iEnd = iMid - 1; |  | 
|  482     else |  | 
|  483       iStart = iMid + 1; |  | 
|  484   } while (iStart <= iEnd); |  | 
|  485   return nullptr; |  | 
|  486 } |  | 
| OLD | NEW |