Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(339)

Side by Side Diff: third_party/libxslt/libxslt/pattern.c

Issue 1848793005: Roll libxslt to 891681e3e948f31732229f53cb6db7215f740fc7 (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « third_party/libxslt/libxslt/numbers.c ('k') | third_party/libxslt/libxslt/preproc.c » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * pattern.c: Implemetation of the template match compilation and lookup 2 * pattern.c: Implemetation of the template match compilation and lookup
3 * 3 *
4 * Reference: 4 * Reference:
5 * http://www.w3.org/TR/1999/REC-xslt-19991116 5 * http://www.w3.org/TR/1999/REC-xslt-19991116
6 * 6 *
7 * See Copyright for the status of this software. 7 * See Copyright for the status of this software.
8 * 8 *
9 * daniel@veillard.com 9 * daniel@veillard.com
10 */ 10 */
(...skipping 433 matching lines...) Expand 10 before | Expand all | Expand 10 after
444 comp->steps[j].indexExtra = t; 444 comp->steps[j].indexExtra = t;
445 t = comp->steps[i].lenExtra; 445 t = comp->steps[i].lenExtra;
446 comp->steps[i].lenExtra = comp->steps[j].lenExtra; 446 comp->steps[i].lenExtra = comp->steps[j].lenExtra;
447 comp->steps[j].lenExtra = t; 447 comp->steps[j].lenExtra = t;
448 j--; 448 j--;
449 i++; 449 i++;
450 } 450 }
451 xsltCompMatchAdd(ctxt, comp, XSLT_OP_END, NULL, NULL, 0); 451 xsltCompMatchAdd(ctxt, comp, XSLT_OP_END, NULL, NULL, 0);
452 452
453 /* 453 /*
454 * detect consecutive XSLT_OP_PREDICATE indicating a direct 454 * Detect consecutive XSLT_OP_PREDICATE and predicates on ops which
455 * matching should be done. 455 * haven't been optimized yet indicating a direct matching should be done.
456 */ 456 */
457 for (i = 0;i < comp->nbStep - 1;i++) { 457 for (i = 0;i < comp->nbStep - 1;i++) {
458 if ((comp->steps[i].op == XSLT_OP_PREDICATE) && 458 xsltOp op = comp->steps[i].op;
459
460 if ((op != XSLT_OP_ELEM) &&
461 (op != XSLT_OP_ALL) &&
459 (comp->steps[i + 1].op == XSLT_OP_PREDICATE)) { 462 (comp->steps[i + 1].op == XSLT_OP_PREDICATE)) {
460 463
461 comp->direct = 1; 464 comp->direct = 1;
462 if (comp->pattern[0] != '/') { 465 if (comp->pattern[0] != '/') {
463 xmlChar *query; 466 xmlChar *query;
464 467
465 query = xmlStrdup((const xmlChar *)"//"); 468 query = xmlStrdup((const xmlChar *)"//");
466 query = xmlStrcat(query, comp->pattern); 469 query = xmlStrcat(query, comp->pattern);
467 470
468 xmlFree((xmlChar *) comp->pattern); 471 xmlFree((xmlChar *) comp->pattern);
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after
614 } 617 }
615 } 618 }
616 } else { 619 } else {
617 } 620 }
618 if (nocache == 1) 621 if (nocache == 1)
619 xmlXPathFreeObject(list); 622 xmlXPathFreeObject(list);
620 return(0); 623 return(0);
621 } 624 }
622 625
623 /** 626 /**
627 * xsltTestPredicateMatch:
628 * @ctxt: a XSLT process context
629 * @comp: the precompiled pattern
630 * @node: a node
631 * @step: the predicate step
632 * @sel: the previous step
633 *
634 * Test whether the node matches the predicate
635 *
636 * Returns 1 if it matches, 0 if it doesn't and -1 in case of failure
637 */
638 static int
639 xsltTestPredicateMatch(xsltTransformContextPtr ctxt, xsltCompMatchPtr comp,
640 xmlNodePtr node, xsltStepOpPtr step,
641 xsltStepOpPtr sel) {
642 xmlNodePtr oldNode;
643 xmlDocPtr doc;
644 int oldCS, oldCP;
645 int pos = 0, len = 0;
646 int isRVT;
647 int match;
648
649 if (step->value == NULL)
650 return(0);
651 if (step->comp == NULL)
652 return(0);
653
654 doc = node->doc;
655 if (XSLT_IS_RES_TREE_FRAG(doc))
656 isRVT = 1;
657 else
658 isRVT = 0;
659
660 /*
661 * Recompute contextSize and proximityPosition.
662 *
663 * TODO: Make this work for additional ops. Currently, only XSLT_OP_ELEM
664 * and XSLT_OP_ALL are supported.
665 */
666 oldCS = ctxt->xpathCtxt->contextSize;
667 oldCP = ctxt->xpathCtxt->proximityPosition;
668 if ((sel != NULL) &&
669 (sel->op == XSLT_OP_ELEM) &&
670 (sel->value != NULL) &&
671 (node->type == XML_ELEMENT_NODE) &&
672 (node->parent != NULL)) {
673 xmlNodePtr previous;
674 int nocache = 0;
675
676 previous = (xmlNodePtr)
677 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr);
678 if ((previous != NULL) &&
679 (previous->parent == node->parent)) {
680 /*
681 * just walk back to adjust the index
682 */
683 int indx = 0;
684 xmlNodePtr sibling = node;
685
686 while (sibling != NULL) {
687 if (sibling == previous)
688 break;
689 if ((sibling->type == XML_ELEMENT_NODE) &&
690 (previous->name != NULL) &&
691 (sibling->name != NULL) &&
692 (previous->name[0] == sibling->name[0]) &&
693 (xmlStrEqual(previous->name, sibling->name)))
694 {
695 if ((sel->value2 == NULL) ||
696 ((sibling->ns != NULL) &&
697 (xmlStrEqual(sel->value2, sibling->ns->href))))
698 indx++;
699 }
700 sibling = sibling->prev;
701 }
702 if (sibling == NULL) {
703 /* hum going backward in document order ... */
704 indx = 0;
705 sibling = node;
706 while (sibling != NULL) {
707 if (sibling == previous)
708 break;
709 if ((sibling->type == XML_ELEMENT_NODE) &&
710 (previous->name != NULL) &&
711 (sibling->name != NULL) &&
712 (previous->name[0] == sibling->name[0]) &&
713 (xmlStrEqual(previous->name, sibling->name)))
714 {
715 if ((sel->value2 == NULL) ||
716 ((sibling->ns != NULL) &&
717 (xmlStrEqual(sel->value2,
718 sibling->ns->href))))
719 {
720 indx--;
721 }
722 }
723 sibling = sibling->next;
724 }
725 }
726 if (sibling != NULL) {
727 pos = XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) + indx;
728 /*
729 * If the node is in a Value Tree we need to
730 * save len, but cannot cache the node!
731 * (bugs 153137 and 158840)
732 */
733 if (node->doc != NULL) {
734 len = XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival);
735 if (!isRVT) {
736 XSLT_RUNTIME_EXTRA(ctxt,
737 sel->previousExtra, ptr) = node;
738 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) = pos;
739 }
740 }
741 } else
742 pos = 0;
743 } else {
744 /*
745 * recompute the index
746 */
747 xmlNodePtr parent = node->parent;
748 xmlNodePtr siblings = NULL;
749
750 if (parent) siblings = parent->children;
751
752 while (siblings != NULL) {
753 if (siblings->type == XML_ELEMENT_NODE) {
754 if (siblings == node) {
755 len++;
756 pos = len;
757 } else if ((node->name != NULL) &&
758 (siblings->name != NULL) &&
759 (node->name[0] == siblings->name[0]) &&
760 (xmlStrEqual(node->name, siblings->name))) {
761 if ((sel->value2 == NULL) ||
762 ((siblings->ns != NULL) &&
763 (xmlStrEqual(sel->value2, siblings->ns->href))))
764 len++;
765 }
766 }
767 siblings = siblings->next;
768 }
769 if ((parent == NULL) || (node->doc == NULL))
770 nocache = 1;
771 else {
772 while (parent->parent != NULL)
773 parent = parent->parent;
774 if (((parent->type != XML_DOCUMENT_NODE) &&
775 (parent->type != XML_HTML_DOCUMENT_NODE)) ||
776 (parent != (xmlNodePtr) node->doc))
777 nocache = 1;
778 }
779 }
780 if (pos != 0) {
781 ctxt->xpathCtxt->contextSize = len;
782 ctxt->xpathCtxt->proximityPosition = pos;
783 /*
784 * If the node is in a Value Tree we cannot
785 * cache it !
786 */
787 if ((!isRVT) && (node->doc != NULL) &&
788 (nocache == 0)) {
789 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr) = node;
790 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) = pos;
791 XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival) = len;
792 }
793 }
794 } else if ((sel != NULL) && (sel->op == XSLT_OP_ALL) &&
795 (node->type == XML_ELEMENT_NODE)) {
796 xmlNodePtr previous;
797 int nocache = 0;
798
799 previous = (xmlNodePtr)
800 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr);
801 if ((previous != NULL) &&
802 (previous->parent == node->parent)) {
803 /*
804 * just walk back to adjust the index
805 */
806 int indx = 0;
807 xmlNodePtr sibling = node;
808
809 while (sibling != NULL) {
810 if (sibling == previous)
811 break;
812 if (sibling->type == XML_ELEMENT_NODE)
813 indx++;
814 sibling = sibling->prev;
815 }
816 if (sibling == NULL) {
817 /* hum going backward in document order ... */
818 indx = 0;
819 sibling = node;
820 while (sibling != NULL) {
821 if (sibling == previous)
822 break;
823 if (sibling->type == XML_ELEMENT_NODE)
824 indx--;
825 sibling = sibling->next;
826 }
827 }
828 if (sibling != NULL) {
829 pos = XSLT_RUNTIME_EXTRA(ctxt,
830 sel->indexExtra, ival) + indx;
831 /*
832 * If the node is in a Value Tree we cannot
833 * cache it !
834 */
835 if ((node->doc != NULL) && !isRVT) {
836 len = XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival);
837 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr) = node;
838 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) = pos;
839 }
840 } else
841 pos = 0;
842 } else {
843 /*
844 * recompute the index
845 */
846 xmlNodePtr parent = node->parent;
847 xmlNodePtr siblings = NULL;
848
849 if (parent) siblings = parent->children;
850
851 while (siblings != NULL) {
852 if (siblings->type == XML_ELEMENT_NODE) {
853 len++;
854 if (siblings == node) {
855 pos = len;
856 }
857 }
858 siblings = siblings->next;
859 }
860 if ((parent == NULL) || (node->doc == NULL))
861 nocache = 1;
862 else {
863 while (parent->parent != NULL)
864 parent = parent->parent;
865 if (((parent->type != XML_DOCUMENT_NODE) &&
866 (parent->type != XML_HTML_DOCUMENT_NODE)) ||
867 (parent != (xmlNodePtr) node->doc))
868 nocache = 1;
869 }
870 }
871 if (pos != 0) {
872 ctxt->xpathCtxt->contextSize = len;
873 ctxt->xpathCtxt->proximityPosition = pos;
874 /*
875 * If the node is in a Value Tree we cannot
876 * cache it !
877 */
878 if ((node->doc != NULL) && (nocache == 0) && !isRVT) {
879 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr) = node;
880 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) = pos;
881 XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival) = len;
882 }
883 }
884 }
885
886 oldNode = ctxt->node;
887 ctxt->node = node;
888
889 match = xsltEvalXPathPredicate(ctxt, step->comp, comp->nsList, comp->nsNr);
890
891 if (pos != 0) {
892 ctxt->xpathCtxt->contextSize = oldCS;
893 ctxt->xpathCtxt->proximityPosition = oldCP;
894 }
895 ctxt->node = oldNode;
896
897 return match;
898 }
899
900 /**
624 * xsltTestCompMatch: 901 * xsltTestCompMatch:
625 * @ctxt: a XSLT process context 902 * @ctxt: a XSLT process context
626 * @comp: the precompiled pattern 903 * @comp: the precompiled pattern
627 * @node: a node 904 * @node: a node
628 * @mode: the mode name or NULL 905 * @mode: the mode name or NULL
629 * @modeURI: the mode URI or NULL 906 * @modeURI: the mode URI or NULL
630 * 907 *
631 * Test whether the node matches the pattern 908 * Test whether the node matches the pattern
632 * 909 *
633 * Returns 1 if it matches, 0 if it doesn't and -1 in case of failure 910 * Returns 1 if it matches, 0 if it doesn't and -1 in case of failure
634 */ 911 */
635 static int 912 static int
636 xsltTestCompMatch(xsltTransformContextPtr ctxt, xsltCompMatchPtr comp, 913 xsltTestCompMatch(xsltTransformContextPtr ctxt, xsltCompMatchPtr comp,
637 » xmlNodePtr node, const xmlChar *mode, 914 » xmlNodePtr matchNode, const xmlChar *mode,
638 const xmlChar *modeURI) { 915 const xmlChar *modeURI) {
639 int i; 916 int i;
917 xmlNodePtr node = matchNode;
640 xsltStepOpPtr step, sel = NULL; 918 xsltStepOpPtr step, sel = NULL;
641 xsltStepStates states = {0, 0, NULL}; /* // may require backtrack */ 919 xsltStepStates states = {0, 0, NULL}; /* // may require backtrack */
642 920
643 if ((comp == NULL) || (node == NULL) || (ctxt == NULL)) { 921 if ((comp == NULL) || (node == NULL) || (ctxt == NULL)) {
644 xsltTransformError(ctxt, NULL, node, 922 xsltTransformError(ctxt, NULL, node,
645 "xsltTestCompMatch: null arg\n"); 923 "xsltTestCompMatch: null arg\n");
646 return(-1); 924 return(-1);
647 } 925 }
648 if (mode != NULL) { 926 if (mode != NULL) {
649 if (comp->mode == NULL) 927 if (comp->mode == NULL)
(...skipping 197 matching lines...) Expand 10 before | Expand all | Expand 10 after
847 goto rollback; 1125 goto rollback;
848 if (!xmlStrEqual(step->value, node->ns->href)) 1126 if (!xmlStrEqual(step->value, node->ns->href))
849 goto rollback; 1127 goto rollback;
850 } 1128 }
851 break; 1129 break;
852 case XSLT_OP_ALL: 1130 case XSLT_OP_ALL:
853 if (node->type != XML_ELEMENT_NODE) 1131 if (node->type != XML_ELEMENT_NODE)
854 goto rollback; 1132 goto rollback;
855 break; 1133 break;
856 case XSLT_OP_PREDICATE: { 1134 case XSLT_OP_PREDICATE: {
857 xmlNodePtr oldNode;
858 xmlDocPtr doc;
859 int oldCS, oldCP;
860 int pos = 0, len = 0;
861 int isRVT;
862
863 /* 1135 /*
864 » » * when there is cascading XSLT_OP_PREDICATE, then use a 1136 » » * When there is cascading XSLT_OP_PREDICATE or a predicate
1137 » » * after an op which hasn't been optimized yet, then use a
865 * direct computation approach. It's not done directly 1138 * direct computation approach. It's not done directly
866 * at the beginning of the routine to filter out as much 1139 * at the beginning of the routine to filter out as much
867 * as possible this costly computation. 1140 * as possible this costly computation.
868 */ 1141 */
869 if (comp->direct) { 1142 if (comp->direct) {
870 if (states.states != NULL) { 1143 if (states.states != NULL) {
871 /* Free the rollback states */ 1144 /* Free the rollback states */
872 xmlFree(states.states); 1145 xmlFree(states.states);
873 } 1146 }
874 » » return(xsltTestCompMatchDirect(ctxt, comp, node, 1147 » » return(xsltTestCompMatchDirect(ctxt, comp, matchNode,
875 comp->nsList, comp->nsNr)); 1148 comp->nsList, comp->nsNr));
876 } 1149 }
877 1150
878 » » doc = node->doc; 1151 » » if (!xsltTestPredicateMatch(ctxt, comp, node, step, sel))
879 » » if (XSLT_IS_RES_TREE_FRAG(doc)) 1152 » » goto rollback;
880 » » isRVT = 1;
881 » » else
882 » » isRVT = 0;
883 1153
884 /*
885 * Depending on the last selection, one may need to
886 * recompute contextSize and proximityPosition.
887 */
888 oldCS = ctxt->xpathCtxt->contextSize;
889 oldCP = ctxt->xpathCtxt->proximityPosition;
890 if ((sel != NULL) &&
891 (sel->op == XSLT_OP_ELEM) &&
892 (sel->value != NULL) &&
893 (node->type == XML_ELEMENT_NODE) &&
894 (node->parent != NULL)) {
895 xmlNodePtr previous;
896 int nocache = 0;
897
898 previous = (xmlNodePtr)
899 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr);
900 if ((previous != NULL) &&
901 (previous->parent == node->parent)) {
902 /*
903 * just walk back to adjust the index
904 */
905 int indx = 0;
906 xmlNodePtr sibling = node;
907
908 while (sibling != NULL) {
909 if (sibling == previous)
910 break;
911 if ((sibling->type == XML_ELEMENT_NODE) &&
912 (previous->name != NULL) &&
913 (sibling->name != NULL) &&
914 (previous->name[0] == sibling->name[0]) &&
915 (xmlStrEqual(previous->name, sibling->name)))
916 {
917 if ((sel->value2 == NULL) ||
918 ((sibling->ns != NULL) &&
919 (xmlStrEqual(sel->value2,
920 sibling->ns->href))))
921 indx++;
922 }
923 sibling = sibling->prev;
924 }
925 if (sibling == NULL) {
926 /* hum going backward in document order ... */
927 indx = 0;
928 sibling = node;
929 while (sibling != NULL) {
930 if (sibling == previous)
931 break;
932 if ((sibling->type == XML_ELEMENT_NODE) &&
933 (previous->name != NULL) &&
934 (sibling->name != NULL) &&
935 (previous->name[0] == sibling->name[0]) &&
936 (xmlStrEqual(previous->name, sibling->name)) )
937 {
938 if ((sel->value2 == NULL) ||
939 ((sibling->ns != NULL) &&
940 (xmlStrEqual(sel->value2,
941 sibling->ns->href))))
942 {
943 indx--;
944 }
945 }
946 sibling = sibling->next;
947 }
948 }
949 if (sibling != NULL) {
950 pos = XSLT_RUNTIME_EXTRA(ctxt,
951 sel->indexExtra, ival) + indx;
952 /*
953 * If the node is in a Value Tree we need to
954 * save len, but cannot cache the node!
955 * (bugs 153137 and 158840)
956 */
957 if (node->doc != NULL) {
958 len = XSLT_RUNTIME_EXTRA(ctxt,
959 sel->lenExtra, ival);
960 if (!isRVT) {
961 XSLT_RUNTIME_EXTRA(ctxt,
962 sel->previousExtra, ptr) = node;
963 XSLT_RUNTIME_EXTRA(ctxt,
964 sel->indexExtra, ival) = pos;
965 }
966 }
967 } else
968 pos = 0;
969 } else {
970 /*
971 * recompute the index
972 */
973 xmlNodePtr parent = node->parent;
974 xmlNodePtr siblings = NULL;
975
976 if (parent) siblings = parent->children;
977
978 while (siblings != NULL) {
979 if (siblings->type == XML_ELEMENT_NODE) {
980 if (siblings == node) {
981 len++;
982 pos = len;
983 } else if ((node->name != NULL) &&
984 (siblings->name != NULL) &&
985 (node->name[0] == siblings->name[0]) &&
986 (xmlStrEqual(node->name, siblings->name))) {
987 if ((sel->value2 == NULL) ||
988 ((siblings->ns != NULL) &&
989 (xmlStrEqual(sel->value2,
990 siblings->ns->href))))
991 len++;
992 }
993 }
994 siblings = siblings->next;
995 }
996 if ((parent == NULL) || (node->doc == NULL))
997 nocache = 1;
998 else {
999 while (parent->parent != NULL)
1000 parent = parent->parent;
1001 if (((parent->type != XML_DOCUMENT_NODE) &&
1002 (parent->type != XML_HTML_DOCUMENT_NODE)) ||
1003 (parent != (xmlNodePtr) node->doc))
1004 nocache = 1;
1005 }
1006 }
1007 if (pos != 0) {
1008 ctxt->xpathCtxt->contextSize = len;
1009 ctxt->xpathCtxt->proximityPosition = pos;
1010 /*
1011 * If the node is in a Value Tree we cannot
1012 * cache it !
1013 */
1014 if ((!isRVT) && (node->doc != NULL) &&
1015 (nocache == 0)) {
1016 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr) =
1017 node;
1018 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) =
1019 pos;
1020 XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival) =
1021 len;
1022 }
1023 }
1024 } else if ((sel != NULL) && (sel->op == XSLT_OP_ALL) &&
1025 (node->type == XML_ELEMENT_NODE)) {
1026 xmlNodePtr previous;
1027 int nocache = 0;
1028
1029 previous = (xmlNodePtr)
1030 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr);
1031 if ((previous != NULL) &&
1032 (previous->parent == node->parent)) {
1033 /*
1034 * just walk back to adjust the index
1035 */
1036 int indx = 0;
1037 xmlNodePtr sibling = node;
1038
1039 while (sibling != NULL) {
1040 if (sibling == previous)
1041 break;
1042 if (sibling->type == XML_ELEMENT_NODE)
1043 indx++;
1044 sibling = sibling->prev;
1045 }
1046 if (sibling == NULL) {
1047 /* hum going backward in document order ... */
1048 indx = 0;
1049 sibling = node;
1050 while (sibling != NULL) {
1051 if (sibling == previous)
1052 break;
1053 if (sibling->type == XML_ELEMENT_NODE)
1054 indx--;
1055 sibling = sibling->next;
1056 }
1057 }
1058 if (sibling != NULL) {
1059 pos = XSLT_RUNTIME_EXTRA(ctxt,
1060 sel->indexExtra, ival) + indx;
1061 /*
1062 * If the node is in a Value Tree we cannot
1063 * cache it !
1064 */
1065 if ((node->doc != NULL) && !isRVT) {
1066 len = XSLT_RUNTIME_EXTRA(ctxt,
1067 sel->lenExtra, ival);
1068 XSLT_RUNTIME_EXTRA(ctxt,
1069 sel->previousExtra, ptr) = node;
1070 XSLT_RUNTIME_EXTRA(ctxt,
1071 sel->indexExtra, ival) = pos;
1072 }
1073 } else
1074 pos = 0;
1075 } else {
1076 /*
1077 * recompute the index
1078 */
1079 xmlNodePtr parent = node->parent;
1080 xmlNodePtr siblings = NULL;
1081
1082 if (parent) siblings = parent->children;
1083
1084 while (siblings != NULL) {
1085 if (siblings->type == XML_ELEMENT_NODE) {
1086 len++;
1087 if (siblings == node) {
1088 pos = len;
1089 }
1090 }
1091 siblings = siblings->next;
1092 }
1093 if ((parent == NULL) || (node->doc == NULL))
1094 nocache = 1;
1095 else {
1096 while (parent->parent != NULL)
1097 parent = parent->parent;
1098 if (((parent->type != XML_DOCUMENT_NODE) &&
1099 (parent->type != XML_HTML_DOCUMENT_NODE)) ||
1100 (parent != (xmlNodePtr) node->doc))
1101 nocache = 1;
1102 }
1103 }
1104 if (pos != 0) {
1105 ctxt->xpathCtxt->contextSize = len;
1106 ctxt->xpathCtxt->proximityPosition = pos;
1107 /*
1108 * If the node is in a Value Tree we cannot
1109 * cache it !
1110 */
1111 if ((node->doc != NULL) && (nocache == 0) && !isRVT) {
1112 XSLT_RUNTIME_EXTRA(ctxt, sel->previousExtra, ptr) =
1113 node;
1114 XSLT_RUNTIME_EXTRA(ctxt, sel->indexExtra, ival) =
1115 pos;
1116 XSLT_RUNTIME_EXTRA(ctxt, sel->lenExtra, ival) =
1117 len;
1118 }
1119 }
1120 }
1121 oldNode = ctxt->node;
1122 ctxt->node = node;
1123
1124 if (step->value == NULL)
1125 goto wrong_index;
1126 if (step->comp == NULL)
1127 goto wrong_index;
1128
1129 if (!xsltEvalXPathPredicate(ctxt, step->comp, comp->nsList,
1130 comp->nsNr))
1131 goto wrong_index;
1132
1133 if (pos != 0) {
1134 ctxt->xpathCtxt->contextSize = oldCS;
1135 ctxt->xpathCtxt->proximityPosition = oldCP;
1136 }
1137 ctxt->node = oldNode;
1138 break; 1154 break;
1139 wrong_index:
1140 if (pos != 0) {
1141 ctxt->xpathCtxt->contextSize = oldCS;
1142 ctxt->xpathCtxt->proximityPosition = oldCP;
1143 }
1144 ctxt->node = oldNode;
1145 goto rollback;
1146 } 1155 }
1147 case XSLT_OP_PI: 1156 case XSLT_OP_PI:
1148 if (node->type != XML_PI_NODE) 1157 if (node->type != XML_PI_NODE)
1149 goto rollback; 1158 goto rollback;
1150 if (step->value != NULL) { 1159 if (step->value != NULL) {
1151 if (!xmlStrEqual(step->value, node->name)) 1160 if (!xmlStrEqual(step->value, node->name))
1152 goto rollback; 1161 goto rollback;
1153 } 1162 }
1154 break; 1163 break;
1155 case XSLT_OP_COMMENT: 1164 case XSLT_OP_COMMENT:
(...skipping 261 matching lines...) Expand 10 before | Expand all | Expand 10 after
1417 lit = xsltScanLiteral(ctxt); 1426 lit = xsltScanLiteral(ctxt);
1418 if (ctxt->error) { 1427 if (ctxt->error) {
1419 xsltTransformError(NULL, NULL, NULL, 1428 xsltTransformError(NULL, NULL, NULL,
1420 "xsltCompileIdKeyPattern : Literal expected\n"); 1429 "xsltCompileIdKeyPattern : Literal expected\n");
1421 return; 1430 return;
1422 } 1431 }
1423 SKIP_BLANKS; 1432 SKIP_BLANKS;
1424 if (CUR != ',') { 1433 if (CUR != ',') {
1425 xsltTransformError(NULL, NULL, NULL, 1434 xsltTransformError(NULL, NULL, NULL,
1426 "xsltCompileIdKeyPattern : , expected\n"); 1435 "xsltCompileIdKeyPattern : , expected\n");
1436 xmlFree(lit);
1427 ctxt->error = 1; 1437 ctxt->error = 1;
1428 return; 1438 return;
1429 } 1439 }
1430 NEXT; 1440 NEXT;
1431 SKIP_BLANKS; 1441 SKIP_BLANKS;
1432 lit2 = xsltScanLiteral(ctxt); 1442 lit2 = xsltScanLiteral(ctxt);
1433 if (ctxt->error) { 1443 if (ctxt->error) {
1434 xsltTransformError(NULL, NULL, NULL, 1444 xsltTransformError(NULL, NULL, NULL,
1435 "xsltCompileIdKeyPattern : Literal expected\n"); 1445 "xsltCompileIdKeyPattern : Literal expected\n");
1436 xmlFree(lit); 1446 xmlFree(lit);
(...skipping 636 matching lines...) Expand 10 before | Expand all | Expand 10 after
2073 const xmlChar *mode, const xmlChar *modeURI) { 2083 const xmlChar *mode, const xmlChar *modeURI) {
2074 xsltCompMatchPtr pat, list, next; 2084 xsltCompMatchPtr pat, list, next;
2075 /* 2085 /*
2076 * 'top' will point to style->xxxMatch ptr - declaring as 'void' 2086 * 'top' will point to style->xxxMatch ptr - declaring as 'void'
2077 * avoids gcc 'type-punned pointer' warning. 2087 * avoids gcc 'type-punned pointer' warning.
2078 */ 2088 */
2079 void **top = NULL; 2089 void **top = NULL;
2080 const xmlChar *name = NULL; 2090 const xmlChar *name = NULL;
2081 float priority; /* the priority */ 2091 float priority; /* the priority */
2082 2092
2083 if ((style == NULL) || (cur == NULL) || (cur->match == NULL)) 2093 if ((style == NULL) || (cur == NULL))
2084 return(-1); 2094 return(-1);
2085 2095
2096 /* Register named template */
2097 if (cur->name != NULL) {
2098 if (style->namedTemplates == NULL) {
2099 style->namedTemplates = xmlHashCreate(10);
2100 if (style->namedTemplates == NULL)
2101 return(-1);
2102 }
2103 else {
2104 void *dup = xmlHashLookup2(style->namedTemplates, cur->name,
2105 cur->nameURI);
2106 if (dup != NULL) {
2107 xsltTransformError(NULL, style, NULL,
2108 "xsl:template: error duplicate name '%s'\n",
2109 cur->name);
2110 style->errors++;
2111 return(-1);
2112 }
2113 }
2114
2115 xmlHashAddEntry2(style->namedTemplates, cur->name, cur->nameURI, cur);
2116 }
2117
2118 if (cur->match == NULL)
2119 return(0);
2120
2086 priority = cur->priority; 2121 priority = cur->priority;
2087 pat = xsltCompilePatternInternal(cur->match, style->doc, cur->elem, 2122 pat = xsltCompilePatternInternal(cur->match, style->doc, cur->elem,
2088 style, NULL, 1); 2123 style, NULL, 1);
2089 if (pat == NULL) 2124 if (pat == NULL)
2090 return(-1); 2125 return(-1);
2091 while (pat) { 2126 while (pat) {
2092 next = pat->next; 2127 next = pat->next;
2093 pat->next = NULL; 2128 pat->next = NULL;
2094 name = NULL; 2129 name = NULL;
2095 2130
(...skipping 449 matching lines...) Expand 10 before | Expand all | Expand 10 after
2545 if (style->attrMatch != NULL) 2580 if (style->attrMatch != NULL)
2546 xsltFreeCompMatchList(style->attrMatch); 2581 xsltFreeCompMatchList(style->attrMatch);
2547 if (style->parentMatch != NULL) 2582 if (style->parentMatch != NULL)
2548 xsltFreeCompMatchList(style->parentMatch); 2583 xsltFreeCompMatchList(style->parentMatch);
2549 if (style->textMatch != NULL) 2584 if (style->textMatch != NULL)
2550 xsltFreeCompMatchList(style->textMatch); 2585 xsltFreeCompMatchList(style->textMatch);
2551 if (style->piMatch != NULL) 2586 if (style->piMatch != NULL)
2552 xsltFreeCompMatchList(style->piMatch); 2587 xsltFreeCompMatchList(style->piMatch);
2553 if (style->commentMatch != NULL) 2588 if (style->commentMatch != NULL)
2554 xsltFreeCompMatchList(style->commentMatch); 2589 xsltFreeCompMatchList(style->commentMatch);
2590 if (style->namedTemplates != NULL)
2591 xmlHashFree(style->namedTemplates, NULL);
2555 } 2592 }
2556 2593
OLDNEW
« no previous file with comments | « third_party/libxslt/libxslt/numbers.c ('k') | third_party/libxslt/libxslt/preproc.c » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698