1 /**********************************************************************
2 regparse.c - Oniguruma (regular expression library)
3 **********************************************************************/
5 * Copyright (c) 2002-2018 K.Kosako <sndgk393 AT ybb DOT ne DOT jp>
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33 #ifdef DEBUG_NODE_FREE
37 #define WARN_BUFSIZE 256
39 #define CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS
42 OnigSyntaxType OnigSyntaxOniguruma = {
43 (( SYN_GNU_REGEX_OP | ONIG_SYN_OP_QMARK_NON_GREEDY |
44 ONIG_SYN_OP_ESC_OCTAL3 | ONIG_SYN_OP_ESC_X_HEX2 |
45 ONIG_SYN_OP_ESC_X_BRACE_HEX8 | ONIG_SYN_OP_ESC_O_BRACE_OCTAL |
46 ONIG_SYN_OP_ESC_CONTROL_CHARS |
47 ONIG_SYN_OP_ESC_C_CONTROL )
48 & ~ONIG_SYN_OP_ESC_LTGT_WORD_BEGIN_END )
49 , ( ONIG_SYN_OP2_QMARK_GROUP_EFFECT |
50 ONIG_SYN_OP2_OPTION_RUBY |
51 ONIG_SYN_OP2_QMARK_LT_NAMED_GROUP | ONIG_SYN_OP2_ESC_K_NAMED_BACKREF |
52 ONIG_SYN_OP2_QMARK_LPAREN_IF_ELSE |
53 ONIG_SYN_OP2_QMARK_TILDE_ABSENT_GROUP |
54 ONIG_SYN_OP2_QMARK_BRACE_CALLOUT |
55 ONIG_SYN_OP2_ESC_X_Y_GRAPHEME_CLUSTER |
56 ONIG_SYN_OP2_ESC_CAPITAL_R_GENERAL_NEWLINE |
57 ONIG_SYN_OP2_ESC_CAPITAL_N_O_SUPER_DOT |
58 ONIG_SYN_OP2_ESC_CAPITAL_K_KEEP |
59 ONIG_SYN_OP2_ESC_G_SUBEXP_CALL |
60 ONIG_SYN_OP2_ESC_P_BRACE_CHAR_PROPERTY |
61 ONIG_SYN_OP2_ESC_P_BRACE_CIRCUMFLEX_NOT |
62 ONIG_SYN_OP2_PLUS_POSSESSIVE_REPEAT |
63 ONIG_SYN_OP2_CCLASS_SET_OP | ONIG_SYN_OP2_ESC_CAPITAL_C_BAR_CONTROL |
64 ONIG_SYN_OP2_ESC_CAPITAL_M_BAR_META | ONIG_SYN_OP2_ESC_V_VTAB |
65 ONIG_SYN_OP2_ESC_H_XDIGIT | ONIG_SYN_OP2_ESC_U_HEX4 )
66 , ( SYN_GNU_REGEX_BV |
67 ONIG_SYN_ALLOW_INTERVAL_LOW_ABBREV |
68 ONIG_SYN_DIFFERENT_LEN_ALT_LOOK_BEHIND |
69 ONIG_SYN_CAPTURE_ONLY_NAMED_GROUP |
70 ONIG_SYN_ALLOW_MULTIPLEX_DEFINITION_NAME |
71 ONIG_SYN_FIXED_INTERVAL_IS_GREEDY_ONLY |
72 ONIG_SYN_WARN_CC_OP_NOT_ESCAPED |
73 ONIG_SYN_WARN_REDUNDANT_NESTED_REPEAT )
77 (OnigCodePoint )'\\' /* esc */
78 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anychar '.' */
79 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anytime '*' */
80 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* zero or one time '?' */
81 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* one or more time '+' */
82 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anychar anytime */
86 OnigSyntaxType OnigSyntaxRuby = {
87 (( SYN_GNU_REGEX_OP | ONIG_SYN_OP_QMARK_NON_GREEDY |
88 ONIG_SYN_OP_ESC_OCTAL3 | ONIG_SYN_OP_ESC_X_HEX2 |
89 ONIG_SYN_OP_ESC_X_BRACE_HEX8 | ONIG_SYN_OP_ESC_O_BRACE_OCTAL |
90 ONIG_SYN_OP_ESC_CONTROL_CHARS |
91 ONIG_SYN_OP_ESC_C_CONTROL )
92 & ~ONIG_SYN_OP_ESC_LTGT_WORD_BEGIN_END )
93 , ( ONIG_SYN_OP2_QMARK_GROUP_EFFECT |
94 ONIG_SYN_OP2_OPTION_RUBY |
95 ONIG_SYN_OP2_QMARK_LT_NAMED_GROUP | ONIG_SYN_OP2_ESC_K_NAMED_BACKREF |
96 ONIG_SYN_OP2_QMARK_LPAREN_IF_ELSE |
97 ONIG_SYN_OP2_QMARK_TILDE_ABSENT_GROUP |
98 ONIG_SYN_OP2_ESC_X_Y_GRAPHEME_CLUSTER |
99 ONIG_SYN_OP2_ESC_CAPITAL_R_GENERAL_NEWLINE |
100 ONIG_SYN_OP2_ESC_CAPITAL_K_KEEP |
101 ONIG_SYN_OP2_ESC_G_SUBEXP_CALL |
102 ONIG_SYN_OP2_ESC_P_BRACE_CHAR_PROPERTY |
103 ONIG_SYN_OP2_ESC_P_BRACE_CIRCUMFLEX_NOT |
104 ONIG_SYN_OP2_PLUS_POSSESSIVE_REPEAT |
105 ONIG_SYN_OP2_CCLASS_SET_OP | ONIG_SYN_OP2_ESC_CAPITAL_C_BAR_CONTROL |
106 ONIG_SYN_OP2_ESC_CAPITAL_M_BAR_META | ONIG_SYN_OP2_ESC_V_VTAB |
107 ONIG_SYN_OP2_ESC_H_XDIGIT | ONIG_SYN_OP2_ESC_U_HEX4 )
108 , ( SYN_GNU_REGEX_BV |
109 ONIG_SYN_ALLOW_INTERVAL_LOW_ABBREV |
110 ONIG_SYN_DIFFERENT_LEN_ALT_LOOK_BEHIND |
111 ONIG_SYN_CAPTURE_ONLY_NAMED_GROUP |
112 ONIG_SYN_ALLOW_MULTIPLEX_DEFINITION_NAME |
113 ONIG_SYN_FIXED_INTERVAL_IS_GREEDY_ONLY |
114 ONIG_SYN_WARN_CC_OP_NOT_ESCAPED |
115 ONIG_SYN_WARN_REDUNDANT_NESTED_REPEAT )
119 (OnigCodePoint )'\\' /* esc */
120 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anychar '.' */
121 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anytime '*' */
122 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* zero or one time '?' */
123 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* one or more time '+' */
124 , (OnigCodePoint )ONIG_INEFFECTIVE_META_CHAR /* anychar anytime */
128 OnigSyntaxType* OnigDefaultSyntax = ONIG_SYNTAX_ONIGURUMA;
130 extern void onig_null_warn(const char* s ARG_UNUSED) { }
132 #ifdef DEFAULT_WARN_FUNCTION
133 static OnigWarnFunc onig_warn = (OnigWarnFunc )DEFAULT_WARN_FUNCTION;
135 static OnigWarnFunc onig_warn = onig_null_warn;
138 #ifdef DEFAULT_VERB_WARN_FUNCTION
139 static OnigWarnFunc onig_verb_warn = (OnigWarnFunc )DEFAULT_VERB_WARN_FUNCTION;
141 static OnigWarnFunc onig_verb_warn = onig_null_warn;
144 extern void onig_set_warn_func(OnigWarnFunc f)
149 extern void onig_set_verb_warn_func(OnigWarnFunc f)
155 onig_warning(const char* s)
157 if (onig_warn == onig_null_warn) return ;
162 #define DEFAULT_MAX_CAPTURE_NUM 32767
164 static int MaxCaptureNum = DEFAULT_MAX_CAPTURE_NUM;
167 onig_set_capture_num_limit(int num)
169 if (num < 0) return -1;
175 static unsigned int ParseDepthLimit = DEFAULT_PARSE_DEPTH_LIMIT;
178 onig_get_parse_depth_limit(void)
180 return ParseDepthLimit;
184 onig_set_parse_depth_limit(unsigned int depth)
187 ParseDepthLimit = DEFAULT_PARSE_DEPTH_LIMIT;
189 ParseDepthLimit = depth;
194 positive_int_multiply(int x, int y)
196 if (x == 0 || y == 0) return 0;
205 bbuf_free(BBuf* bbuf)
207 if (IS_NOT_NULL(bbuf)) {
208 if (IS_NOT_NULL(bbuf->p)) xfree(bbuf->p);
214 bbuf_clone(BBuf** rto, BBuf* from)
219 *rto = to = (BBuf* )xmalloc(sizeof(BBuf));
220 CHECK_NULL_RETURN_MEMERR(to);
221 r = BB_INIT(to, from->alloc);
227 to->used = from->used;
228 xmemcpy(to->p, from->p, from->used);
232 static int backref_rel_to_abs(int rel_no, ScanEnv* env)
235 return env->num_mem + rel_no;
238 return env->num_mem + 1 + rel_no;
242 #define OPTION_ON(v,f) ((v) |= (f))
243 #define OPTION_OFF(v,f) ((v) &= ~(f))
245 #define OPTION_NEGATE(v,f,negative) (negative) ? ((v) &= ~(f)) : ((v) |= (f))
247 #define MBCODE_START_POS(enc) \
248 (OnigCodePoint )(ONIGENC_MBC_MINLEN(enc) > 1 ? 0 : 0x80)
250 #define SET_ALL_MULTI_BYTE_RANGE(enc, pbuf) \
251 add_code_range_to_buf(pbuf, MBCODE_START_POS(enc), ~((OnigCodePoint )0))
253 #define ADD_ALL_MULTI_BYTE_RANGE(enc, mbuf) do {\
254 if (! ONIGENC_IS_SINGLEBYTE(enc)) {\
255 r = SET_ALL_MULTI_BYTE_RANGE(enc, &(mbuf));\
256 if (r != 0) return r;\
261 #define BITSET_IS_EMPTY(bs,empty) do {\
264 for (i = 0; i < (int )BITSET_SIZE; i++) {\
272 bitset_set_range(BitSetRef bs, int from, int to)
275 for (i = from; i <= to && i < SINGLE_BYTE_SIZE; i++) {
276 BITSET_SET_BIT(bs, i);
282 bitset_set_all(BitSetRef bs)
285 for (i = 0; i < BITSET_SIZE; i++) { bs[i] = ~((Bits )0); }
290 bitset_invert(BitSetRef bs)
293 for (i = 0; i < (int )BITSET_SIZE; i++) { bs[i] = ~(bs[i]); }
297 bitset_invert_to(BitSetRef from, BitSetRef to)
300 for (i = 0; i < (int )BITSET_SIZE; i++) { to[i] = ~(from[i]); }
304 bitset_and(BitSetRef dest, BitSetRef bs)
307 for (i = 0; i < (int )BITSET_SIZE; i++) { dest[i] &= bs[i]; }
311 bitset_or(BitSetRef dest, BitSetRef bs)
314 for (i = 0; i < (int )BITSET_SIZE; i++) { dest[i] |= bs[i]; }
318 bitset_copy(BitSetRef dest, BitSetRef bs)
321 for (i = 0; i < (int )BITSET_SIZE; i++) { dest[i] = bs[i]; }
325 onig_strncmp(const UChar* s1, const UChar* s2, int n)
337 onig_strcpy(UChar* dest, const UChar* src, const UChar* end)
339 int len = (int )(end - src);
341 xmemcpy(dest, src, len);
342 dest[len] = (UChar )0;
347 strdup_with_null(OnigEncoding enc, UChar* s, UChar* end)
349 int slen, term_len, i;
352 slen = (int )(end - s);
353 term_len = ONIGENC_MBC_MINLEN(enc);
355 r = (UChar* )xmalloc(slen + term_len);
356 CHECK_NULL_RETURN(r);
359 for (i = 0; i < term_len; i++)
360 r[slen + i] = (UChar )0;
366 save_entry(ScanEnv* env, enum SaveType type, int* id)
368 int nid = env->save_num;
371 if (IS_NULL(env->saves)) {
373 env->saves = (SaveItem* )xmalloc(sizeof(SaveItem) * n);
374 CHECK_NULL_RETURN_MEMERR(env->saves);
375 env->save_alloc_num = n;
377 else if (env->save_alloc_num <= nid) {
378 int n = env->save_alloc_num * 2;
379 SaveItem* p = (SaveItem* )xrealloc(env->saves, sizeof(SaveItem) * n);
380 CHECK_NULL_RETURN_MEMERR(p);
382 env->save_alloc_num = n;
385 env->saves[nid].type = type;
393 /* scan pattern methods */
396 #define PFETCH_READY UChar* pfetch_prev
397 #define PEND (p < end ? 0 : 1)
398 #define PUNFETCH p = pfetch_prev
401 p += ONIGENC_MBC_ENC_LEN(enc, p); \
403 #define PFETCH(c) do { \
404 c = ONIGENC_MBC_TO_CODE(enc, p, end); \
406 p += ONIGENC_MBC_ENC_LEN(enc, p); \
409 #define PINC_S do { \
410 p += ONIGENC_MBC_ENC_LEN(enc, p); \
412 #define PFETCH_S(c) do { \
413 c = ONIGENC_MBC_TO_CODE(enc, p, end); \
414 p += ONIGENC_MBC_ENC_LEN(enc, p); \
417 #define PPEEK (p < end ? ONIGENC_MBC_TO_CODE(enc, p, end) : PEND_VALUE)
418 #define PPEEK_IS(c) (PPEEK == (OnigCodePoint )c)
421 strcat_capa(UChar* dest, UChar* dest_end, const UChar* src, const UChar* src_end,
427 r = (UChar* )xrealloc(dest, capa + 1);
429 r = (UChar* )xmalloc(capa + 1);
431 CHECK_NULL_RETURN(r);
432 onig_strcpy(r + (dest_end - dest), src, src_end);
436 /* dest on static area */
438 strcat_capa_from_static(UChar* dest, UChar* dest_end,
439 const UChar* src, const UChar* src_end, int capa)
443 r = (UChar* )xmalloc(capa + 1);
444 CHECK_NULL_RETURN(r);
445 onig_strcpy(r, dest, dest_end);
446 onig_strcpy(r + (dest_end - dest), src, src_end);
451 #ifdef USE_ST_LIBRARY
459 str_end_cmp(st_str_end_key* x, st_str_end_key* y)
464 if ((x->end - x->s) != (y->end - y->s))
470 c = (int )*p - (int )*q;
471 if (c != 0) return c;
480 str_end_hash(st_str_end_key* x)
487 val = val * 997 + (int )*p++;
490 return val + (val >> 5);
493 extern hash_table_type*
494 onig_st_init_strend_table_with_size(int size)
496 static struct st_hash_type hashType = {
501 return (hash_table_type* )
502 onig_st_init_table_with_size(&hashType, size);
506 onig_st_lookup_strend(hash_table_type* table, const UChar* str_key,
507 const UChar* end_key, hash_data_type *value)
511 key.s = (UChar* )str_key;
512 key.end = (UChar* )end_key;
514 return onig_st_lookup(table, (st_data_t )(&key), value);
518 onig_st_insert_strend(hash_table_type* table, const UChar* str_key,
519 const UChar* end_key, hash_data_type value)
524 key = (st_str_end_key* )xmalloc(sizeof(st_str_end_key));
525 CHECK_NULL_RETURN_MEMERR(key);
527 key->s = (UChar* )str_key;
528 key->end = (UChar* )end_key;
529 result = onig_st_insert(table, (st_data_t )key, value);
536 #endif /* USE_ST_LIBRARY */
539 #define INIT_NAME_BACKREFS_ALLOC_NUM 8
543 int name_len; /* byte length */
544 int back_num; /* number of backrefs */
550 #ifdef USE_ST_LIBRARY
552 typedef st_table NameTable;
553 typedef st_data_t HashDataType; /* 1.6 st.h doesn't define st_data_t type */
555 #define NAMEBUF_SIZE 24
556 #define NAMEBUF_SIZE_1 25
560 i_print_name_entry(UChar* key, NameEntry* e, void* arg)
563 FILE* fp = (FILE* )arg;
565 fprintf(fp, "%s: ", e->name);
566 if (e->back_num == 0)
568 else if (e->back_num == 1)
569 fprintf(fp, "%d", e->back_ref1);
571 for (i = 0; i < e->back_num; i++) {
572 if (i > 0) fprintf(fp, ", ");
573 fprintf(fp, "%d", e->back_refs[i]);
581 onig_print_names(FILE* fp, regex_t* reg)
583 NameTable* t = (NameTable* )reg->name_table;
585 if (IS_NOT_NULL(t)) {
586 fprintf(fp, "name table\n");
587 onig_st_foreach(t, i_print_name_entry, (HashDataType )fp);
592 #endif /* ONIG_DEBUG */
595 i_free_name_entry(UChar* key, NameEntry* e, void* arg ARG_UNUSED)
598 if (IS_NOT_NULL(e->back_refs)) xfree(e->back_refs);
605 names_clear(regex_t* reg)
607 NameTable* t = (NameTable* )reg->name_table;
609 if (IS_NOT_NULL(t)) {
610 onig_st_foreach(t, i_free_name_entry, 0);
616 onig_names_free(regex_t* reg)
621 r = names_clear(reg);
622 if (r != 0) return r;
624 t = (NameTable* )reg->name_table;
625 if (IS_NOT_NULL(t)) onig_st_free_table(t);
626 reg->name_table = (void* )NULL;
631 name_find(regex_t* reg, const UChar* name, const UChar* name_end)
634 NameTable* t = (NameTable* )reg->name_table;
636 e = (NameEntry* )NULL;
637 if (IS_NOT_NULL(t)) {
638 onig_st_lookup_strend(t, name, name_end, (HashDataType* )((void* )(&e)));
644 int (*func)(const UChar*, const UChar*,int,int*,regex_t*,void*);
652 i_names(UChar* key ARG_UNUSED, NameEntry* e, INamesArg* arg)
654 int r = (*(arg->func))(e->name,
655 e->name + e->name_len,
657 (e->back_num > 1 ? e->back_refs : &(e->back_ref1)),
667 onig_foreach_name(regex_t* reg,
668 int (*func)(const UChar*, const UChar*,int,int*,regex_t*,void*), void* arg)
671 NameTable* t = (NameTable* )reg->name_table;
674 if (IS_NOT_NULL(t)) {
678 narg.enc = reg->enc; /* should be pattern encoding. */
679 onig_st_foreach(t, i_names, (HashDataType )&narg);
685 i_renumber_name(UChar* key ARG_UNUSED, NameEntry* e, GroupNumRemap* map)
689 if (e->back_num > 1) {
690 for (i = 0; i < e->back_num; i++) {
691 e->back_refs[i] = map[e->back_refs[i]].new_val;
694 else if (e->back_num == 1) {
695 e->back_ref1 = map[e->back_ref1].new_val;
702 onig_renumber_name_table(regex_t* reg, GroupNumRemap* map)
704 NameTable* t = (NameTable* )reg->name_table;
706 if (IS_NOT_NULL(t)) {
707 onig_st_foreach(t, i_renumber_name, (HashDataType )map);
714 onig_number_of_names(regex_t* reg)
716 NameTable* t = (NameTable* )reg->name_table;
719 return t->num_entries;
724 #else /* USE_ST_LIBRARY */
726 #define INIT_NAMES_ALLOC_NUM 8
736 onig_print_names(FILE* fp, regex_t* reg)
740 NameTable* t = (NameTable* )reg->name_table;
742 if (IS_NOT_NULL(t) && t->num > 0) {
743 fprintf(fp, "name table\n");
744 for (i = 0; i < t->num; i++) {
746 fprintf(fp, "%s: ", e->name);
747 if (e->back_num == 0) {
750 else if (e->back_num == 1) {
751 fprintf(fp, "%d", e->back_ref1);
754 for (j = 0; j < e->back_num; j++) {
755 if (j > 0) fprintf(fp, ", ");
756 fprintf(fp, "%d", e->back_refs[j]);
768 names_clear(regex_t* reg)
772 NameTable* t = (NameTable* )reg->name_table;
774 if (IS_NOT_NULL(t)) {
775 for (i = 0; i < t->num; i++) {
777 if (IS_NOT_NULL(e->name)) {
783 if (IS_NOT_NULL(e->back_refs)) xfree(e->back_refs);
784 e->back_refs = (int* )NULL;
787 if (IS_NOT_NULL(t->e)) {
797 onig_names_free(regex_t* reg)
802 r = names_clear(reg);
803 if (r != 0) return r;
805 t = (NameTable* )reg->name_table;
806 if (IS_NOT_NULL(t)) xfree(t);
807 reg->name_table = NULL;
812 name_find(regex_t* reg, UChar* name, UChar* name_end)
816 NameTable* t = (NameTable* )reg->name_table;
818 if (IS_NOT_NULL(t)) {
819 len = name_end - name;
820 for (i = 0; i < t->num; i++) {
822 if (len == e->name_len && onig_strncmp(name, e->name, len) == 0)
826 return (NameEntry* )NULL;
830 onig_foreach_name(regex_t* reg,
831 int (*func)(const UChar*, const UChar*,int,int*,regex_t*,void*), void* arg)
835 NameTable* t = (NameTable* )reg->name_table;
837 if (IS_NOT_NULL(t)) {
838 for (i = 0; i < t->num; i++) {
840 r = (*func)(e->name, e->name + e->name_len, e->back_num,
841 (e->back_num > 1 ? e->back_refs : &(e->back_ref1)),
843 if (r != 0) return r;
850 onig_number_of_names(regex_t* reg)
852 NameTable* t = (NameTable* )reg->name_table;
860 #endif /* else USE_ST_LIBRARY */
863 name_add(regex_t* reg, UChar* name, UChar* name_end, int backref, ScanEnv* env)
868 NameTable* t = (NameTable* )reg->name_table;
870 if (name_end - name <= 0)
871 return ONIGERR_EMPTY_GROUP_NAME;
873 e = name_find(reg, name, name_end);
875 #ifdef USE_ST_LIBRARY
877 t = onig_st_init_strend_table_with_size(5);
878 reg->name_table = (void* )t;
880 e = (NameEntry* )xmalloc(sizeof(NameEntry));
881 CHECK_NULL_RETURN_MEMERR(e);
883 e->name = strdup_with_null(reg->enc, name, name_end);
884 if (IS_NULL(e->name)) {
885 xfree(e); return ONIGERR_MEMORY;
887 r = onig_st_insert_strend(t, e->name, (e->name + (name_end - name)),
891 e->name_len = (int )(name_end - name);
894 e->back_refs = (int* )NULL;
899 alloc = INIT_NAMES_ALLOC_NUM;
900 t = (NameTable* )xmalloc(sizeof(NameTable));
901 CHECK_NULL_RETURN_MEMERR(t);
906 t->e = (NameEntry* )xmalloc(sizeof(NameEntry) * alloc);
909 return ONIGERR_MEMORY;
915 else if (t->num == t->alloc) {
918 alloc = t->alloc * 2;
919 t->e = (NameEntry* )xrealloc(t->e, sizeof(NameEntry) * alloc);
920 CHECK_NULL_RETURN_MEMERR(t->e);
924 for (i = t->num; i < t->alloc; i++) {
926 t->e[i].name_len = 0;
927 t->e[i].back_num = 0;
928 t->e[i].back_alloc = 0;
929 t->e[i].back_refs = (int* )NULL;
934 e->name = strdup_with_null(reg->enc, name, name_end);
935 if (IS_NULL(e->name)) return ONIGERR_MEMORY;
936 e->name_len = name_end - name;
940 if (e->back_num >= 1 &&
941 ! IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_MULTIPLEX_DEFINITION_NAME)) {
942 onig_scan_env_set_error_string(env, ONIGERR_MULTIPLEX_DEFINED_NAME,
944 return ONIGERR_MULTIPLEX_DEFINED_NAME;
948 if (e->back_num == 1) {
949 e->back_ref1 = backref;
952 if (e->back_num == 2) {
953 alloc = INIT_NAME_BACKREFS_ALLOC_NUM;
954 e->back_refs = (int* )xmalloc(sizeof(int) * alloc);
955 CHECK_NULL_RETURN_MEMERR(e->back_refs);
956 e->back_alloc = alloc;
957 e->back_refs[0] = e->back_ref1;
958 e->back_refs[1] = backref;
961 if (e->back_num > e->back_alloc) {
962 alloc = e->back_alloc * 2;
963 e->back_refs = (int* )xrealloc(e->back_refs, sizeof(int) * alloc);
964 CHECK_NULL_RETURN_MEMERR(e->back_refs);
965 e->back_alloc = alloc;
967 e->back_refs[e->back_num - 1] = backref;
975 onig_name_to_group_numbers(regex_t* reg, const UChar* name,
976 const UChar* name_end, int** nums)
978 NameEntry* e = name_find(reg, name, name_end);
980 if (IS_NULL(e)) return ONIGERR_UNDEFINED_NAME_REFERENCE;
982 switch (e->back_num) {
986 *nums = &(e->back_ref1);
989 *nums = e->back_refs;
996 onig_name_to_backref_number(regex_t* reg, const UChar* name,
997 const UChar* name_end, OnigRegion *region)
1001 n = onig_name_to_group_numbers(reg, name, name_end, &nums);
1005 return ONIGERR_PARSER_BUG;
1009 if (IS_NOT_NULL(region)) {
1010 for (i = n - 1; i >= 0; i--) {
1011 if (region->beg[nums[i]] != ONIG_REGION_NOTPOS)
1020 onig_noname_group_capture_is_active(regex_t* reg)
1022 if (ONIG_IS_OPTION_ON(reg->options, ONIG_OPTION_DONT_CAPTURE_GROUP))
1025 if (onig_number_of_names(reg) > 0 &&
1026 IS_SYNTAX_BV(reg->syntax, ONIG_SYN_CAPTURE_ONLY_NAMED_GROUP) &&
1027 !ONIG_IS_OPTION_ON(reg->options, ONIG_OPTION_CAPTURE_GROUP)) {
1035 #define INIT_SCANENV_MEMENV_ALLOC_SIZE 16
1038 scan_env_clear(ScanEnv* env)
1040 MEM_STATUS_CLEAR(env->capture_history);
1041 MEM_STATUS_CLEAR(env->bt_mem_start);
1042 MEM_STATUS_CLEAR(env->bt_mem_end);
1043 MEM_STATUS_CLEAR(env->backrefed_mem);
1044 env->error = (UChar* )NULL;
1045 env->error_end = (UChar* )NULL;
1049 env->unset_addr_list = NULL;
1050 env->has_call_zero = 0;
1056 env->mem_env_dynamic = (MemEnv* )NULL;
1058 xmemset(env->mem_env_static, 0, sizeof(env->mem_env_static));
1060 env->parse_depth = 0;
1063 env->save_alloc_num = 0;
1068 scan_env_add_mem_entry(ScanEnv* env)
1073 need = env->num_mem + 1;
1074 if (need > MaxCaptureNum && MaxCaptureNum != 0)
1075 return ONIGERR_TOO_MANY_CAPTURES;
1077 if (need >= SCANENV_MEMENV_SIZE) {
1078 if (env->mem_alloc <= need) {
1079 if (IS_NULL(env->mem_env_dynamic)) {
1080 alloc = INIT_SCANENV_MEMENV_ALLOC_SIZE;
1081 p = (MemEnv* )xmalloc(sizeof(MemEnv) * alloc);
1082 CHECK_NULL_RETURN_MEMERR(p);
1083 xmemcpy(p, env->mem_env_static, sizeof(env->mem_env_static));
1086 alloc = env->mem_alloc * 2;
1087 p = (MemEnv* )xrealloc(env->mem_env_dynamic, sizeof(MemEnv) * alloc);
1088 CHECK_NULL_RETURN_MEMERR(p);
1091 for (i = env->num_mem + 1; i < alloc; i++) {
1092 p[i].node = NULL_NODE;
1099 env->mem_env_dynamic = p;
1100 env->mem_alloc = alloc;
1105 return env->num_mem;
1109 scan_env_set_mem_node(ScanEnv* env, int num, Node* node)
1111 if (env->num_mem >= num)
1112 SCANENV_MEMENV(env)[num].node = node;
1114 return ONIGERR_PARSER_BUG;
1119 onig_node_free(Node* node)
1122 if (IS_NULL(node)) return ;
1124 #ifdef DEBUG_NODE_FREE
1125 fprintf(stderr, "onig_node_free: %p\n", node);
1128 switch (NODE_TYPE(node)) {
1130 if (STR_(node)->capa != 0 &&
1131 IS_NOT_NULL(STR_(node)->s) && STR_(node)->s != STR_(node)->buf) {
1132 xfree(STR_(node)->s);
1138 onig_node_free(NODE_CAR(node));
1140 Node* next_node = NODE_CDR(node);
1150 CClassNode* cc = CCLASS_(node);
1153 bbuf_free(cc->mbuf);
1158 if (IS_NOT_NULL(BACKREF_(node)->back_dynamic))
1159 xfree(BACKREF_(node)->back_dynamic);
1162 case NODE_ENCLOSURE:
1163 if (NODE_BODY(node))
1164 onig_node_free(NODE_BODY(node));
1167 EnclosureNode* en = ENCLOSURE_(node);
1168 if (en->type == ENCLOSURE_IF_ELSE) {
1169 onig_node_free(en->te.Then);
1170 onig_node_free(en->te.Else);
1177 if (NODE_BODY(node))
1178 onig_node_free(NODE_BODY(node));
1191 cons_node_free_alone(Node* node)
1195 onig_node_free(node);
1199 list_node_free_not_car(Node* node)
1204 if (IS_NULL(node)) return;
1206 next_node = NODE_CDR(node);
1217 node = (Node* )xmalloc(sizeof(Node));
1218 xmemset(node, 0, sizeof(*node));
1220 #ifdef DEBUG_NODE_FREE
1221 fprintf(stderr, "node_new: %p\n", node);
1228 initialize_cclass(CClassNode* cc)
1230 BITSET_CLEAR(cc->bs);
1236 node_new_cclass(void)
1238 Node* node = node_new();
1239 CHECK_NULL_RETURN(node);
1241 NODE_SET_TYPE(node, NODE_CCLASS);
1242 initialize_cclass(CCLASS_(node));
1247 node_new_ctype(int type, int not, OnigOptionType options)
1249 Node* node = node_new();
1250 CHECK_NULL_RETURN(node);
1252 NODE_SET_TYPE(node, NODE_CTYPE);
1253 CTYPE_(node)->ctype = type;
1254 CTYPE_(node)->not = not;
1255 CTYPE_(node)->options = options;
1256 CTYPE_(node)->ascii_mode = IS_ASCII_MODE_CTYPE_OPTION(type, options);
1261 node_new_anychar(void)
1263 Node* node = node_new_ctype(CTYPE_ANYCHAR, 0, ONIG_OPTION_NONE);
1268 node_new_anychar_with_fixed_option(OnigOptionType option)
1273 node = node_new_anychar();
1275 ct->options = option;
1276 NODE_STATUS_ADD(node, NST_FIXED_OPTION);
1281 node_new_no_newline(Node** node, ScanEnv* env)
1285 n = node_new_anychar_with_fixed_option(ONIG_OPTION_NONE);
1286 CHECK_NULL_RETURN_MEMERR(n);
1292 node_new_true_anychar(Node** node, ScanEnv* env)
1296 n = node_new_anychar_with_fixed_option(ONIG_OPTION_MULTILINE);
1297 CHECK_NULL_RETURN_MEMERR(n);
1303 node_new_list(Node* left, Node* right)
1305 Node* node = node_new();
1306 CHECK_NULL_RETURN(node);
1308 NODE_SET_TYPE(node, NODE_LIST);
1309 NODE_CAR(node) = left;
1310 NODE_CDR(node) = right;
1315 onig_node_new_list(Node* left, Node* right)
1317 return node_new_list(left, right);
1321 onig_node_list_add(Node* list, Node* x)
1325 n = onig_node_new_list(x, NULL);
1326 if (IS_NULL(n)) return NULL_NODE;
1328 if (IS_NOT_NULL(list)) {
1329 while (IS_NOT_NULL(NODE_CDR(list)))
1330 list = NODE_CDR(list);
1339 onig_node_new_alt(Node* left, Node* right)
1341 Node* node = node_new();
1342 CHECK_NULL_RETURN(node);
1344 NODE_SET_TYPE(node, NODE_ALT);
1345 NODE_CAR(node) = left;
1346 NODE_CDR(node) = right;
1351 make_list_or_alt(NodeType type, int n, Node* ns[])
1355 if (n <= 0) return NULL_NODE;
1359 CHECK_NULL_RETURN(r);
1360 NODE_SET_TYPE(r, type);
1361 NODE_CAR(r) = ns[0];
1362 NODE_CDR(r) = NULL_NODE;
1368 CHECK_NULL_RETURN(r);
1370 right = make_list_or_alt(type, n - 1, ns + 1);
1371 if (IS_NULL(right)) {
1376 NODE_SET_TYPE(r, type);
1377 NODE_CAR(r) = ns[0];
1378 NODE_CDR(r) = right;
1385 make_list(int n, Node* ns[])
1387 return make_list_or_alt(NODE_LIST, n, ns);
1391 make_alt(int n, Node* ns[])
1393 return make_list_or_alt(NODE_ALT, n, ns);
1397 onig_node_new_anchor(int type, int ascii_mode)
1399 Node* node = node_new();
1400 CHECK_NULL_RETURN(node);
1402 NODE_SET_TYPE(node, NODE_ANCHOR);
1403 ANCHOR_(node)->type = type;
1404 ANCHOR_(node)->char_len = -1;
1405 ANCHOR_(node)->ascii_mode = ascii_mode;
1410 node_new_backref(int back_num, int* backrefs, int by_name,
1411 #ifdef USE_BACKREF_WITH_LEVEL
1412 int exist_level, int nest_level,
1417 Node* node = node_new();
1419 CHECK_NULL_RETURN(node);
1421 NODE_SET_TYPE(node, NODE_BACKREF);
1422 BACKREF_(node)->back_num = back_num;
1423 BACKREF_(node)->back_dynamic = (int* )NULL;
1425 NODE_STATUS_ADD(node, NST_BY_NAME);
1427 #ifdef USE_BACKREF_WITH_LEVEL
1428 if (exist_level != 0) {
1429 NODE_STATUS_ADD(node, NST_NEST_LEVEL);
1430 BACKREF_(node)->nest_level = nest_level;
1434 for (i = 0; i < back_num; i++) {
1435 if (backrefs[i] <= env->num_mem &&
1436 IS_NULL(SCANENV_MEMENV(env)[backrefs[i]].node)) {
1437 NODE_STATUS_ADD(node, NST_RECURSION); /* /...(\1).../ */
1442 if (back_num <= NODE_BACKREFS_SIZE) {
1443 for (i = 0; i < back_num; i++)
1444 BACKREF_(node)->back_static[i] = backrefs[i];
1447 int* p = (int* )xmalloc(sizeof(int) * back_num);
1449 onig_node_free(node);
1452 BACKREF_(node)->back_dynamic = p;
1453 for (i = 0; i < back_num; i++)
1460 node_new_backref_checker(int back_num, int* backrefs, int by_name,
1461 #ifdef USE_BACKREF_WITH_LEVEL
1462 int exist_level, int nest_level,
1468 node = node_new_backref(back_num, backrefs, by_name,
1469 #ifdef USE_BACKREF_WITH_LEVEL
1470 exist_level, nest_level,
1473 CHECK_NULL_RETURN(node);
1475 NODE_STATUS_ADD(node, NST_CHECKER);
1481 node_new_call(UChar* name, UChar* name_end, int gnum, int by_number)
1483 Node* node = node_new();
1484 CHECK_NULL_RETURN(node);
1486 NODE_SET_TYPE(node, NODE_CALL);
1487 CALL_(node)->by_number = by_number;
1488 CALL_(node)->name = name;
1489 CALL_(node)->name_end = name_end;
1490 CALL_(node)->group_num = gnum;
1491 CALL_(node)->entry_count = 1;
1497 node_new_quantifier(int lower, int upper, int by_number)
1499 Node* node = node_new();
1500 CHECK_NULL_RETURN(node);
1502 NODE_SET_TYPE(node, NODE_QUANT);
1503 QUANT_(node)->lower = lower;
1504 QUANT_(node)->upper = upper;
1505 QUANT_(node)->greedy = 1;
1506 QUANT_(node)->body_empty_info = QUANT_BODY_IS_NOT_EMPTY;
1507 QUANT_(node)->head_exact = NULL_NODE;
1508 QUANT_(node)->next_head_exact = NULL_NODE;
1509 QUANT_(node)->is_refered = 0;
1511 NODE_STATUS_ADD(node, NST_BY_NUMBER);
1517 node_new_enclosure(enum EnclosureType type)
1519 Node* node = node_new();
1520 CHECK_NULL_RETURN(node);
1522 NODE_SET_TYPE(node, NODE_ENCLOSURE);
1523 ENCLOSURE_(node)->type = type;
1526 case ENCLOSURE_MEMORY:
1527 ENCLOSURE_(node)->m.regnum = 0;
1528 ENCLOSURE_(node)->m.called_addr = -1;
1529 ENCLOSURE_(node)->m.entry_count = 1;
1530 ENCLOSURE_(node)->m.called_state = 0;
1533 case ENCLOSURE_OPTION:
1534 ENCLOSURE_(node)->o.options = 0;
1537 case ENCLOSURE_STOP_BACKTRACK:
1540 case ENCLOSURE_IF_ELSE:
1541 ENCLOSURE_(node)->te.Then = 0;
1542 ENCLOSURE_(node)->te.Else = 0;
1546 ENCLOSURE_(node)->opt_count = 0;
1551 onig_node_new_enclosure(int type)
1553 return node_new_enclosure(type);
1557 node_new_enclosure_if_else(Node* cond, Node* Then, Node* Else)
1560 n = node_new_enclosure(ENCLOSURE_IF_ELSE);
1561 CHECK_NULL_RETURN(n);
1563 NODE_BODY(n) = cond;
1564 ENCLOSURE_(n)->te.Then = Then;
1565 ENCLOSURE_(n)->te.Else = Else;
1570 node_new_memory(int is_named)
1572 Node* node = node_new_enclosure(ENCLOSURE_MEMORY);
1573 CHECK_NULL_RETURN(node);
1575 NODE_STATUS_ADD(node, NST_NAMED_GROUP);
1581 node_new_option(OnigOptionType option)
1583 Node* node = node_new_enclosure(ENCLOSURE_OPTION);
1584 CHECK_NULL_RETURN(node);
1585 ENCLOSURE_(node)->o.options = option;
1590 node_new_fail(Node** node, ScanEnv* env)
1593 CHECK_NULL_RETURN_MEMERR(*node);
1595 NODE_SET_TYPE(*node, NODE_GIMMICK);
1596 GIMMICK_(*node)->type = GIMMICK_FAIL;
1601 node_new_save_gimmick(Node** node, enum SaveType save_type, ScanEnv* env)
1606 r = save_entry(env, save_type, &id);
1607 if (r != ONIG_NORMAL) return r;
1610 CHECK_NULL_RETURN_MEMERR(*node);
1612 NODE_SET_TYPE(*node, NODE_GIMMICK);
1613 GIMMICK_(*node)->id = id;
1614 GIMMICK_(*node)->type = GIMMICK_SAVE;
1615 GIMMICK_(*node)->detail_type = (int )save_type;
1621 node_new_update_var_gimmick(Node** node, enum UpdateVarType update_var_type,
1622 int id, ScanEnv* env)
1625 CHECK_NULL_RETURN_MEMERR(*node);
1627 NODE_SET_TYPE(*node, NODE_GIMMICK);
1628 GIMMICK_(*node)->id = id;
1629 GIMMICK_(*node)->type = GIMMICK_UPDATE_VAR;
1630 GIMMICK_(*node)->detail_type = (int )update_var_type;
1636 node_new_keep(Node** node, ScanEnv* env)
1640 r = node_new_save_gimmick(node, SAVE_KEEP, env);
1641 if (r != 0) return r;
1648 node_new_callout(Node** node, enum CalloutType callout_type, ScanEnv* env)
1653 ext = onig_get_regex_ext(env->reg);
1654 CHECK_NULL_RETURN_MEMERR(ext);
1655 if (IS_NULL(ext->pattern)) {
1656 r = onig_ext_set_pattern(env->reg, env->pattern, env->pattern_end);
1657 if (r != ONIG_NORMAL) return r;
1661 CHECK_NULL_RETURN_MEMERR(*node);
1663 NODE_SET_TYPE(*node, NODE_GIMMICK);
1664 GIMMICK_(*node)->id = 0;
1665 GIMMICK_(*node)->type = GIMMICK_CALLOUT;
1666 GIMMICK_(*node)->detail_type = (int )callout_type;
1667 GIMMICK_(*node)->start = -1;
1668 GIMMICK_(*node)->end = -1;
1675 make_extended_grapheme_cluster(Node** node, ScanEnv* env)
1682 /* \X == (?>\O(?:\Y\O)*) */
1687 ns[0] = onig_node_new_anchor(ANCHOR_NO_EXTENDED_GRAPHEME_CLUSTER_BOUNDARY, 0);
1688 if (IS_NULL(ns[0])) goto err;
1690 r = node_new_true_anychar(&ns[1], env);
1691 if (r != 0) goto err1;
1693 x = make_list(2, ns);
1694 if (IS_NULL(x)) goto err;
1698 x = node_new_quantifier(0, REPEAT_INFINITE, 1);
1699 if (IS_NULL(x)) goto err;
1701 NODE_BODY(x) = ns[0];
1705 r = node_new_true_anychar(&ns[0], env);
1706 if (r != 0) goto err1;
1708 x = make_list(2, ns);
1709 if (IS_NULL(x)) goto err;
1714 x = node_new_enclosure(ENCLOSURE_STOP_BACKTRACK);
1715 if (IS_NULL(x)) goto err;
1717 NODE_BODY(x) = ns[0];
1725 for (i = 0; i < 2; i++) onig_node_free(ns[i]);
1730 make_absent_engine(Node** node, int pre_save_right_id, Node* absent,
1731 Node* step_one, int lower, int upper, int possessive,
1732 int is_range_cutter, ScanEnv* env)
1740 for (i = 0; i < 4; i++) ns[i] = NULL_NODE;
1743 ns[3] = step_one; // for err
1744 r = node_new_save_gimmick(&ns[0], SAVE_S, env);
1745 if (r != 0) goto err;
1747 id = GIMMICK_(ns[0])->id;
1748 r = node_new_update_var_gimmick(&ns[2], UPDATE_VAR_RIGHT_RANGE_FROM_S_STACK,
1750 if (r != 0) goto err;
1752 r = node_new_fail(&ns[3], env);
1753 if (r != 0) goto err;
1755 x = make_list(4, ns);
1756 if (IS_NULL(x)) goto err0;
1760 ns[2] = ns[3] = NULL_NODE;
1762 x = make_alt(2, ns);
1763 if (IS_NULL(x)) goto err0;
1767 x = node_new_quantifier(lower, upper, 0);
1768 if (IS_NULL(x)) goto err0;
1770 NODE_BODY(x) = ns[0];
1773 if (possessive != 0) {
1774 x = node_new_enclosure(ENCLOSURE_STOP_BACKTRACK);
1775 if (IS_NULL(x)) goto err0;
1777 NODE_BODY(x) = ns[0];
1781 r = node_new_update_var_gimmick(&ns[1], UPDATE_VAR_RIGHT_RANGE_FROM_STACK,
1782 pre_save_right_id, env);
1783 if (r != 0) goto err;
1785 r = node_new_fail(&ns[2], env);
1786 if (r != 0) goto err;
1788 x = make_list(2, ns + 1);
1789 if (IS_NULL(x)) goto err0;
1791 ns[1] = x; ns[2] = NULL_NODE;
1793 x = make_alt(2, ns);
1794 if (IS_NULL(x)) goto err0;
1796 if (is_range_cutter != 0)
1797 NODE_STATUS_ADD(x, NST_SUPER);
1805 for (i = 0; i < 4; i++) onig_node_free(ns[i]);
1810 make_absent_tail(Node** node1, Node** node2, int pre_save_right_id,
1819 *node1 = *node2 = NULL_NODE;
1820 save = ns[0] = ns[1] = NULL_NODE;
1822 r = node_new_save_gimmick(&save, SAVE_RIGHT_RANGE, env);
1823 if (r != 0) goto err;
1825 id = GIMMICK_(save)->id;
1826 r = node_new_update_var_gimmick(&ns[0], UPDATE_VAR_RIGHT_RANGE_FROM_STACK,
1828 if (r != 0) goto err;
1830 r = node_new_fail(&ns[1], env);
1831 if (r != 0) goto err;
1833 x = make_list(2, ns);
1834 if (IS_NULL(x)) goto err0;
1836 ns[0] = NULL_NODE; ns[1] = x;
1838 r = node_new_update_var_gimmick(&ns[0], UPDATE_VAR_RIGHT_RANGE_FROM_STACK,
1839 pre_save_right_id, env);
1840 if (r != 0) goto err;
1842 x = make_alt(2, ns);
1843 if (IS_NULL(x)) goto err0;
1852 onig_node_free(save);
1853 onig_node_free(ns[0]);
1854 onig_node_free(ns[1]);
1859 make_range_clear(Node** node, ScanEnv* env)
1868 save = ns[0] = ns[1] = NULL_NODE;
1870 r = node_new_save_gimmick(&save, SAVE_RIGHT_RANGE, env);
1871 if (r != 0) goto err;
1873 id = GIMMICK_(save)->id;
1874 r = node_new_update_var_gimmick(&ns[0], UPDATE_VAR_RIGHT_RANGE_FROM_STACK,
1876 if (r != 0) goto err;
1878 r = node_new_fail(&ns[1], env);
1879 if (r != 0) goto err;
1881 x = make_list(2, ns);
1882 if (IS_NULL(x)) goto err0;
1884 ns[0] = NULL_NODE; ns[1] = x;
1886 r = node_new_update_var_gimmick(&ns[0], UPDATE_VAR_RIGHT_RANGE_INIT, 0, env);
1887 if (r != 0) goto err;
1889 x = make_alt(2, ns);
1890 if (IS_NULL(x)) goto err0;
1892 NODE_STATUS_ADD(x, NST_SUPER);
1897 x = make_list(2, ns);
1898 if (IS_NULL(x)) goto err0;
1906 onig_node_free(save);
1907 onig_node_free(ns[0]);
1908 onig_node_free(ns[1]);
1913 is_simple_one_char_repeat(Node* node, Node** rquant, Node** rbody,
1914 int* is_possessive, ScanEnv* env)
1919 *rquant = *rbody = 0;
1922 if (NODE_TYPE(node) == NODE_QUANT) {
1926 if (NODE_TYPE(node) == NODE_ENCLOSURE) {
1927 EnclosureNode* en = ENCLOSURE_(node);
1928 if (en->type == ENCLOSURE_STOP_BACKTRACK) {
1930 quant = NODE_ENCLOSURE_BODY(en);
1931 if (NODE_TYPE(quant) != NODE_QUANT)
1941 if (QUANT_(quant)->greedy == 0)
1944 body = NODE_BODY(quant);
1945 switch (NODE_TYPE(body)) {
1949 StrNode* sn = STR_(body);
1953 while (s < sn->end) {
1954 s += enclen(env->enc, s);
1969 if (node != quant) {
1970 NODE_BODY(node) = 0;
1971 onig_node_free(node);
1973 NODE_BODY(quant) = NULL_NODE;
1980 make_absent_tree_for_simple_one_char_repeat(Node** node, Node* absent, Node* quant,
1981 Node* body, int possessive, ScanEnv* env)
1992 ns[0] = ns[1] = NULL_NODE;
1993 ns[2] = body, ns[3] = absent;
1995 lower = QUANT_(quant)->lower;
1996 upper = QUANT_(quant)->upper;
1997 onig_node_free(quant);
1999 r = node_new_save_gimmick(&ns[0], SAVE_RIGHT_RANGE, env);
2000 if (r != 0) goto err;
2002 id1 = GIMMICK_(ns[0])->id;
2004 r = make_absent_engine(&ns[1], id1, absent, body, lower, upper, possessive,
2006 if (r != 0) goto err;
2008 ns[2] = ns[3] = NULL_NODE;
2010 r = node_new_update_var_gimmick(&ns[2], UPDATE_VAR_RIGHT_RANGE_FROM_STACK,
2012 if (r != 0) goto err;
2014 x = make_list(3, ns);
2015 if (IS_NULL(x)) goto err0;
2023 for (i = 0; i < 4; i++) onig_node_free(ns[i]);
2028 make_absent_tree(Node** node, Node* absent, Node* expr, int is_range_cutter,
2039 for (i = 0; i < 7; i++) ns[i] = NULL_NODE;
2040 ns[4] = expr; ns[5] = absent;
2042 if (is_range_cutter == 0) {
2046 if (expr == NULL_NODE) {
2047 /* default expr \O* */
2048 quant = node_new_quantifier(0, REPEAT_INFINITE, 0);
2049 if (IS_NULL(quant)) goto err0;
2051 r = node_new_true_anychar(&body, env);
2053 onig_node_free(quant);
2060 if (is_simple_one_char_repeat(expr, &quant, &body, &possessive, env)) {
2062 r = make_absent_tree_for_simple_one_char_repeat(node, absent, quant,
2063 body, possessive, env);
2066 onig_node_free(quant);
2067 onig_node_free(body);
2076 r = node_new_save_gimmick(&ns[0], SAVE_RIGHT_RANGE, env);
2077 if (r != 0) goto err;
2079 id1 = GIMMICK_(ns[0])->id;
2081 r = node_new_save_gimmick(&ns[1], SAVE_S, env);
2082 if (r != 0) goto err;
2084 id2 = GIMMICK_(ns[1])->id;
2086 r = node_new_true_anychar(&ns[3], env);
2087 if (r != 0) goto err;
2090 r = make_absent_engine(&ns[2], id1, absent, ns[3], 0, REPEAT_INFINITE,
2091 possessive, is_range_cutter, env);
2092 if (r != 0) goto err;
2097 r = node_new_update_var_gimmick(&ns[3], UPDATE_VAR_S_FROM_STACK, id2, env);
2098 if (r != 0) goto err;
2100 if (is_range_cutter != 0) {
2101 x = make_list(4, ns);
2102 if (IS_NULL(x)) goto err0;
2105 r = make_absent_tail(&ns[5], &ns[6], id1, env);
2106 if (r != 0) goto err;
2108 x = make_list(7, ns);
2109 if (IS_NULL(x)) goto err0;
2118 for (i = 0; i < 7; i++) onig_node_free(ns[i]);
2123 onig_node_str_cat(Node* node, const UChar* s, const UChar* end)
2125 int addlen = (int )(end - s);
2128 int len = (int )(STR_(node)->end - STR_(node)->s);
2130 if (STR_(node)->capa > 0 || (len + addlen > NODE_STRING_BUF_SIZE - 1)) {
2132 int capa = len + addlen + NODE_STRING_MARGIN;
2134 if (capa <= STR_(node)->capa) {
2135 onig_strcpy(STR_(node)->s + len, s, end);
2138 if (STR_(node)->s == STR_(node)->buf)
2139 p = strcat_capa_from_static(STR_(node)->s, STR_(node)->end,
2142 p = strcat_capa(STR_(node)->s, STR_(node)->end, s, end, capa);
2144 CHECK_NULL_RETURN_MEMERR(p);
2146 STR_(node)->capa = capa;
2150 onig_strcpy(STR_(node)->s + len, s, end);
2152 STR_(node)->end = STR_(node)->s + len + addlen;
2159 onig_node_str_set(Node* node, const UChar* s, const UChar* end)
2161 onig_node_str_clear(node);
2162 return onig_node_str_cat(node, s, end);
2166 node_str_cat_char(Node* node, UChar c)
2171 return onig_node_str_cat(node, s, s + 1);
2175 onig_node_conv_to_str_node(Node* node, int flag)
2177 NODE_SET_TYPE(node, NODE_STRING);
2178 STR_(node)->flag = flag;
2179 STR_(node)->capa = 0;
2180 STR_(node)->s = STR_(node)->buf;
2181 STR_(node)->end = STR_(node)->buf;
2185 onig_node_str_clear(Node* node)
2187 if (STR_(node)->capa != 0 &&
2188 IS_NOT_NULL(STR_(node)->s) && STR_(node)->s != STR_(node)->buf) {
2189 xfree(STR_(node)->s);
2192 STR_(node)->capa = 0;
2193 STR_(node)->flag = 0;
2194 STR_(node)->s = STR_(node)->buf;
2195 STR_(node)->end = STR_(node)->buf;
2199 node_new_str(const UChar* s, const UChar* end)
2201 Node* node = node_new();
2202 CHECK_NULL_RETURN(node);
2204 NODE_SET_TYPE(node, NODE_STRING);
2205 STR_(node)->capa = 0;
2206 STR_(node)->flag = 0;
2207 STR_(node)->s = STR_(node)->buf;
2208 STR_(node)->end = STR_(node)->buf;
2209 if (onig_node_str_cat(node, s, end)) {
2210 onig_node_free(node);
2217 onig_node_new_str(const UChar* s, const UChar* end)
2219 return node_new_str(s, end);
2223 node_new_str_raw(UChar* s, UChar* end)
2225 Node* node = node_new_str(s, end);
2226 NODE_STRING_SET_RAW(node);
2231 node_new_empty(void)
2233 return node_new_str(NULL, NULL);
2237 node_new_str_raw_char(UChar c)
2242 return node_new_str_raw(p, p + 1);
2246 str_node_split_last_char(StrNode* sn, OnigEncoding enc)
2249 Node* n = NULL_NODE;
2251 if (sn->end > sn->s) {
2252 p = onigenc_get_prev_char_head(enc, sn->s, sn->end);
2253 if (p && p > sn->s) { /* can be split. */
2254 n = node_new_str(p, sn->end);
2255 if ((sn->flag & STRING_RAW) != 0)
2256 NODE_STRING_SET_RAW(n);
2258 sn->end = (UChar* )p;
2265 str_node_can_be_split(StrNode* sn, OnigEncoding enc)
2267 if (sn->end > sn->s) {
2268 return ((enclen(enc, sn->s) < sn->end - sn->s) ? 1 : 0);
2273 #ifdef USE_PAD_TO_SHORT_BYTE_CHAR
2275 node_str_head_pad(StrNode* sn, int num, UChar val)
2277 UChar buf[NODE_STRING_BUF_SIZE];
2280 len = sn->end - sn->s;
2281 onig_strcpy(buf, sn->s, sn->end);
2282 onig_strcpy(&(sn->s[num]), buf, buf + len);
2285 for (i = 0; i < num; i++) {
2292 onig_scan_unsigned_number(UChar** src, const UChar* end, OnigEncoding enc)
2294 unsigned int num, val;
2302 if (IS_CODE_DIGIT_ASCII(enc, c)) {
2303 val = (unsigned int )DIGITVAL(c);
2304 if ((INT_MAX_LIMIT - val) / 10UL < num)
2305 return -1; /* overflow */
2307 num = num * 10 + val;
2319 scan_unsigned_hexadecimal_number(UChar** src, UChar* end, int minlen,
2320 int maxlen, OnigEncoding enc)
2323 unsigned int num, val;
2330 while (! PEND && n < maxlen) {
2332 if (IS_CODE_XDIGIT_ASCII(enc, c)) {
2334 val = (unsigned int )XDIGITVAL(enc,c);
2335 if ((INT_MAX_LIMIT - val) / 16UL < num)
2336 return ONIGERR_TOO_BIG_NUMBER; /* overflow */
2338 num = (num << 4) + XDIGITVAL(enc,c);
2347 return ONIGERR_INVALID_CODE_POINT_VALUE;
2354 scan_unsigned_octal_number(UChar** src, UChar* end, int maxlen,
2358 unsigned int num, val;
2363 while (! PEND && maxlen-- != 0) {
2365 if (IS_CODE_DIGIT_ASCII(enc, c) && c < '8') {
2367 if ((INT_MAX_LIMIT - val) / 8UL < num)
2368 return -1; /* overflow */
2370 num = (num << 3) + val;
2382 #define BB_WRITE_CODE_POINT(bbuf,pos,code) \
2383 BB_WRITE(bbuf, pos, &(code), SIZE_CODE_POINT)
2386 [n][from-1][to-1][from-2][to-2] ... [from-n][to-n]
2387 (all data size is OnigCodePoint)
2390 new_code_range(BBuf** pbuf)
2392 #define INIT_MULTI_BYTE_RANGE_SIZE (SIZE_CODE_POINT * 5)
2397 bbuf = *pbuf = (BBuf* )xmalloc(sizeof(BBuf));
2398 CHECK_NULL_RETURN_MEMERR(bbuf);
2399 r = BB_INIT(bbuf, INIT_MULTI_BYTE_RANGE_SIZE);
2407 BB_WRITE_CODE_POINT(bbuf, 0, n);
2412 add_code_range_to_buf(BBuf** pbuf, OnigCodePoint from, OnigCodePoint to)
2415 int low, high, bound, x;
2416 OnigCodePoint n, *data;
2420 n = from; from = to; to = n;
2423 if (IS_NULL(*pbuf)) {
2424 r = new_code_range(pbuf);
2425 if (r != 0) return r;
2431 GET_CODE_POINT(n, bbuf->p);
2433 data = (OnigCodePoint* )(bbuf->p);
2436 for (low = 0, bound = n; low < bound; ) {
2437 x = (low + bound) >> 1;
2438 if (from > data[x*2 + 1])
2444 high = (to == ~((OnigCodePoint )0)) ? n : low;
2445 for (bound = n; high < bound; ) {
2446 x = (high + bound) >> 1;
2447 if (to + 1 >= data[x*2])
2453 inc_n = low + 1 - high;
2454 if (n + inc_n > ONIG_MAX_MULTI_BYTE_RANGES_NUM)
2455 return ONIGERR_TOO_MANY_MULTI_BYTE_RANGES;
2458 if (from > data[low*2])
2460 if (to < data[(high - 1)*2 + 1])
2461 to = data[(high - 1)*2 + 1];
2464 if (inc_n != 0 && (OnigCodePoint )high < n) {
2465 int from_pos = SIZE_CODE_POINT * (1 + high * 2);
2466 int to_pos = SIZE_CODE_POINT * (1 + (low + 1) * 2);
2467 int size = (n - high) * 2 * SIZE_CODE_POINT;
2470 BB_MOVE_RIGHT(bbuf, from_pos, to_pos, size);
2473 BB_MOVE_LEFT_REDUCE(bbuf, from_pos, to_pos);
2477 pos = SIZE_CODE_POINT * (1 + low * 2);
2478 BB_ENSURE_SIZE(bbuf, pos + SIZE_CODE_POINT * 2);
2479 BB_WRITE_CODE_POINT(bbuf, pos, from);
2480 BB_WRITE_CODE_POINT(bbuf, pos + SIZE_CODE_POINT, to);
2482 BB_WRITE_CODE_POINT(bbuf, 0, n);
2488 add_code_range(BBuf** pbuf, ScanEnv* env, OnigCodePoint from, OnigCodePoint to)
2491 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_EMPTY_RANGE_IN_CC))
2494 return ONIGERR_EMPTY_RANGE_IN_CHAR_CLASS;
2497 return add_code_range_to_buf(pbuf, from, to);
2501 not_code_range_buf(OnigEncoding enc, BBuf* bbuf, BBuf** pbuf)
2504 OnigCodePoint pre, from, *data, to = 0;
2506 *pbuf = (BBuf* )NULL;
2507 if (IS_NULL(bbuf)) {
2509 return SET_ALL_MULTI_BYTE_RANGE(enc, pbuf);
2512 data = (OnigCodePoint* )(bbuf->p);
2513 GET_CODE_POINT(n, data);
2515 if (n <= 0) goto set_all;
2518 pre = MBCODE_START_POS(enc);
2519 for (i = 0; i < n; i++) {
2522 if (pre <= from - 1) {
2523 r = add_code_range_to_buf(pbuf, pre, from - 1);
2524 if (r != 0) return r;
2526 if (to == ~((OnigCodePoint )0)) break;
2529 if (to < ~((OnigCodePoint )0)) {
2530 r = add_code_range_to_buf(pbuf, to + 1, ~((OnigCodePoint )0));
2535 #define SWAP_BB_NOT(bbuf1, not1, bbuf2, not2) do {\
2538 tnot = not1; not1 = not2; not2 = tnot; \
2539 tbuf = bbuf1; bbuf1 = bbuf2; bbuf2 = tbuf; \
2543 or_code_range_buf(OnigEncoding enc, BBuf* bbuf1, int not1,
2544 BBuf* bbuf2, int not2, BBuf** pbuf)
2547 OnigCodePoint i, n1, *data1;
2548 OnigCodePoint from, to;
2550 *pbuf = (BBuf* )NULL;
2551 if (IS_NULL(bbuf1) && IS_NULL(bbuf2)) {
2552 if (not1 != 0 || not2 != 0)
2553 return SET_ALL_MULTI_BYTE_RANGE(enc, pbuf);
2559 SWAP_BB_NOT(bbuf1, not1, bbuf2, not2);
2561 if (IS_NULL(bbuf1)) {
2563 return SET_ALL_MULTI_BYTE_RANGE(enc, pbuf);
2567 return bbuf_clone(pbuf, bbuf2);
2570 return not_code_range_buf(enc, bbuf2, pbuf);
2576 SWAP_BB_NOT(bbuf1, not1, bbuf2, not2);
2578 data1 = (OnigCodePoint* )(bbuf1->p);
2579 GET_CODE_POINT(n1, data1);
2582 if (not2 == 0 && not1 == 0) { /* 1 OR 2 */
2583 r = bbuf_clone(pbuf, bbuf2);
2585 else if (not1 == 0) { /* 1 OR (not 2) */
2586 r = not_code_range_buf(enc, bbuf2, pbuf);
2588 if (r != 0) return r;
2590 for (i = 0; i < n1; i++) {
2593 r = add_code_range_to_buf(pbuf, from, to);
2594 if (r != 0) return r;
2600 and_code_range1(BBuf** pbuf, OnigCodePoint from1, OnigCodePoint to1,
2601 OnigCodePoint* data, int n)
2604 OnigCodePoint from2, to2;
2606 for (i = 0; i < n; i++) {
2609 if (from2 < from1) {
2610 if (to2 < from1) continue;
2615 else if (from2 <= to1) {
2617 if (from1 <= from2 - 1) {
2618 r = add_code_range_to_buf(pbuf, from1, from2-1);
2619 if (r != 0) return r;
2630 if (from1 > to1) break;
2633 r = add_code_range_to_buf(pbuf, from1, to1);
2634 if (r != 0) return r;
2640 and_code_range_buf(BBuf* bbuf1, int not1, BBuf* bbuf2, int not2, BBuf** pbuf)
2643 OnigCodePoint i, j, n1, n2, *data1, *data2;
2644 OnigCodePoint from, to, from1, to1, from2, to2;
2646 *pbuf = (BBuf* )NULL;
2647 if (IS_NULL(bbuf1)) {
2648 if (not1 != 0 && IS_NOT_NULL(bbuf2)) /* not1 != 0 -> not2 == 0 */
2649 return bbuf_clone(pbuf, bbuf2);
2652 else if (IS_NULL(bbuf2)) {
2654 return bbuf_clone(pbuf, bbuf1);
2659 SWAP_BB_NOT(bbuf1, not1, bbuf2, not2);
2661 data1 = (OnigCodePoint* )(bbuf1->p);
2662 data2 = (OnigCodePoint* )(bbuf2->p);
2663 GET_CODE_POINT(n1, data1);
2664 GET_CODE_POINT(n2, data2);
2668 if (not2 == 0 && not1 == 0) { /* 1 AND 2 */
2669 for (i = 0; i < n1; i++) {
2672 for (j = 0; j < n2; j++) {
2675 if (from2 > to1) break;
2676 if (to2 < from1) continue;
2677 from = MAX(from1, from2);
2679 r = add_code_range_to_buf(pbuf, from, to);
2680 if (r != 0) return r;
2684 else if (not1 == 0) { /* 1 AND (not 2) */
2685 for (i = 0; i < n1; i++) {
2688 r = and_code_range1(pbuf, from1, to1, data2, n2);
2689 if (r != 0) return r;
2697 and_cclass(CClassNode* dest, CClassNode* cc, OnigEncoding enc)
2700 BBuf *buf1, *buf2, *pbuf;
2701 BitSetRef bsr1, bsr2;
2704 not1 = IS_NCCLASS_NOT(dest);
2707 not2 = IS_NCCLASS_NOT(cc);
2712 bitset_invert_to(bsr1, bs1);
2716 bitset_invert_to(bsr2, bs2);
2719 bitset_and(bsr1, bsr2);
2720 if (bsr1 != dest->bs) {
2721 bitset_copy(dest->bs, bsr1);
2724 bitset_invert(dest->bs);
2727 if (! ONIGENC_IS_SINGLEBYTE(enc)) {
2728 if (not1 != 0 && not2 != 0) {
2729 r = or_code_range_buf(enc, buf1, 0, buf2, 0, &pbuf);
2732 r = and_code_range_buf(buf1, not1, buf2, not2, &pbuf);
2733 if (r == 0 && not1 != 0) {
2735 r = not_code_range_buf(enc, pbuf, &tbuf);
2744 if (r != 0) return r;
2754 or_cclass(CClassNode* dest, CClassNode* cc, OnigEncoding enc)
2757 BBuf *buf1, *buf2, *pbuf;
2758 BitSetRef bsr1, bsr2;
2761 not1 = IS_NCCLASS_NOT(dest);
2764 not2 = IS_NCCLASS_NOT(cc);
2769 bitset_invert_to(bsr1, bs1);
2773 bitset_invert_to(bsr2, bs2);
2776 bitset_or(bsr1, bsr2);
2777 if (bsr1 != dest->bs) {
2778 bitset_copy(dest->bs, bsr1);
2781 bitset_invert(dest->bs);
2784 if (! ONIGENC_IS_SINGLEBYTE(enc)) {
2785 if (not1 != 0 && not2 != 0) {
2786 r = and_code_range_buf(buf1, 0, buf2, 0, &pbuf);
2789 r = or_code_range_buf(enc, buf1, not1, buf2, not2, &pbuf);
2790 if (r == 0 && not1 != 0) {
2792 r = not_code_range_buf(enc, pbuf, &tbuf);
2801 if (r != 0) return r;
2811 static OnigCodePoint
2812 conv_backslash_value(OnigCodePoint c, ScanEnv* env)
2814 if (IS_SYNTAX_OP(env->syntax, ONIG_SYN_OP_ESC_CONTROL_CHARS)) {
2816 case 'n': return '\n';
2817 case 't': return '\t';
2818 case 'r': return '\r';
2819 case 'f': return '\f';
2820 case 'a': return '\007';
2821 case 'b': return '\010';
2822 case 'e': return '\033';
2824 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_ESC_V_VTAB))
2836 is_invalid_quantifier_target(Node* node)
2838 switch (NODE_TYPE(node)) {
2844 case NODE_ENCLOSURE:
2845 /* allow enclosed elements */
2846 /* return is_invalid_quantifier_target(NODE_BODY(node)); */
2851 if (! is_invalid_quantifier_target(NODE_CAR(node))) return 0;
2852 } while (IS_NOT_NULL(node = NODE_CDR(node)));
2858 if (is_invalid_quantifier_target(NODE_CAR(node))) return 1;
2859 } while (IS_NOT_NULL(node = NODE_CDR(node)));
2868 /* ?:0, *:1, +:2, ??:3, *?:4, +?:5 */
2870 quantifier_type_num(QuantNode* q)
2873 if (q->lower == 0) {
2874 if (q->upper == 1) return 0;
2875 else if (IS_REPEAT_INFINITE(q->upper)) return 1;
2877 else if (q->lower == 1) {
2878 if (IS_REPEAT_INFINITE(q->upper)) return 2;
2882 if (q->lower == 0) {
2883 if (q->upper == 1) return 3;
2884 else if (IS_REPEAT_INFINITE(q->upper)) return 4;
2886 else if (q->lower == 1) {
2887 if (IS_REPEAT_INFINITE(q->upper)) return 5;
2895 RQ_ASIS = 0, /* as is */
2896 RQ_DEL = 1, /* delete parent */
2898 RQ_AQ, /* to '*?' */
2899 RQ_QQ, /* to '??' */
2900 RQ_P_QQ, /* to '+)??' */
2901 RQ_PQ_Q /* to '+?)?' */
2904 static enum ReduceType ReduceTypeTable[6][6] = {
2905 {RQ_DEL, RQ_A, RQ_A, RQ_QQ, RQ_AQ, RQ_ASIS}, /* '?' */
2906 {RQ_DEL, RQ_DEL, RQ_DEL, RQ_P_QQ, RQ_P_QQ, RQ_DEL}, /* '*' */
2907 {RQ_A, RQ_A, RQ_DEL, RQ_ASIS, RQ_P_QQ, RQ_DEL}, /* '+' */
2908 {RQ_DEL, RQ_AQ, RQ_AQ, RQ_DEL, RQ_AQ, RQ_AQ}, /* '??' */
2909 {RQ_DEL, RQ_DEL, RQ_DEL, RQ_DEL, RQ_DEL, RQ_DEL}, /* '*?' */
2910 {RQ_ASIS, RQ_PQ_Q, RQ_DEL, RQ_AQ, RQ_AQ, RQ_DEL} /* '+?' */
2914 onig_reduce_nested_quantifier(Node* pnode, Node* cnode)
2921 pnum = quantifier_type_num(p);
2922 cnum = quantifier_type_num(c);
2923 if (pnum < 0 || cnum < 0) {
2924 if ((p->lower == p->upper) && ! IS_REPEAT_INFINITE(p->upper)) {
2925 if ((c->lower == c->upper) && ! IS_REPEAT_INFINITE(c->upper)) {
2926 int n = positive_int_multiply(p->lower, c->lower);
2928 p->lower = p->upper = n;
2929 NODE_BODY(pnode) = NODE_BODY(cnode);
2938 switch(ReduceTypeTable[cnum][pnum]) {
2943 NODE_BODY(pnode) = NODE_BODY(cnode);
2944 p->lower = 0; p->upper = REPEAT_INFINITE; p->greedy = 1;
2947 NODE_BODY(pnode) = NODE_BODY(cnode);
2948 p->lower = 0; p->upper = REPEAT_INFINITE; p->greedy = 0;
2951 NODE_BODY(pnode) = NODE_BODY(cnode);
2952 p->lower = 0; p->upper = 1; p->greedy = 0;
2955 NODE_BODY(pnode) = cnode;
2956 p->lower = 0; p->upper = 1; p->greedy = 0;
2957 c->lower = 1; c->upper = REPEAT_INFINITE; c->greedy = 1;
2961 NODE_BODY(pnode) = cnode;
2962 p->lower = 0; p->upper = 1; p->greedy = 1;
2963 c->lower = 1; c->upper = REPEAT_INFINITE; c->greedy = 0;
2967 NODE_BODY(pnode) = cnode;
2973 NODE_BODY(cnode) = NULL_NODE;
2974 onig_node_free(cnode);
2978 node_new_general_newline(Node** node, ScanEnv* env)
2982 UChar buf[ONIGENC_CODE_TO_MBC_MAXLEN * 2];
2988 dlen = ONIGENC_CODE_TO_MBC(env->enc, 0x0d, buf);
2989 if (dlen < 0) return dlen;
2990 alen = ONIGENC_CODE_TO_MBC(env->enc, 0x0a, buf + dlen);
2991 if (alen < 0) return alen;
2993 crnl = node_new_str_raw(buf, buf + dlen + alen);
2994 CHECK_NULL_RETURN_MEMERR(crnl);
2996 ncc = node_new_cclass();
2997 if (IS_NULL(ncc)) goto err2;
3001 bitset_set_range(cc->bs, 0x0a, 0x0d);
3004 r = add_code_range(&(cc->mbuf), env, 0x0a, 0x0d);
3007 onig_node_free(ncc);
3009 onig_node_free(crnl);
3010 return ONIGERR_MEMORY;
3014 if (ONIGENC_IS_UNICODE_ENCODING(env->enc)) {
3015 r = add_code_range(&(cc->mbuf), env, 0x85, 0x85);
3016 if (r != 0) goto err1;
3017 r = add_code_range(&(cc->mbuf), env, 0x2028, 0x2029);
3018 if (r != 0) goto err1;
3021 x = node_new_enclosure_if_else(crnl, 0, ncc);
3022 if (IS_NULL(x)) goto err1;
3029 TK_EOT = 0, /* end of token */
3041 TK_ANYCHAR_ANYTIME, /* SQL '%' == .* */
3047 TK_CHAR_PROPERTY, /* \p{...}, \P{...} */
3049 TK_GENERAL_NEWLINE, /* \R */
3050 TK_NO_NEWLINE, /* \N */
3051 TK_TRUE_ANYCHAR, /* \O */
3052 TK_EXTENDED_GRAPHEME_CLUSTER, /* \X */
3057 TK_POSIX_BRACKET_OPEN,
3059 TK_CC_CC_OPEN /* [ */
3063 enum TokenSyms type;
3065 int base; /* is number: 8, 16 (used in [....]) */
3084 #ifdef USE_BACKREF_WITH_LEVEL
3086 int level; /* \k<name+n> */
3104 fetch_range_quantifier(UChar** src, UChar* end, OnigToken* tok, ScanEnv* env)
3106 int low, up, syn_allow, non_low = 0;
3109 OnigEncoding enc = env->enc;
3113 syn_allow = IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_INVALID_INTERVAL);
3117 return 1; /* "....{" : OK! */
3119 return ONIGERR_END_PATTERN_AT_LEFT_BRACE; /* "....{" syntax error */
3124 if (c == ')' || c == '(' || c == '|') {
3125 return ONIGERR_END_PATTERN_AT_LEFT_BRACE;
3129 low = onig_scan_unsigned_number(&p, end, env->enc);
3130 if (low < 0) return ONIGERR_TOO_BIG_NUMBER_FOR_REPEAT_RANGE;
3131 if (low > ONIG_MAX_REPEAT_NUM)
3132 return ONIGERR_TOO_BIG_NUMBER_FOR_REPEAT_RANGE;
3134 if (p == *src) { /* can't read low */
3135 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_INTERVAL_LOW_ABBREV)) {
3136 /* allow {,n} as {0,n} */
3144 if (PEND) goto invalid;
3148 up = onig_scan_unsigned_number(&p, end, env->enc);
3149 if (up < 0) return ONIGERR_TOO_BIG_NUMBER_FOR_REPEAT_RANGE;
3150 if (up > ONIG_MAX_REPEAT_NUM)
3151 return ONIGERR_TOO_BIG_NUMBER_FOR_REPEAT_RANGE;
3156 up = REPEAT_INFINITE; /* {n,} : {n,infinite} */
3164 up = low; /* {n} : exact n times */
3168 if (PEND) goto invalid;
3170 if (IS_SYNTAX_OP(env->syntax, ONIG_SYN_OP_ESC_BRACE_INTERVAL)) {
3171 if (c != MC_ESC(env->syntax)) goto invalid;
3174 if (c != '}') goto invalid;
3176 if (!IS_REPEAT_INFINITE(up) && low > up) {
3177 return ONIGERR_UPPER_SMALLER_THAN_LOWER_IN_REPEAT_RANGE;
3180 tok->type = TK_INTERVAL;
3181 tok->u.repeat.lower = low;
3182 tok->u.repeat.upper = up;
3184 return r; /* 0: normal {n,m}, 2: fixed {n} */
3188 /* *src = p; */ /* !!! Don't do this line !!! */
3192 return ONIGERR_INVALID_REPEAT_RANGE_PATTERN;
3195 /* \M-, \C-, \c, or \... */
3197 fetch_escaped_value(UChar** src, UChar* end, ScanEnv* env, OnigCodePoint* val)
3201 OnigEncoding enc = env->enc;
3204 if (PEND) return ONIGERR_END_PATTERN_AT_ESCAPE;
3209 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_ESC_CAPITAL_M_BAR_META)) {
3210 if (PEND) return ONIGERR_END_PATTERN_AT_META;
3212 if (c != '-') return ONIGERR_META_CODE_SYNTAX;
3213 if (PEND) return ONIGERR_END_PATTERN_AT_META;
3215 if (c == MC_ESC(env->syntax)) {
3216 v = fetch_escaped_value(&p, end, env, &c);
3217 if (v < 0) return v;
3219 c = ((c & 0xff) | 0x80);
3226 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_ESC_CAPITAL_C_BAR_CONTROL)) {
3227 if (PEND) return ONIGERR_END_PATTERN_AT_CONTROL;
3229 if (c != '-') return ONIGERR_CONTROL_CODE_SYNTAX;
3236 if (IS_SYNTAX_OP(env->syntax, ONIG_SYN_OP_ESC_C_CONTROL)) {
3238 if (PEND) return ONIGERR_END_PATTERN_AT_CONTROL;
3244 if (c == MC_ESC(env->syntax)) {
3245 v = fetch_escaped_value(&p, end, env, &c);
3246 if (v < 0) return v;
3257 c = conv_backslash_value(c, env);
3267 static int fetch_token(OnigToken* tok, UChar** src, UChar* end, ScanEnv* env);
3269 static OnigCodePoint
3270 get_name_end_code_point(OnigCodePoint start)
3273 case '<': return (OnigCodePoint )'>'; break;
3274 case '\'': return (OnigCodePoint )'\''; break;
3275 case '(': return (OnigCodePoint )')'; break;
3280 return (OnigCodePoint )0;
3289 #ifdef USE_BACKREF_WITH_LEVEL
3291 \k<name+n>, \k<name-n>
3292 \k<num+n>, \k<num-n>
3293 \k<-num+n>, \k<-num-n>
3294 \k<+num+n>, \k<+num-n>
3297 fetch_name_with_level(OnigCodePoint start_code, UChar** src, UChar* end,
3298 UChar** rname_end, ScanEnv* env,
3299 int* rback_num, int* rlevel, enum REF_NUM* num_type)
3301 int r, sign, exist_level;
3303 OnigCodePoint end_code;
3304 OnigCodePoint c = 0;
3305 OnigEncoding enc = env->enc;
3313 *num_type = IS_NOT_NUM;
3317 end_code = get_name_end_code_point(start_code);
3323 return ONIGERR_EMPTY_GROUP_NAME;
3328 return ONIGERR_EMPTY_GROUP_NAME;
3330 if (IS_CODE_DIGIT_ASCII(enc, c)) {
3331 *num_type = IS_ABS_NUM;
3334 else if (c == '-') {
3335 *num_type = IS_REL_NUM;
3339 else if (c == '+') {
3340 *num_type = IS_REL_NUM;
3344 else if (!ONIGENC_IS_CODE_WORD(enc, c)) {
3345 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3352 if (c == end_code || c == ')' || c == '+' || c == '-') {
3353 if (*num_type != IS_NOT_NUM && digit_count == 0)
3354 r = ONIGERR_INVALID_GROUP_NAME;
3358 if (*num_type != IS_NOT_NUM) {
3359 if (IS_CODE_DIGIT_ASCII(enc, c)) {
3363 r = ONIGERR_INVALID_GROUP_NAME;
3364 *num_type = IS_NOT_NUM;
3367 else if (!ONIGENC_IS_CODE_WORD(enc, c)) {
3368 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3372 if (r == 0 && c != end_code) {
3373 if (c == '+' || c == '-') {
3375 int flag = (c == '-' ? -1 : 1);
3378 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3382 if (! IS_CODE_DIGIT_ASCII(enc, c)) goto err;
3384 level = onig_scan_unsigned_number(&p, end, enc);
3385 if (level < 0) return ONIGERR_TOO_BIG_NUMBER;
3386 *rlevel = (level * flag);
3399 r = ONIGERR_INVALID_GROUP_NAME;
3404 if (*num_type != IS_NOT_NUM) {
3405 *rback_num = onig_scan_unsigned_number(&pnum_head, name_end, enc);
3406 if (*rback_num < 0) return ONIGERR_TOO_BIG_NUMBER;
3407 else if (*rback_num == 0) {
3408 if (*num_type == IS_REL_NUM)
3415 *rname_end = name_end;
3417 return (exist_level ? 1 : 0);
3420 onig_scan_env_set_error_string(env, r, *src, name_end);
3424 #endif /* USE_BACKREF_WITH_LEVEL */
3427 ref: 0 -> define name (don't allow number name)
3428 1 -> reference name (allow number name)
3431 fetch_name(OnigCodePoint start_code, UChar** src, UChar* end,
3432 UChar** rname_end, ScanEnv* env, int* rback_num,
3433 enum REF_NUM* num_type, int ref)
3437 OnigCodePoint end_code;
3438 OnigCodePoint c = 0;
3439 OnigEncoding enc = env->enc;
3446 end_code = get_name_end_code_point(start_code);
3452 *num_type = IS_NOT_NUM;
3455 return ONIGERR_EMPTY_GROUP_NAME;
3460 return ONIGERR_EMPTY_GROUP_NAME;
3462 if (IS_CODE_DIGIT_ASCII(enc, c)) {
3464 *num_type = IS_ABS_NUM;
3466 r = ONIGERR_INVALID_GROUP_NAME;
3470 else if (c == '-') {
3472 *num_type = IS_REL_NUM;
3477 r = ONIGERR_INVALID_GROUP_NAME;
3480 else if (c == '+') {
3482 *num_type = IS_REL_NUM;
3487 r = ONIGERR_INVALID_GROUP_NAME;
3490 else if (!ONIGENC_IS_CODE_WORD(enc, c)) {
3491 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3499 if (c == end_code || c == ')') {
3500 if (*num_type != IS_NOT_NUM && digit_count == 0)
3501 r = ONIGERR_INVALID_GROUP_NAME;
3505 if (*num_type != IS_NOT_NUM) {
3506 if (IS_CODE_DIGIT_ASCII(enc, c)) {
3510 if (!ONIGENC_IS_CODE_WORD(enc, c))
3511 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3513 r = ONIGERR_INVALID_GROUP_NAME;
3515 *num_type = IS_NOT_NUM;
3519 if (!ONIGENC_IS_CODE_WORD(enc, c)) {
3520 r = ONIGERR_INVALID_CHAR_IN_GROUP_NAME;
3525 if (c != end_code) {
3526 r = ONIGERR_INVALID_GROUP_NAME;
3530 if (*num_type != IS_NOT_NUM) {
3531 *rback_num = onig_scan_unsigned_number(&pnum_head, name_end, enc);
3532 if (*rback_num < 0) return ONIGERR_TOO_BIG_NUMBER;
3533 else if (*rback_num == 0) {
3534 if (*num_type == IS_REL_NUM) {
3535 r = ONIGERR_INVALID_GROUP_NAME;
3543 *rname_end = name_end;
3551 if (c == end_code || c == ')')
3558 onig_scan_env_set_error_string(env, r, *src, name_end);
3564 CC_ESC_WARN(ScanEnv* env, UChar *c)
3566 if (onig_warn == onig_null_warn) return ;
3568 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_WARN_CC_OP_NOT_ESCAPED) &&
3569 IS_SYNTAX_BV(env->syntax, ONIG_SYN_BACKSLASH_ESCAPE_IN_CC)) {
3570 UChar buf[WARN_BUFSIZE];
3571 onig_snprintf_with_pattern(buf, WARN_BUFSIZE, env->enc,
3572 env->pattern, env->pattern_end,
3573 (UChar* )"character class has '%s' without escape",
3575 (*onig_warn)((char* )buf);
3580 CLOSE_BRACKET_WITHOUT_ESC_WARN(ScanEnv* env, UChar* c)
3582 if (onig_warn == onig_null_warn) return ;
3584 if (IS_SYNTAX_BV((env)->syntax, ONIG_SYN_WARN_CC_OP_NOT_ESCAPED)) {
3585 UChar buf[WARN_BUFSIZE];
3586 onig_snprintf_with_pattern(buf, WARN_BUFSIZE, (env)->enc,
3587 (env)->pattern, (env)->pattern_end,
3588 (UChar* )"regular expression has '%s' without escape", c);
3589 (*onig_warn)((char* )buf);
3594 find_str_position(OnigCodePoint s[], int n, UChar* from, UChar* to,
3595 UChar **next, OnigEncoding enc)
3603 x = ONIGENC_MBC_TO_CODE(enc, p, to);
3604 q = p + enclen(enc, p);
3606 for (i = 1; i < n && q < to; i++) {
3607 x = ONIGENC_MBC_TO_CODE(enc, q, to);
3608 if (x != s[i]) break;
3609 q += enclen(enc, q);
3612 if (IS_NOT_NULL(next))
3623 str_exist_check_with_esc(OnigCodePoint s[], int n, UChar* from, UChar* to,
3624 OnigCodePoint bad, OnigEncoding enc, OnigSyntaxType* syn)
3635 p += enclen(enc, p);
3638 x = ONIGENC_MBC_TO_CODE(enc, p, to);
3639 q = p + enclen(enc, p);
3641 for (i = 1; i < n && q < to; i++) {
3642 x = ONIGENC_MBC_TO_CODE(enc, q, to);
3643 if (x != s[i]) break;
3644 q += enclen(enc, q);
3646 if (i >= n) return 1;
3647 p += enclen(enc, p);
3650 x = ONIGENC_MBC_TO_CODE(enc, p, to);
3651 if (x == bad) return 0;
3652 else if (x == MC_ESC(syn)) in_esc = 1;
3661 fetch_token_in_cc(OnigToken* tok, UChar** src, UChar* end, ScanEnv* env)
3664 OnigCodePoint c, c2;
3665 OnigSyntaxType* syn = env->syntax;
3666 OnigEncoding enc = env->enc;
3677 tok->type = TK_CHAR;
3683 tok->type = TK_CC_CLOSE;
3685 else if (c == '-') {
3686 tok->type = TK_CC_RANGE;
3688 else if (c == MC_ESC(syn)) {
3689 if (! IS_SYNTAX_BV(syn, ONIG_SYN_BACKSLASH_ESCAPE_IN_CC))
3692 if (PEND) return ONIGERR_END_PATTERN_AT_ESCAPE;
3699 tok->type = TK_CHAR_TYPE;
3700 tok->u.prop.ctype = ONIGENC_CTYPE_WORD;
3701 tok->u.prop.not = 0;
3704 tok->type = TK_CHAR_TYPE;
3705 tok->u.prop.ctype = ONIGENC_CTYPE_WORD;
3706 tok->u.prop.not = 1;
3709 tok->type = TK_CHAR_TYPE;
3710 tok->u.prop.ctype = ONIGENC_CTYPE_DIGIT;
3711 tok->u.prop.not = 0;
3714 tok->type = TK_CHAR_TYPE;
3715 tok->u.prop.ctype = ONIGENC_CTYPE_DIGIT;
3716 tok->u.prop.not = 1;
3719 tok->type = TK_CHAR_TYPE;
3720 tok->u.prop.ctype = ONIGENC_CTYPE_SPACE;
3721 tok->u.prop.not = 0;
3724 tok->type = TK_CHAR_TYPE;
3725 tok->u.prop.ctype = ONIGENC_CTYPE_SPACE;
3726 tok->u.prop.not = 1;
3729 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_H_XDIGIT)) break;
3730 tok->type = TK_CHAR_TYPE;
3731 tok->u.prop.ctype = ONIGENC_CTYPE_XDIGIT;
3732 tok->u.prop.not = 0;
3735 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_H_XDIGIT)) break;
3736 tok->type = TK_CHAR_TYPE;
3737 tok->u.prop.ctype = ONIGENC_CTYPE_XDIGIT;
3738 tok->u.prop.not = 1;
3747 IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_P_BRACE_CHAR_PROPERTY)) {
3749 tok->type = TK_CHAR_PROPERTY;
3750 tok->u.prop.not = (c == 'P' ? 1 : 0);
3752 if (!PEND && IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_P_BRACE_CIRCUMFLEX_NOT)) {
3755 tok->u.prop.not = (tok->u.prop.not == 0 ? 1 : 0);
3767 if (PPEEK_IS('{') && IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_O_BRACE_OCTAL)) {
3769 num = scan_unsigned_octal_number(&p, end, 11, enc);
3770 if (num < 0) return ONIGERR_TOO_BIG_WIDE_CHAR_VALUE;
3773 if (IS_CODE_DIGIT_ASCII(enc, c2))
3774 return ONIGERR_TOO_LONG_WIDE_CHAR_VALUE;
3777 if (p > prev + enclen(enc, prev) && !PEND && (PPEEK_IS('}'))) {
3779 tok->type = TK_CODE_POINT;
3781 tok->u.code = (OnigCodePoint )num;
3784 /* can't read nothing or invalid format */
3794 if (PPEEK_IS('{') && IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_X_BRACE_HEX8)) {
3796 num = scan_unsigned_hexadecimal_number(&p, end, 0, 8, enc);
3798 if (num == ONIGERR_TOO_BIG_NUMBER)
3799 return ONIGERR_TOO_BIG_WIDE_CHAR_VALUE;
3805 if (IS_CODE_XDIGIT_ASCII(enc, c2))
3806 return ONIGERR_TOO_LONG_WIDE_CHAR_VALUE;
3809 if (p > prev + enclen(enc, prev) && !PEND && (PPEEK_IS('}'))) {
3811 tok->type = TK_CODE_POINT;
3813 tok->u.code = (OnigCodePoint )num;
3816 /* can't read nothing or invalid format */
3820 else if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_X_HEX2)) {
3821 num = scan_unsigned_hexadecimal_number(&p, end, 0, 2, enc);
3822 if (num < 0) return num;
3823 if (p == prev) { /* can't read nothing. */
3824 num = 0; /* but, it's not error */
3826 tok->type = TK_RAW_BYTE;
3836 if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_U_HEX4)) {
3837 num = scan_unsigned_hexadecimal_number(&p, end, 4, 4, enc);
3838 if (num < 0) return num;
3839 if (p == prev) { /* can't read nothing. */
3840 num = 0; /* but, it's not error */
3842 tok->type = TK_CODE_POINT;
3844 tok->u.code = (OnigCodePoint )num;
3849 case '1': case '2': case '3': case '4': case '5': case '6': case '7':
3850 if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_OCTAL3)) {
3853 num = scan_unsigned_octal_number(&p, end, 3, enc);
3854 if (num < 0 || num >= 256) return ONIGERR_TOO_BIG_NUMBER;
3855 if (p == prev) { /* can't read nothing. */
3856 num = 0; /* but, it's not error */
3858 tok->type = TK_RAW_BYTE;
3866 num = fetch_escaped_value(&p, end, env, &c2);
3867 if (num < 0) return num;
3868 if (tok->u.c != c2) {
3870 tok->type = TK_CODE_POINT;
3875 else if (c == '[') {
3876 if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_POSIX_BRACKET) && (PPEEK_IS(':'))) {
3877 OnigCodePoint send[] = { (OnigCodePoint )':', (OnigCodePoint )']' };
3878 tok->backp = p; /* point at '[' is read */
3880 if (str_exist_check_with_esc(send, 2, p, end,
3881 (OnigCodePoint )']', enc, syn)) {
3882 tok->type = TK_POSIX_BRACKET_OPEN;
3891 if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_CCLASS_SET_OP)) {
3892 tok->type = TK_CC_CC_OPEN;
3895 CC_ESC_WARN(env, (UChar* )"[");
3899 else if (c == '&') {
3900 if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_CCLASS_SET_OP) &&
3901 !PEND && (PPEEK_IS('&'))) {
3903 tok->type = TK_CC_AND;
3913 fetch_token(OnigToken* tok, UChar** src, UChar* end, ScanEnv* env)
3917 OnigEncoding enc = env->enc;
3918 OnigSyntaxType* syn = env->syntax;
3929 tok->type = TK_STRING;
3934 if (IS_MC_ESC_CODE(c, syn)) {
3935 if (PEND) return ONIGERR_END_PATTERN_AT_ESCAPE;
3944 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_ASTERISK_ZERO_INF)) break;
3945 tok->type = TK_OP_REPEAT;
3946 tok->u.repeat.lower = 0;
3947 tok->u.repeat.upper = REPEAT_INFINITE;
3952 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_PLUS_ONE_INF)) break;
3953 tok->type = TK_OP_REPEAT;
3954 tok->u.repeat.lower = 1;
3955 tok->u.repeat.upper = REPEAT_INFINITE;
3960 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_QMARK_ZERO_ONE)) break;
3961 tok->type = TK_OP_REPEAT;
3962 tok->u.repeat.lower = 0;
3963 tok->u.repeat.upper = 1;
3965 if (!PEND && PPEEK_IS('?') &&
3966 IS_SYNTAX_OP(syn, ONIG_SYN_OP_QMARK_NON_GREEDY)) {
3968 tok->u.repeat.greedy = 0;
3969 tok->u.repeat.possessive = 0;
3973 if (!PEND && PPEEK_IS('+') &&
3974 ((IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_PLUS_POSSESSIVE_REPEAT) &&
3975 tok->type != TK_INTERVAL) ||
3976 (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_PLUS_POSSESSIVE_INTERVAL) &&
3977 tok->type == TK_INTERVAL))) {
3979 tok->u.repeat.greedy = 1;
3980 tok->u.repeat.possessive = 1;
3983 tok->u.repeat.greedy = 1;
3984 tok->u.repeat.possessive = 0;
3990 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_BRACE_INTERVAL)) break;
3991 r = fetch_range_quantifier(&p, end, tok, env);
3992 if (r < 0) return r; /* error */
3993 if (r == 0) goto greedy_check;
3994 else if (r == 2) { /* {n} */
3995 if (IS_SYNTAX_BV(syn, ONIG_SYN_FIXED_INTERVAL_IS_GREEDY_ONLY))
3996 goto possessive_check;
4000 /* r == 1 : normal char */
4004 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_VBAR_ALT)) break;
4009 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_LPAREN_SUBEXP)) break;
4010 tok->type = TK_SUBEXP_OPEN;
4014 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_LPAREN_SUBEXP)) break;
4015 tok->type = TK_SUBEXP_CLOSE;
4019 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_W_WORD)) break;
4020 tok->type = TK_CHAR_TYPE;
4021 tok->u.prop.ctype = ONIGENC_CTYPE_WORD;
4022 tok->u.prop.not = 0;
4026 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_W_WORD)) break;
4027 tok->type = TK_CHAR_TYPE;
4028 tok->u.prop.ctype = ONIGENC_CTYPE_WORD;
4029 tok->u.prop.not = 1;
4033 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_B_WORD_BOUND)) break;
4034 tok->type = TK_ANCHOR;
4035 tok->u.anchor = ANCHOR_WORD_BOUNDARY;
4039 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_B_WORD_BOUND)) break;
4040 tok->type = TK_ANCHOR;
4041 tok->u.anchor = ANCHOR_NO_WORD_BOUNDARY;
4045 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP2_ESC_X_Y_GRAPHEME_CLUSTER)) break;
4046 tok->type = TK_ANCHOR;
4047 tok->u.anchor = ANCHOR_EXTENDED_GRAPHEME_CLUSTER_BOUNDARY;
4051 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP2_ESC_X_Y_GRAPHEME_CLUSTER)) break;
4052 tok->type = TK_ANCHOR;
4053 tok->u.anchor = ANCHOR_NO_EXTENDED_GRAPHEME_CLUSTER_BOUNDARY;
4056 #ifdef USE_WORD_BEGIN_END
4058 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_LTGT_WORD_BEGIN_END)) break;
4059 tok->type = TK_ANCHOR;
4060 tok->u.anchor = ANCHOR_WORD_BEGIN;
4064 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_LTGT_WORD_BEGIN_END)) break;
4065 tok->type = TK_ANCHOR;
4066 tok->u.anchor = ANCHOR_WORD_END;
4071 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_S_WHITE_SPACE)) break;
4072 tok->type = TK_CHAR_TYPE;
4073 tok->u.prop.ctype = ONIGENC_CTYPE_SPACE;
4074 tok->u.prop.not = 0;
4078 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_S_WHITE_SPACE)) break;
4079 tok->type = TK_CHAR_TYPE;
4080 tok->u.prop.ctype = ONIGENC_CTYPE_SPACE;
4081 tok->u.prop.not = 1;
4085 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_D_DIGIT)) break;
4086 tok->type = TK_CHAR_TYPE;
4087 tok->u.prop.ctype = ONIGENC_CTYPE_DIGIT;
4088 tok->u.prop.not = 0;
4092 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_D_DIGIT)) break;
4093 tok->type = TK_CHAR_TYPE;
4094 tok->u.prop.ctype = ONIGENC_CTYPE_DIGIT;
4095 tok->u.prop.not = 1;
4099 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_H_XDIGIT)) break;
4100 tok->type = TK_CHAR_TYPE;
4101 tok->u.prop.ctype = ONIGENC_CTYPE_XDIGIT;
4102 tok->u.prop.not = 0;
4106 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_H_XDIGIT)) break;
4107 tok->type = TK_CHAR_TYPE;
4108 tok->u.prop.ctype = ONIGENC_CTYPE_XDIGIT;
4109 tok->u.prop.not = 1;
4113 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_CAPITAL_K_KEEP)) break;
4114 tok->type = TK_KEEP;
4118 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_CAPITAL_R_GENERAL_NEWLINE)) break;
4119 tok->type = TK_GENERAL_NEWLINE;
4123 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_CAPITAL_N_O_SUPER_DOT)) break;
4124 tok->type = TK_NO_NEWLINE;
4128 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_CAPITAL_N_O_SUPER_DOT)) break;
4129 tok->type = TK_TRUE_ANYCHAR;
4133 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_X_Y_GRAPHEME_CLUSTER)) break;
4134 tok->type = TK_EXTENDED_GRAPHEME_CLUSTER;
4138 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_AZ_BUF_ANCHOR)) break;
4140 tok->type = TK_ANCHOR;
4141 tok->u.subtype = ANCHOR_BEGIN_BUF;
4145 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_AZ_BUF_ANCHOR)) break;
4146 tok->type = TK_ANCHOR;
4147 tok->u.subtype = ANCHOR_SEMI_END_BUF;
4151 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_AZ_BUF_ANCHOR)) break;
4153 tok->type = TK_ANCHOR;
4154 tok->u.subtype = ANCHOR_END_BUF;
4158 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_CAPITAL_G_BEGIN_ANCHOR)) break;
4159 tok->type = TK_ANCHOR;
4160 tok->u.subtype = ANCHOR_BEGIN_POSITION;
4164 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_GNU_BUF_ANCHOR)) break;
4169 if (! IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_GNU_BUF_ANCHOR)) break;
4177 if (PPEEK_IS('{') && IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_O_BRACE_OCTAL)) {
4179 num = scan_unsigned_octal_number(&p, end, 11, enc);
4180 if (num < 0) return ONIGERR_TOO_BIG_WIDE_CHAR_VALUE;
4182 if (IS_CODE_DIGIT_ASCII(enc, PPEEK))
4183 return ONIGERR_TOO_LONG_WIDE_CHAR_VALUE;
4186 if ((p > prev + enclen(enc, prev)) && !PEND && PPEEK_IS('}')) {
4188 tok->type = TK_CODE_POINT;
4189 tok->u.code = (OnigCodePoint )num;
4192 /* can't read nothing or invalid format */
4202 if (PPEEK_IS('{') && IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_X_BRACE_HEX8)) {
4204 num = scan_unsigned_hexadecimal_number(&p, end, 0, 8, enc);
4206 if (num == ONIGERR_TOO_BIG_NUMBER)
4207 return ONIGERR_TOO_BIG_WIDE_CHAR_VALUE;
4212 if (IS_CODE_XDIGIT_ASCII(enc, PPEEK))
4213 return ONIGERR_TOO_LONG_WIDE_CHAR_VALUE;
4216 if ((p > prev + enclen(enc, prev)) && !PEND && PPEEK_IS('}')) {
4218 tok->type = TK_CODE_POINT;
4219 tok->u.code = (OnigCodePoint )num;
4222 /* can't read nothing or invalid format */
4226 else if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_X_HEX2)) {
4227 num = scan_unsigned_hexadecimal_number(&p, end, 0, 2, enc);
4228 if (num < 0) return num;
4229 if (p == prev) { /* can't read nothing. */
4230 num = 0; /* but, it's not error */
4232 tok->type = TK_RAW_BYTE;
4242 if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_U_HEX4)) {
4243 num = scan_unsigned_hexadecimal_number(&p, end, 4, 4, enc);
4244 if (num < 0) return num;
4245 if (p == prev) { /* can't read nothing. */
4246 num = 0; /* but, it's not error */
4248 tok->type = TK_CODE_POINT;
4250 tok->u.code = (OnigCodePoint )num;
4254 case '1': case '2': case '3': case '4':
4255 case '5': case '6': case '7': case '8': case '9':
4258 num = onig_scan_unsigned_number(&p, end, enc);
4259 if (num < 0 || num > ONIG_MAX_BACKREF_NUM) {
4263 if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_DECIMAL_BACKREF) &&
4264 (num <= env->num_mem || num <= 9)) { /* This spec. from GNU regex */
4265 if (IS_SYNTAX_BV(syn, ONIG_SYN_STRICT_CHECK_BACKREF)) {
4266 if (num > env->num_mem || IS_NULL(SCANENV_MEMENV(env)[num].node))
4267 return ONIGERR_INVALID_BACKREF;
4270 tok->type = TK_BACKREF;
4271 tok->u.backref.num = 1;
4272 tok->u.backref.ref1 = num;
4273 tok->u.backref.by_name = 0;
4274 #ifdef USE_BACKREF_WITH_LEVEL
4275 tok->u.backref.exist_level = 0;
4281 if (c == '8' || c == '9') {
4290 if (IS_SYNTAX_OP(syn, ONIG_SYN_OP_ESC_OCTAL3)) {
4292 num = scan_unsigned_octal_number(&p, end, (c == '0' ? 2:3), enc);
4293 if (num < 0 || num >= 256) return ONIGERR_TOO_BIG_NUMBER;
4294 if (p == prev) { /* can't read nothing. */
4295 num = 0; /* but, it's not error */
4297 tok->type = TK_RAW_BYTE;
4301 else if (c != '0') {
4307 if (!PEND && IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_K_NAMED_BACKREF)) {
4309 if (c == '<' || c == '\'') {
4313 enum REF_NUM num_type;
4317 #ifdef USE_BACKREF_WITH_LEVEL
4318 name_end = NULL_UCHARP; /* no need. escape gcc warning. */
4319 r = fetch_name_with_level((OnigCodePoint )c, &p, end, &name_end,
4320 env, &back_num, &tok->u.backref.level, &num_type);
4321 if (r == 1) tok->u.backref.exist_level = 1;
4322 else tok->u.backref.exist_level = 0;
4324 r = fetch_name(c, &p, end, &name_end, env, &back_num, &num_type, 1);
4326 if (r < 0) return r;
4328 if (num_type != IS_NOT_NUM) {
4329 if (num_type == IS_REL_NUM) {
4330 back_num = backref_rel_to_abs(back_num, env);
4333 return ONIGERR_INVALID_BACKREF;
4335 if (IS_SYNTAX_BV(syn, ONIG_SYN_STRICT_CHECK_BACKREF)) {
4336 if (back_num > env->num_mem ||
4337 IS_NULL(SCANENV_MEMENV(env)[back_num].node))
4338 return ONIGERR_INVALID_BACKREF;
4340 tok->type = TK_BACKREF;
4341 tok->u.backref.by_name = 0;
4342 tok->u.backref.num = 1;
4343 tok->u.backref.ref1 = back_num;
4346 num = onig_name_to_group_numbers(env->reg, prev, name_end, &backs);
4348 onig_scan_env_set_error_string(env,
4349 ONIGERR_UNDEFINED_NAME_REFERENCE, prev, name_end);
4350 return ONIGERR_UNDEFINED_NAME_REFERENCE;
4352 if (IS_SYNTAX_BV(syn, ONIG_SYN_STRICT_CHECK_BACKREF)) {
4354 for (i = 0; i < num; i++) {
4355 if (backs[i] > env->num_mem ||
4356 IS_NULL(SCANENV_MEMENV(env)[backs[i]].node))
4357 return ONIGERR_INVALID_BACKREF;
4361 tok->type = TK_BACKREF;
4362 tok->u.backref.by_name = 1;
4364 tok->u.backref.num = 1;
4365 tok->u.backref.ref1 = backs[0];
4368 tok->u.backref.num = num;
4369 tok->u.backref.refs = backs;
4380 if (!PEND && IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_G_SUBEXP_CALL)) {
4382 if (c == '<' || c == '\'') {
4385 enum REF_NUM num_type;
4388 r = fetch_name((OnigCodePoint )c, &p, end, &name_end, env,
4389 &gnum, &num_type, 1);
4390 if (r < 0) return r;
4392 if (num_type != IS_NOT_NUM) {
4393 if (num_type == IS_REL_NUM) {
4394 gnum = backref_rel_to_abs(gnum, env);
4396 return ONIGERR_UNDEFINED_GROUP_REFERENCE;
4398 tok->u.call.by_number = 1;
4399 tok->u.call.gnum = gnum;
4402 tok->u.call.by_number = 0;
4403 tok->u.call.gnum = 0;
4406 tok->type = TK_CALL;
4407 tok->u.call.name = prev;
4408 tok->u.call.name_end = name_end;
4417 if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_CAPITAL_Q_QUOTE)) {
4418 tok->type = TK_QUOTE_OPEN;
4424 if (!PEND && PPEEK_IS('{') &&
4425 IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_P_BRACE_CHAR_PROPERTY)) {
4427 tok->type = TK_CHAR_PROPERTY;
4428 tok->u.prop.not = (c == 'P' ? 1 : 0);
4431 IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_ESC_P_BRACE_CIRCUMFLEX_NOT)) {
4434 tok->u.prop.not = (tok->u.prop.not == 0 ? 1 : 0);
4447 num = fetch_escaped_value(&p, end, env, &c2);
4448 if (num < 0) return num;
4450 if (tok->u.c != c2) {
4451 tok->type = TK_CODE_POINT;
4455 p = tok->backp + enclen(enc, tok->backp);
4465 #ifdef USE_VARIABLE_META_CHARS
4466 if ((c != ONIG_INEFFECTIVE_META_CHAR) &&
4467 IS_SYNTAX_OP(syn, ONIG_SYN_OP_VARIABLE_META_CHARACTERS)) {
4468 if (c == MC_ANYCHAR(syn))
4470 else if (c == MC_ANYTIME(syn))
4472 else if (c == MC_ZERO_OR_ONE_TIME(syn))
4473 goto zero_or_one_time;
4474 else if (c == MC_ONE_OR_MORE_TIME(syn))
4475 goto one_or_more_time;
4476 else if (c == MC_ANYCHAR_ANYTIME(syn)) {
4477 tok->type = TK_ANYCHAR_ANYTIME;
4485 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_DOT_ANYCHAR)) break;
4486 #ifdef USE_VARIABLE_META_CHARS
4489 tok->type = TK_ANYCHAR;
4493 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_ASTERISK_ZERO_INF)) break;
4494 #ifdef USE_VARIABLE_META_CHARS
4497 tok->type = TK_OP_REPEAT;
4498 tok->u.repeat.lower = 0;
4499 tok->u.repeat.upper = REPEAT_INFINITE;
4504 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_PLUS_ONE_INF)) break;
4505 #ifdef USE_VARIABLE_META_CHARS
4508 tok->type = TK_OP_REPEAT;
4509 tok->u.repeat.lower = 1;
4510 tok->u.repeat.upper = REPEAT_INFINITE;
4515 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_QMARK_ZERO_ONE)) break;
4516 #ifdef USE_VARIABLE_META_CHARS
4519 tok->type = TK_OP_REPEAT;
4520 tok->u.repeat.lower = 0;
4521 tok->u.repeat.upper = 1;
4526 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_BRACE_INTERVAL)) break;
4527 r = fetch_range_quantifier(&p, end, tok, env);
4528 if (r < 0) return r; /* error */
4529 if (r == 0) goto greedy_check;
4530 else if (r == 2) { /* {n} */
4531 if (IS_SYNTAX_BV(syn, ONIG_SYN_FIXED_INTERVAL_IS_GREEDY_ONLY))
4532 goto possessive_check;
4536 /* r == 1 : normal char */
4540 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_VBAR_ALT)) break;
4545 if (!PEND && PPEEK_IS('?') &&
4546 IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_QMARK_GROUP_EFFECT)) {
4553 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
4555 if (c == MC_ESC(syn)) {
4556 if (! PEND) PFETCH(c);
4559 if (c == ')') break;
4564 else if (IS_SYNTAX_OP2(syn, ONIG_SYN_OP2_QMARK_PERL_SUBEXP_CALL)) {
4568 enum REF_NUM num_type;
4575 r = fetch_name((OnigCodePoint )'(', &p, end, &name_end, env, &gnum,
4577 if (r < 0) return r;
4579 tok->type = TK_CALL;
4580 tok->u.call.by_number = 0;
4581 tok->u.call.gnum = 0;
4582 tok->u.call.name = name;
4583 tok->u.call.name_end = name_end;
4588 tok->type = TK_CALL;
4589 tok->u.call.by_number = 1;
4590 tok->u.call.gnum = 0;
4591 tok->u.call.name = p;
4593 if (! PPEEK_IS(')')) return ONIGERR_INVALID_GROUP_NAME;
4594 tok->u.call.name_end = p;
4599 goto lparen_qmark_num;
4602 if (! ONIGENC_IS_CODE_DIGIT(enc, c)) goto lparen_qmark_end;
4607 r = fetch_name((OnigCodePoint )'(', &p, end, &name_end, env,
4608 &gnum, &num_type, 1);
4609 if (r < 0) return r;
4611 if (num_type == IS_NOT_NUM) {
4612 return ONIGERR_INVALID_GROUP_NAME;
4615 if (num_type == IS_REL_NUM) {
4616 gnum = backref_rel_to_abs(gnum, env);
4618 return ONIGERR_UNDEFINED_GROUP_REFERENCE;
4620 tok->u.call.by_number = 1;
4621 tok->u.call.gnum = gnum;
4624 tok->type = TK_CALL;
4625 tok->u.call.name = name;
4626 tok->u.call.name_end = name_end;
4636 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_LPAREN_SUBEXP)) break;
4637 tok->type = TK_SUBEXP_OPEN;
4641 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_LPAREN_SUBEXP)) break;
4642 tok->type = TK_SUBEXP_CLOSE;
4646 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_LINE_ANCHOR)) break;
4647 tok->type = TK_ANCHOR;
4648 tok->u.subtype = (IS_SINGLELINE(env->options)
4649 ? ANCHOR_BEGIN_BUF : ANCHOR_BEGIN_LINE);
4653 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_LINE_ANCHOR)) break;
4654 tok->type = TK_ANCHOR;
4655 tok->u.subtype = (IS_SINGLELINE(env->options)
4656 ? ANCHOR_SEMI_END_BUF : ANCHOR_END_LINE);
4660 if (! IS_SYNTAX_OP(syn, ONIG_SYN_OP_BRACKET_CC)) break;
4661 tok->type = TK_CC_OPEN;
4665 if (*src > env->pattern) /* /].../ is allowed. */
4666 CLOSE_BRACKET_WITHOUT_ESC_WARN(env, (UChar* )"]");
4670 if (IS_EXTEND(env->options)) {
4673 if (ONIGENC_IS_CODE_NEWLINE(enc, c))
4681 case ' ': case '\t': case '\n': case '\r': case '\f':
4682 if (IS_EXTEND(env->options))
4692 #ifdef USE_VARIABLE_META_CHARS
4700 add_ctype_to_cc_by_range(CClassNode* cc, int ctype ARG_UNUSED, int not,
4701 OnigEncoding enc ARG_UNUSED, OnigCodePoint sb_out,
4702 const OnigCodePoint mbr[])
4707 int n = ONIGENC_CODE_RANGE_NUM(mbr);
4710 for (i = 0; i < n; i++) {
4711 for (j = ONIGENC_CODE_RANGE_FROM(mbr, i);
4712 j <= ONIGENC_CODE_RANGE_TO(mbr, i); j++) {
4714 if (j > ONIGENC_CODE_RANGE_FROM(mbr, i)) {
4715 r = add_code_range_to_buf(&(cc->mbuf), j,
4716 ONIGENC_CODE_RANGE_TO(mbr, i));
4717 if (r != 0) return r;
4723 BITSET_SET_BIT(cc->bs, j);
4728 for ( ; i < n; i++) {
4729 r = add_code_range_to_buf(&(cc->mbuf),
4730 ONIGENC_CODE_RANGE_FROM(mbr, i),
4731 ONIGENC_CODE_RANGE_TO(mbr, i));
4732 if (r != 0) return r;
4736 OnigCodePoint prev = 0;
4738 for (i = 0; i < n; i++) {
4739 for (j = prev; j < ONIGENC_CODE_RANGE_FROM(mbr, i); j++) {
4743 BITSET_SET_BIT(cc->bs, j);
4745 prev = ONIGENC_CODE_RANGE_TO(mbr, i) + 1;
4747 for (j = prev; j < sb_out; j++) {
4748 BITSET_SET_BIT(cc->bs, j);
4754 for (i = 0; i < n; i++) {
4755 if (prev < ONIGENC_CODE_RANGE_FROM(mbr, i)) {
4756 r = add_code_range_to_buf(&(cc->mbuf), prev,
4757 ONIGENC_CODE_RANGE_FROM(mbr, i) - 1);
4758 if (r != 0) return r;
4760 prev = ONIGENC_CODE_RANGE_TO(mbr, i) + 1;
4761 if (prev == 0) goto end;
4764 r = add_code_range_to_buf(&(cc->mbuf), prev, MAX_CODE_POINT);
4765 if (r != 0) return r;
4773 add_ctype_to_cc_by_range_limit(CClassNode* cc, int ctype ARG_UNUSED, int not,
4774 OnigEncoding enc ARG_UNUSED,
4775 OnigCodePoint sb_out,
4776 const OnigCodePoint mbr[], OnigCodePoint limit)
4783 int n = ONIGENC_CODE_RANGE_NUM(mbr);
4786 for (i = 0; i < n; i++) {
4787 for (j = ONIGENC_CODE_RANGE_FROM(mbr, i);
4788 j <= ONIGENC_CODE_RANGE_TO(mbr, i); j++) {
4789 if (j > limit) goto end;
4791 if (j > ONIGENC_CODE_RANGE_FROM(mbr, i)) {
4792 to = ONIGENC_CODE_RANGE_TO(mbr, i);
4793 if (to > limit) to = limit;
4794 r = add_code_range_to_buf(&(cc->mbuf), j, to);
4795 if (r != 0) return r;
4801 BITSET_SET_BIT(cc->bs, j);
4806 for ( ; i < n; i++) {
4807 from = ONIGENC_CODE_RANGE_FROM(mbr, i);
4808 to = ONIGENC_CODE_RANGE_TO(mbr, i);
4809 if (from > limit) break;
4810 if (to > limit) to = limit;
4811 r = add_code_range_to_buf(&(cc->mbuf), from, to);
4812 if (r != 0) return r;
4816 OnigCodePoint prev = 0;
4818 for (i = 0; i < n; i++) {
4819 from = ONIGENC_CODE_RANGE_FROM(mbr, i);
4821 for (j = prev; j < sb_out; j++) {
4822 BITSET_SET_BIT(cc->bs, j);
4826 for (j = prev; j < from; j++) {
4827 if (j >= sb_out) goto sb_end2;
4828 BITSET_SET_BIT(cc->bs, j);
4830 prev = ONIGENC_CODE_RANGE_TO(mbr, i);
4831 if (prev > limit) prev = limit;
4833 if (prev == 0) goto end;
4835 for (j = prev; j < sb_out; j++) {
4836 BITSET_SET_BIT(cc->bs, j);
4842 for (i = 0; i < n; i++) {
4843 from = ONIGENC_CODE_RANGE_FROM(mbr, i);
4844 if (from > limit) goto last;
4847 r = add_code_range_to_buf(&(cc->mbuf), prev, from - 1);
4848 if (r != 0) return r;
4850 prev = ONIGENC_CODE_RANGE_TO(mbr, i);
4851 if (prev > limit) prev = limit;
4853 if (prev == 0) goto end;
4857 r = add_code_range_to_buf(&(cc->mbuf), prev, MAX_CODE_POINT);
4858 if (r != 0) return r;
4866 add_ctype_to_cc(CClassNode* cc, int ctype, int not, ScanEnv* env)
4868 #define ASCII_LIMIT 127
4872 const OnigCodePoint *ranges;
4873 OnigCodePoint limit;
4874 OnigCodePoint sb_out;
4875 OnigEncoding enc = env->enc;
4877 ascii_mode = IS_ASCII_MODE_CTYPE_OPTION(ctype, env->options);
4879 r = ONIGENC_GET_CTYPE_CODE_RANGE(enc, ctype, &sb_out, &ranges);
4881 if (ascii_mode == 0)
4882 r = add_ctype_to_cc_by_range(cc, ctype, not, env->enc, sb_out, ranges);
4884 r = add_ctype_to_cc_by_range_limit(cc, ctype, not, env->enc, sb_out,
4885 ranges, ASCII_LIMIT);
4888 else if (r != ONIG_NO_SUPPORT_CONFIG) {
4893 limit = ascii_mode ? ASCII_LIMIT : SINGLE_BYTE_SIZE;
4896 case ONIGENC_CTYPE_ALPHA:
4897 case ONIGENC_CTYPE_BLANK:
4898 case ONIGENC_CTYPE_CNTRL:
4899 case ONIGENC_CTYPE_DIGIT:
4900 case ONIGENC_CTYPE_LOWER:
4901 case ONIGENC_CTYPE_PUNCT:
4902 case ONIGENC_CTYPE_SPACE:
4903 case ONIGENC_CTYPE_UPPER:
4904 case ONIGENC_CTYPE_XDIGIT:
4905 case ONIGENC_CTYPE_ASCII:
4906 case ONIGENC_CTYPE_ALNUM:
4908 for (c = 0; c < (int )limit; c++) {
4909 if (! ONIGENC_IS_CODE_CTYPE(enc, (OnigCodePoint )c, ctype))
4910 BITSET_SET_BIT(cc->bs, c);
4912 for (c = limit; c < SINGLE_BYTE_SIZE; c++) {
4913 BITSET_SET_BIT(cc->bs, c);
4916 ADD_ALL_MULTI_BYTE_RANGE(enc, cc->mbuf);
4919 for (c = 0; c < (int )limit; c++) {
4920 if (ONIGENC_IS_CODE_CTYPE(enc, (OnigCodePoint )c, ctype))
4921 BITSET_SET_BIT(cc->bs, c);
4926 case ONIGENC_CTYPE_GRAPH:
4927 case ONIGENC_CTYPE_PRINT:
4928 case ONIGENC_CTYPE_WORD:
4930 for (c = 0; c < (int )limit; c++) {
4931 if (ONIGENC_CODE_TO_MBCLEN(enc, c) > 0 /* check invalid code point */
4932 && ! ONIGENC_IS_CODE_CTYPE(enc, (OnigCodePoint )c, ctype))
4933 BITSET_SET_BIT(cc->bs, c);
4935 for (c = limit; c < SINGLE_BYTE_SIZE; c++) {
4936 if (ONIGENC_CODE_TO_MBCLEN(enc, c) > 0)
4937 BITSET_SET_BIT(cc->bs, c);
4941 for (c = 0; c < (int )limit; c++) {
4942 if (ONIGENC_IS_CODE_CTYPE(enc, (OnigCodePoint )c, ctype))
4943 BITSET_SET_BIT(cc->bs, c);
4945 if (ascii_mode == 0)
4946 ADD_ALL_MULTI_BYTE_RANGE(enc, cc->mbuf);
4951 return ONIGERR_PARSER_BUG;
4959 parse_posix_bracket(CClassNode* cc, UChar** src, UChar* end, ScanEnv* env)
4961 #define POSIX_BRACKET_CHECK_LIMIT_LENGTH 20
4962 #define POSIX_BRACKET_NAME_MIN_LEN 4
4964 static PosixBracketEntryType PBS[] = {
4965 { (UChar* )"alnum", ONIGENC_CTYPE_ALNUM, 5 },
4966 { (UChar* )"alpha", ONIGENC_CTYPE_ALPHA, 5 },
4967 { (UChar* )"blank", ONIGENC_CTYPE_BLANK, 5 },
4968 { (UChar* )"cntrl", ONIGENC_CTYPE_CNTRL, 5 },
4969 { (UChar* )"digit", ONIGENC_CTYPE_DIGIT, 5 },
4970 { (UChar* )"graph", ONIGENC_CTYPE_GRAPH, 5 },
4971 { (UChar* )"lower", ONIGENC_CTYPE_LOWER, 5 },
4972 { (UChar* )"print", ONIGENC_CTYPE_PRINT, 5 },
4973 { (UChar* )"punct", ONIGENC_CTYPE_PUNCT, 5 },
4974 { (UChar* )"space", ONIGENC_CTYPE_SPACE, 5 },
4975 { (UChar* )"upper", ONIGENC_CTYPE_UPPER, 5 },
4976 { (UChar* )"xdigit", ONIGENC_CTYPE_XDIGIT, 6 },
4977 { (UChar* )"ascii", ONIGENC_CTYPE_ASCII, 5 },
4978 { (UChar* )"word", ONIGENC_CTYPE_WORD, 4 },
4979 { (UChar* )NULL, -1, 0 }
4982 PosixBracketEntryType *pb;
4985 OnigEncoding enc = env->enc;
4988 if (PPEEK_IS('^')) {
4995 if (onigenc_strlen(enc, p, end) < POSIX_BRACKET_NAME_MIN_LEN + 3)
4996 goto not_posix_bracket;
4998 for (pb = PBS; IS_NOT_NULL(pb->name); pb++) {
4999 if (onigenc_with_ascii_strncmp(enc, p, end, pb->name, pb->len) == 0) {
5000 p = (UChar* )onigenc_step(enc, p, end, pb->len);
5001 if (onigenc_with_ascii_strncmp(enc, p, end, (UChar* )":]", 2) != 0)
5002 return ONIGERR_INVALID_POSIX_BRACKET_TYPE;
5004 r = add_ctype_to_cc(cc, pb->ctype, not, env);
5005 if (r != 0) return r;
5016 while (!PEND && ((c = PPEEK) != ':') && c != ']') {
5018 if (++i > POSIX_BRACKET_CHECK_LIMIT_LENGTH) break;
5020 if (c == ':' && ! PEND) {
5025 return ONIGERR_INVALID_POSIX_BRACKET_TYPE;
5029 return 1; /* 1: is not POSIX bracket, but no error. */
5033 fetch_char_property_to_ctype(UChar** src, UChar* end, ScanEnv* env)
5037 OnigEncoding enc = env->enc;
5038 UChar *prev, *start, *p = *src;
5047 r = ONIGENC_PROPERTY_NAME_TO_CTYPE(enc, start, prev);
5053 else if (c == '(' || c == ')' || c == '{' || c == '|') {
5054 r = ONIGERR_INVALID_CHAR_PROPERTY_NAME;
5059 onig_scan_env_set_error_string(env, r, *src, prev);
5064 parse_char_property(Node** np, OnigToken* tok, UChar** src, UChar* end, ScanEnv* env)
5069 ctype = fetch_char_property_to_ctype(src, end, env);
5070 if (ctype < 0) return ctype;
5072 *np = node_new_cclass();
5073 CHECK_NULL_RETURN_MEMERR(*np);
5075 r = add_ctype_to_cc(cc, ctype, 0, env);
5076 if (r != 0) return r;
5077 if (tok->u.prop.not != 0) NCCLASS_SET_NOT(cc);
5097 next_state_class(CClassNode* cc, OnigCodePoint* vs, enum CCVALTYPE* type,
5098 enum CCSTATE* state, ScanEnv* env)
5102 if (*state == CCS_RANGE)
5103 return ONIGERR_CHAR_CLASS_VALUE_AT_END_OF_RANGE;
5105 if (*state == CCS_VALUE && *type != CCV_CLASS) {
5106 if (*type == CCV_SB)
5107 BITSET_SET_BIT(cc->bs, (int )(*vs));
5108 else if (*type == CCV_CODE_POINT) {
5109 r = add_code_range(&(cc->mbuf), env, *vs, *vs);
5110 if (r < 0) return r;
5120 next_state_val(CClassNode* cc, OnigCodePoint *from, OnigCodePoint to,
5121 int* from_israw, int to_israw,
5122 enum CCVALTYPE intype, enum CCVALTYPE* type,
5123 enum CCSTATE* state, ScanEnv* env)
5129 if (*type == CCV_SB) {
5131 return ONIGERR_INVALID_CODE_POINT_VALUE;
5133 BITSET_SET_BIT(cc->bs, (int )(*from));
5135 else if (*type == CCV_CODE_POINT) {
5136 r = add_code_range(&(cc->mbuf), env, *from, *from);
5137 if (r < 0) return r;
5142 if (intype == *type) {
5143 if (intype == CCV_SB) {
5144 if (*from > 0xff || to > 0xff)
5145 return ONIGERR_INVALID_CODE_POINT_VALUE;
5148 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_EMPTY_RANGE_IN_CC))
5151 return ONIGERR_EMPTY_RANGE_IN_CHAR_CLASS;
5153 bitset_set_range(cc->bs, (int )*from, (int )to);
5156 r = add_code_range(&(cc->mbuf), env, *from, to);
5157 if (r < 0) return r;
5162 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_EMPTY_RANGE_IN_CC))
5165 return ONIGERR_EMPTY_RANGE_IN_CHAR_CLASS;
5167 bitset_set_range(cc->bs, (int )*from, (int )(to < 0xff ? to : 0xff));
5168 r = add_code_range(&(cc->mbuf), env, (OnigCodePoint )*from, to);
5169 if (r < 0) return r;
5172 *state = CCS_COMPLETE;
5184 *from_israw = to_israw;
5191 code_exist_check(OnigCodePoint c, UChar* from, UChar* end, int ignore_escaped,
5196 OnigEncoding enc = env->enc;
5201 if (ignore_escaped && in_esc) {
5206 if (code == c) return 1;
5207 if (code == MC_ESC(env->syntax)) in_esc = 1;
5214 parse_char_class(Node** np, OnigToken* tok, UChar** src, UChar* end, ScanEnv* env)
5216 int r, neg, len, fetched, and_start;
5217 OnigCodePoint v, vs;
5220 CClassNode *cc, *prev_cc;
5224 enum CCVALTYPE val_type, in_type;
5225 int val_israw, in_israw;
5229 if (env->parse_depth > ParseDepthLimit)
5230 return ONIGERR_PARSE_DEPTH_LIMIT_OVER;
5231 prev_cc = (CClassNode* )NULL;
5232 r = fetch_token_in_cc(tok, src, end, env);
5233 if (r == TK_CHAR && tok->u.c == '^' && tok->escaped == 0) {
5235 r = fetch_token_in_cc(tok, src, end, env);
5241 if (r < 0) return r;
5242 if (r == TK_CC_CLOSE) {
5243 if (! code_exist_check((OnigCodePoint )']',
5244 *src, env->pattern_end, 1, env))
5245 return ONIGERR_EMPTY_CHAR_CLASS;
5247 CC_ESC_WARN(env, (UChar* )"]");
5248 r = tok->type = TK_CHAR; /* allow []...] */
5251 *np = node = node_new_cclass();
5252 CHECK_NULL_RETURN_MEMERR(node);
5258 while (r != TK_CC_CLOSE) {
5263 len = ONIGENC_CODE_TO_MBCLEN(env->enc, tok->u.c);
5265 in_type = CCV_CODE_POINT;
5275 v = (OnigCodePoint )tok->u.c;
5281 /* tok->base != 0 : octal or hexadec. */
5282 if (! ONIGENC_IS_SINGLEBYTE(env->enc) && tok->base != 0) {
5283 UChar buf[ONIGENC_CODE_TO_MBC_MAXLEN];
5284 UChar* bufe = buf + ONIGENC_CODE_TO_MBC_MAXLEN;
5286 int i, base = tok->base;
5289 for (i = 1; i < ONIGENC_MBC_MAXLEN(env->enc); i++) {
5290 r = fetch_token_in_cc(tok, &p, end, env);
5291 if (r < 0) goto err;
5292 if (r != TK_RAW_BYTE || tok->base != base) {
5299 if (i < ONIGENC_MBC_MINLEN(env->enc)) {
5300 r = ONIGERR_TOO_SHORT_MULTI_BYTE_STRING;
5304 len = enclen(env->enc, buf);
5306 r = ONIGERR_TOO_SHORT_MULTI_BYTE_STRING;
5309 else if (i > len) { /* fetch back */
5311 for (i = 1; i < len; i++) {
5312 r = fetch_token_in_cc(tok, &p, end, env);
5318 v = (OnigCodePoint )buf[0];
5322 v = ONIGENC_MBC_TO_CODE(env->enc, buf, bufe);
5323 in_type = CCV_CODE_POINT;
5327 v = (OnigCodePoint )tok->u.c;
5339 len = ONIGENC_CODE_TO_MBCLEN(env->enc, v);
5344 in_type = (len == 1 ? CCV_SB : CCV_CODE_POINT);
5346 r = next_state_val(cc, &vs, v, &val_israw, in_israw, in_type, &val_type,
5348 if (r != 0) goto err;
5351 case TK_POSIX_BRACKET_OPEN:
5352 r = parse_posix_bracket(cc, &p, end, env);
5353 if (r < 0) goto err;
5354 if (r == 1) { /* is not POSIX bracket */
5355 CC_ESC_WARN(env, (UChar* )"[");
5357 v = (OnigCodePoint )tok->u.c;
5365 r = add_ctype_to_cc(cc, tok->u.prop.ctype, tok->u.prop.not, env);
5366 if (r != 0) goto err;
5369 r = next_state_class(cc, &vs, &val_type, &state, env);
5370 if (r != 0) goto err;
5373 case TK_CHAR_PROPERTY:
5375 int ctype = fetch_char_property_to_ctype(&p, end, env);
5380 r = add_ctype_to_cc(cc, ctype, tok->u.prop.not, env);
5381 if (r != 0) goto err;
5387 if (state == CCS_VALUE) {
5388 r = fetch_token_in_cc(tok, &p, end, env);
5389 if (r < 0) goto err;
5391 if (r == TK_CC_CLOSE) { /* allow [x-] */
5393 v = (OnigCodePoint )'-';
5397 else if (r == TK_CC_AND) {
5398 CC_ESC_WARN(env, (UChar* )"-");
5402 if (val_type == CCV_CLASS) {
5403 r = ONIGERR_UNMATCHED_RANGE_SPECIFIER_IN_CHAR_CLASS;
5409 else if (state == CCS_START) {
5410 /* [-xa] is allowed */
5411 v = (OnigCodePoint )tok->u.c;
5414 r = fetch_token_in_cc(tok, &p, end, env);
5415 if (r < 0) goto err;
5417 /* [--x] or [a&&-x] is warned. */
5418 if (r == TK_CC_RANGE || and_start != 0)
5419 CC_ESC_WARN(env, (UChar* )"-");
5423 else if (state == CCS_RANGE) {
5424 CC_ESC_WARN(env, (UChar* )"-");
5425 goto any_char_in; /* [!--x] is allowed */
5427 else { /* CCS_COMPLETE */
5428 r = fetch_token_in_cc(tok, &p, end, env);
5429 if (r < 0) goto err;
5431 if (r == TK_CC_CLOSE) goto range_end_val; /* allow [a-b-] */
5432 else if (r == TK_CC_AND) {
5433 CC_ESC_WARN(env, (UChar* )"-");
5437 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_DOUBLE_RANGE_OP_IN_CC)) {
5438 CC_ESC_WARN(env, (UChar* )"-");
5439 goto range_end_val; /* [0-9-a] is allowed as [0-9\-a] */
5441 r = ONIGERR_UNMATCHED_RANGE_SPECIFIER_IN_CHAR_CLASS;
5446 case TK_CC_CC_OPEN: /* [ */
5451 r = parse_char_class(&anode, tok, &p, end, env);
5453 onig_node_free(anode);
5456 acc = CCLASS_(anode);
5457 r = or_cclass(cc, acc, env->enc);
5458 onig_node_free(anode);
5461 if (r != 0) goto err;
5465 case TK_CC_AND: /* && */
5467 if (state == CCS_VALUE) {
5468 r = next_state_val(cc, &vs, 0, &val_israw, 0, val_type,
5469 &val_type, &state, env);
5470 if (r != 0) goto err;
5472 /* initialize local variables */
5476 if (IS_NOT_NULL(prev_cc)) {
5477 r = and_cclass(prev_cc, cc, env->enc);
5478 if (r != 0) goto err;
5479 bbuf_free(cc->mbuf);
5485 initialize_cclass(cc);
5490 r = ONIGERR_PREMATURE_END_OF_CHAR_CLASS;
5494 r = ONIGERR_PARSER_BUG;
5502 r = fetch_token_in_cc(tok, &p, end, env);
5503 if (r < 0) goto err;
5507 if (state == CCS_VALUE) {
5508 r = next_state_val(cc, &vs, 0, &val_israw, 0, val_type,
5509 &val_type, &state, env);
5510 if (r != 0) goto err;
5513 if (IS_NOT_NULL(prev_cc)) {
5514 r = and_cclass(prev_cc, cc, env->enc);
5515 if (r != 0) goto err;
5516 bbuf_free(cc->mbuf);
5521 NCCLASS_SET_NOT(cc);
5523 NCCLASS_CLEAR_NOT(cc);
5524 if (IS_NCCLASS_NOT(cc) &&
5525 IS_SYNTAX_BV(env->syntax, ONIG_SYN_NOT_NEWLINE_IN_NEGATIVE_CC)) {
5526 int is_empty = (IS_NULL(cc->mbuf) ? 1 : 0);
5528 BITSET_IS_EMPTY(cc->bs, is_empty);
5530 if (is_empty == 0) {
5531 #define NEWLINE_CODE 0x0a
5533 if (ONIGENC_IS_CODE_NEWLINE(env->enc, NEWLINE_CODE)) {
5534 if (ONIGENC_CODE_TO_MBCLEN(env->enc, NEWLINE_CODE) == 1)
5535 BITSET_SET_BIT(cc->bs, NEWLINE_CODE);
5537 add_code_range(&(cc->mbuf), env, NEWLINE_CODE, NEWLINE_CODE);
5546 if (cc != CCLASS_(*np))
5547 bbuf_free(cc->mbuf);
5551 static int parse_subexp(Node** top, OnigToken* tok, int term,
5552 UChar** src, UChar* end, ScanEnv* env);
5554 /* (?{...}) (?{{...}}) */
5556 parse_code_callout(Node** np, int cterm, UChar** src, UChar* end, ScanEnv* env)
5564 OnigEncoding enc = env->enc;
5569 if (PEND) return ONIGERR_INVALID_CALLOUT_PATTERN;
5572 while (PPEEK_IS('{')) {
5575 if (PEND) return ONIGERR_INVALID_CALLOUT_PATTERN;
5580 if (PEND) return ONIGERR_INVALID_CALLOUT_PATTERN;
5587 if (PEND) return ONIGERR_INVALID_CALLOUT_PATTERN;
5596 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5599 return ONIGERR_INVALID_CALLOUT_PATTERN;
5601 r = node_new_callout(np, CALLOUT_CODE, env);
5602 if (r != 0) return r;
5604 GIMMICK_(*np)->start = code_start - env->pattern;
5605 GIMMICK_(*np)->end = code_end - env->pattern;
5612 parse_enclosure(Node** np, OnigToken* tok, int term, UChar** src, UChar* end,
5617 OnigOptionType option;
5620 OnigEncoding enc = env->enc;
5626 if (PEND) return ONIGERR_END_PATTERN_WITH_UNMATCHED_PARENTHESIS;
5628 option = env->options;
5629 if (PPEEK_IS('?') &&
5630 IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_GROUP_EFFECT)) {
5632 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5636 case ':': /* (?:...) grouping only */
5638 r = fetch_token(tok, &p, end, env);
5639 if (r < 0) return r;
5640 r = parse_subexp(np, tok, term, &p, end, env);
5641 if (r < 0) return r;
5643 return 1; /* group */
5647 *np = onig_node_new_anchor(ANCHOR_PREC_READ, 0);
5649 case '!': /* preceding read */
5650 *np = onig_node_new_anchor(ANCHOR_PREC_READ_NOT, 0);
5652 case '>': /* (?>...) stop backtrack */
5653 *np = node_new_enclosure(ENCLOSURE_STOP_BACKTRACK);
5657 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_LT_NAMED_GROUP)) {
5661 return ONIGERR_UNDEFINED_GROUP_OPTION;
5664 case '<': /* look behind (?<=...), (?<!...) */
5665 if (PEND) return ONIGERR_END_PATTERN_WITH_UNMATCHED_PARENTHESIS;
5668 *np = onig_node_new_anchor(ANCHOR_LOOK_BEHIND, 0);
5670 *np = onig_node_new_anchor(ANCHOR_LOOK_BEHIND_NOT, 0);
5672 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_LT_NAMED_GROUP)) {
5675 enum REF_NUM num_type;
5685 r = fetch_name((OnigCodePoint )c, &p, end, &name_end, env, &num,
5687 if (r < 0) return r;
5689 num = scan_env_add_mem_entry(env);
5690 if (num < 0) return num;
5691 if (list_capture != 0 && num >= (int )MEM_STATUS_BITS_NUM)
5692 return ONIGERR_GROUP_NUMBER_OVER_FOR_CAPTURE_HISTORY;
5694 r = name_add(env->reg, name, name_end, num, env);
5695 if (r != 0) return r;
5696 *np = node_new_memory(1);
5697 CHECK_NULL_RETURN_MEMERR(*np);
5698 ENCLOSURE_(*np)->m.regnum = num;
5699 if (list_capture != 0)
5700 MEM_STATUS_ON_SIMPLE(env->capture_history, num);
5704 return ONIGERR_UNDEFINED_GROUP_OPTION;
5710 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_TILDE_ABSENT_GROUP)) {
5714 int is_range_cutter;
5716 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5718 if (PPEEK_IS('|')) { // (?~|generator|absent)
5720 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5723 if (PPEEK_IS(')')) { // (?~|) : range clear
5725 r = make_range_clear(np, env);
5726 if (r != 0) return r;
5733 r = fetch_token(tok, &p, end, env);
5734 if (r < 0) return r;
5735 r = parse_subexp(&absent, tok, term, &p, end, env);
5737 onig_node_free(absent);
5742 is_range_cutter = 0;
5743 if (head_bar != 0) {
5745 if (NODE_TYPE(top) != NODE_ALT || IS_NULL(NODE_CDR(top))) {
5747 is_range_cutter = 1;
5748 //return ONIGERR_INVALID_ABSENT_GROUP_GENERATOR_PATTERN;
5751 absent = NODE_CAR(top);
5752 expr = NODE_CDR(top);
5753 NODE_CAR(top) = NULL_NODE;
5754 NODE_CDR(top) = NULL_NODE;
5755 onig_node_free(top);
5756 if (IS_NULL(NODE_CDR(expr))) {
5758 expr = NODE_CAR(top);
5759 NODE_CAR(top) = NULL_NODE;
5760 onig_node_free(top);
5765 r = make_absent_tree(np, absent, expr, is_range_cutter, env);
5772 return ONIGERR_UNDEFINED_GROUP_OPTION;
5777 if (! IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_BRACE_CALLOUT))
5778 return ONIGERR_UNDEFINED_GROUP_OPTION;
5780 /* (?{...}) (?{{...}}) */
5781 r = parse_code_callout(np, ')', &p, end, env);
5782 if (r != 0) return r;
5789 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_LPAREN_IF_ELSE)) {
5792 int condition_is_checker;
5794 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5796 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
5798 if (IS_CODE_DIGIT_ASCII(enc, c)
5799 || c == '-' || c == '+' || c == '<' || c == '\'') {
5804 enum REF_NUM num_type;
5807 is_enclosed = (c == '<' || c == '\'') ? 1 : 0;
5812 #ifdef USE_BACKREF_WITH_LEVEL
5813 name_end = NULL_UCHARP; /* no need. escape gcc warning. */
5814 r = fetch_name_with_level(
5815 (OnigCodePoint )(is_enclosed != 0 ? c : '('),
5817 env, &back_num, &level, &num_type);
5818 if (r == 1) exist_level = 1;
5820 r = fetch_name((OnigCodePoint )(is_enclosed != 0 ? c : '('),
5821 &p, end, &name_end, env, &back_num, &num_type, 1);
5824 if (is_enclosed == 0) {
5831 condition_is_checker = 1;
5832 if (num_type != IS_NOT_NUM) {
5833 if (num_type == IS_REL_NUM) {
5834 back_num = backref_rel_to_abs(back_num, env);
5837 return ONIGERR_INVALID_BACKREF;
5839 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_STRICT_CHECK_BACKREF)) {
5840 if (back_num > env->num_mem ||
5841 IS_NULL(SCANENV_MEMENV(env)[back_num].node))
5842 return ONIGERR_INVALID_BACKREF;
5845 condition = node_new_backref_checker(1, &back_num, 0,
5846 #ifdef USE_BACKREF_WITH_LEVEL
5855 num = onig_name_to_group_numbers(env->reg, prev, name_end, &backs);
5857 onig_scan_env_set_error_string(env,
5858 ONIGERR_UNDEFINED_NAME_REFERENCE, prev, name_end);
5859 return ONIGERR_UNDEFINED_NAME_REFERENCE;
5861 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_STRICT_CHECK_BACKREF)) {
5863 for (i = 0; i < num; i++) {
5864 if (backs[i] > env->num_mem ||
5865 IS_NULL(SCANENV_MEMENV(env)[backs[i]].node))
5866 return ONIGERR_INVALID_BACKREF;
5870 condition = node_new_backref_checker(num, backs, 1,
5871 #ifdef USE_BACKREF_WITH_LEVEL
5877 if (is_enclosed != 0) {
5878 if (PEND) goto err_if_else;
5880 if (c != ')') goto err_if_else;
5886 condition_is_checker = 0;
5887 r = fetch_token(tok, &p, end, env);
5888 if (r < 0) return r;
5889 r = parse_subexp(&condition, tok, term, &p, end, env);
5891 onig_node_free(condition);
5896 CHECK_NULL_RETURN_MEMERR(condition);
5900 onig_node_free(condition);
5901 return ONIGERR_END_PATTERN_IN_GROUP;
5904 if (PPEEK_IS(')')) { /* case: empty body: make backref checker */
5905 if (condition_is_checker == 0) {
5906 onig_node_free(condition);
5907 return ONIGERR_INVALID_IF_ELSE_SYNTAX;
5912 else { /* if-else */
5916 if (PPEEK_IS('|')) {
5924 r = fetch_token(tok, &p, end, env);
5926 onig_node_free(condition);
5929 r = parse_subexp(&target, tok, term, &p, end, env);
5931 onig_node_free(condition);
5932 onig_node_free(target);
5936 if (then_is_empty != 0) {
5940 if (NODE_TYPE(target) == NODE_ALT) {
5941 Then = NODE_CAR(target);
5942 if (NODE_CDR(NODE_CDR(target)) == NULL_NODE) {
5943 Else = NODE_CAR(NODE_CDR(target));
5944 cons_node_free_alone(NODE_CDR(target));
5947 Else = NODE_CDR(target);
5949 cons_node_free_alone(target);
5957 *np = node_new_enclosure_if_else(condition, Then, Else);
5959 onig_node_free(condition);
5960 onig_node_free(Then);
5961 onig_node_free(Else);
5962 return ONIGERR_MEMORY;
5968 return ONIGERR_UNDEFINED_GROUP_OPTION;
5973 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_ATMARK_CAPTURE_HISTORY)) {
5974 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_QMARK_LT_NAMED_GROUP)) {
5976 if (c == '<' || c == '\'') {
5978 goto named_group2; /* (?@<name>...) */
5983 *np = node_new_memory(0);
5984 CHECK_NULL_RETURN_MEMERR(*np);
5985 num = scan_env_add_mem_entry(env);
5989 else if (num >= (int )MEM_STATUS_BITS_NUM) {
5990 return ONIGERR_GROUP_NUMBER_OVER_FOR_CAPTURE_HISTORY;
5992 ENCLOSURE_(*np)->m.regnum = num;
5993 MEM_STATUS_ON_SIMPLE(env->capture_history, num);
5996 return ONIGERR_UNDEFINED_GROUP_OPTION;
6000 #ifdef USE_POSIXLINE_OPTION
6003 case '-': case 'i': case 'm': case 's': case 'x':
6004 case 'W': case 'D': case 'S': case 'P':
6014 case '-': neg = 1; break;
6015 case 'x': OPTION_NEGATE(option, ONIG_OPTION_EXTEND, neg); break;
6016 case 'i': OPTION_NEGATE(option, ONIG_OPTION_IGNORECASE, neg); break;
6018 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_OPTION_PERL)) {
6019 OPTION_NEGATE(option, ONIG_OPTION_MULTILINE, neg);
6022 return ONIGERR_UNDEFINED_GROUP_OPTION;
6026 if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_OPTION_PERL)) {
6027 OPTION_NEGATE(option, ONIG_OPTION_SINGLELINE, (neg == 0 ? 1 : 0));
6029 else if (IS_SYNTAX_OP2(env->syntax, ONIG_SYN_OP2_OPTION_RUBY)) {
6030 OPTION_NEGATE(option, ONIG_OPTION_MULTILINE, neg);
6033 return ONIGERR_UNDEFINED_GROUP_OPTION;
6035 #ifdef USE_POSIXLINE_OPTION
6037 OPTION_NEGATE(option, ONIG_OPTION_MULTILINE|ONIG_OPTION_SINGLELINE, neg);
6040 case 'W': OPTION_NEGATE(option, ONIG_OPTION_WORD_IS_ASCII, neg); break;
6041 case 'D': OPTION_NEGATE(option, ONIG_OPTION_DIGIT_IS_ASCII, neg); break;
6042 case 'S': OPTION_NEGATE(option, ONIG_OPTION_SPACE_IS_ASCII, neg); break;
6043 case 'P': OPTION_NEGATE(option, ONIG_OPTION_POSIX_IS_ASCII, neg); break;
6046 return ONIGERR_UNDEFINED_GROUP_OPTION;
6050 *np = node_new_option(option);
6051 CHECK_NULL_RETURN_MEMERR(*np);
6053 return 2; /* option only */
6055 else if (c == ':') {
6056 OnigOptionType prev = env->options;
6058 env->options = option;
6059 r = fetch_token(tok, &p, end, env);
6060 if (r < 0) return r;
6061 r = parse_subexp(&target, tok, term, &p, end, env);
6062 env->options = prev;
6064 onig_node_free(target);
6067 *np = node_new_option(option);
6068 CHECK_NULL_RETURN_MEMERR(*np);
6069 NODE_BODY(*np) = target;
6074 if (PEND) return ONIGERR_END_PATTERN_IN_GROUP;
6081 return ONIGERR_UNDEFINED_GROUP_OPTION;
6085 if (ONIG_IS_OPTION_ON(env->options, ONIG_OPTION_DONT_CAPTURE_GROUP))
6088 *np = node_new_memory(0);
6089 CHECK_NULL_RETURN_MEMERR(*np);
6090 num = scan_env_add_mem_entry(env);
6091 if (num < 0) return num;
6092 ENCLOSURE_(*np)->m.regnum = num;
6095 CHECK_NULL_RETURN_MEMERR(*np);
6096 r = fetch_token(tok, &p, end, env);
6097 if (r < 0) return r;
6098 r = parse_subexp(&target, tok, term, &p, end, env);
6100 onig_node_free(target);
6104 NODE_BODY(*np) = target;
6106 if (NODE_TYPE(*np) == NODE_ENCLOSURE) {
6107 if (ENCLOSURE_(*np)->type == ENCLOSURE_MEMORY) {
6108 /* Don't move this to previous of parse_subexp() */
6109 r = scan_env_set_mem_node(env, ENCLOSURE_(*np)->m.regnum, *np);
6110 if (r != 0) return r;
6119 static const char* PopularQStr[] = {
6120 "?", "*", "+", "??", "*?", "+?"
6123 static const char* ReduceQStr[] = {
6124 "", "", "*", "*?", "??", "+ and ??", "+? and ?"
6128 set_quantifier(Node* qnode, Node* target, int group, ScanEnv* env)
6133 if (qn->lower == 1 && qn->upper == 1)
6136 switch (NODE_TYPE(target)) {
6139 StrNode* sn = STR_(target);
6140 if (str_node_can_be_split(sn, env->enc)) {
6141 Node* n = str_node_split_last_char(sn, env->enc);
6142 if (IS_NOT_NULL(n)) {
6143 NODE_BODY(qnode) = n;
6151 { /* check redundant double repeat. */
6152 /* verbose warn (?:.?)? etc... but not warn (.?)? etc... */
6153 QuantNode* qnt = QUANT_(target);
6154 int nestq_num = quantifier_type_num(qn);
6155 int targetq_num = quantifier_type_num(qnt);
6157 #ifdef USE_WARNING_REDUNDANT_NESTED_REPEAT_OPERATOR
6158 if (! NODE_IS_BY_NUMBER(qnode) && ! NODE_IS_BY_NUMBER(target) &&
6159 IS_SYNTAX_BV(env->syntax, ONIG_SYN_WARN_REDUNDANT_NESTED_REPEAT)) {
6160 UChar buf[WARN_BUFSIZE];
6162 switch(ReduceTypeTable[targetq_num][nestq_num]) {
6167 if (onig_verb_warn != onig_null_warn) {
6168 onig_snprintf_with_pattern(buf, WARN_BUFSIZE, env->enc,
6169 env->pattern, env->pattern_end,
6170 (UChar* )"redundant nested repeat operator");
6171 (*onig_verb_warn)((char* )buf);
6177 if (onig_verb_warn != onig_null_warn) {
6178 onig_snprintf_with_pattern(buf, WARN_BUFSIZE, env->enc,
6179 env->pattern, env->pattern_end,
6180 (UChar* )"nested repeat operator %s and %s was replaced with '%s'",
6181 PopularQStr[targetq_num], PopularQStr[nestq_num],
6182 ReduceQStr[ReduceTypeTable[targetq_num][nestq_num]]);
6183 (*onig_verb_warn)((char* )buf);
6192 if (targetq_num >= 0 && nestq_num < 0) {
6193 if (targetq_num == 1 || targetq_num == 2) { /* * or + */
6194 /* (?:a*){n,m}, (?:a+){n,m} => (?:a*){n,n}, (?:a+){n,n} */
6195 if (! IS_REPEAT_INFINITE(qn->upper) && qn->upper > 1 && qn->greedy) {
6196 qn->upper = (qn->lower == 0 ? 1 : qn->lower);
6201 NODE_BODY(qnode) = target;
6202 onig_reduce_nested_quantifier(qnode, target);
6212 NODE_BODY(qnode) = target;
6218 #ifndef CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS
6220 clear_not_flag_cclass(CClassNode* cc, OnigEncoding enc)
6225 if (IS_NCCLASS_NOT(cc)) {
6226 bitset_invert(cc->bs);
6228 if (! ONIGENC_IS_SINGLEBYTE(enc)) {
6229 r = not_code_range_buf(enc, cc->mbuf, &tbuf);
6230 if (r != 0) return r;
6232 bbuf_free(cc->mbuf);
6236 NCCLASS_CLEAR_NOT(cc);
6241 #endif /* CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS */
6248 } IApplyCaseFoldArg;
6251 i_apply_case_fold(OnigCodePoint from, OnigCodePoint to[], int to_len, void* arg)
6253 IApplyCaseFoldArg* iarg;
6258 iarg = (IApplyCaseFoldArg* )arg;
6264 int is_in = onig_is_code_in_cc(env->enc, from, cc);
6265 #ifdef CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS
6266 if ((is_in != 0 && !IS_NCCLASS_NOT(cc)) ||
6267 (is_in == 0 && IS_NCCLASS_NOT(cc))) {
6268 if (ONIGENC_MBC_MINLEN(env->enc) > 1 || *to >= SINGLE_BYTE_SIZE) {
6269 add_code_range(&(cc->mbuf), env, *to, *to);
6272 BITSET_SET_BIT(bs, *to);
6277 if (ONIGENC_MBC_MINLEN(env->enc) > 1 || *to >= SINGLE_BYTE_SIZE) {
6278 if (IS_NCCLASS_NOT(cc)) clear_not_flag_cclass(cc, env->enc);
6279 add_code_range(&(cc->mbuf), env, *to, *to);
6282 if (IS_NCCLASS_NOT(cc)) {
6283 BITSET_CLEAR_BIT(bs, *to);
6286 BITSET_SET_BIT(bs, *to);
6289 #endif /* CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS */
6293 UChar buf[ONIGENC_CODE_TO_MBC_MAXLEN];
6294 Node *snode = NULL_NODE;
6296 if (onig_is_code_in_cc(env->enc, from, cc)
6297 #ifdef CASE_FOLD_IS_APPLIED_INSIDE_NEGATIVE_CCLASS
6298 && !IS_NCCLASS_NOT(cc)
6301 for (i = 0; i < to_len; i++) {
6302 len = ONIGENC_CODE_TO_MBC(env->enc, to[i], buf);
6304 snode = onig_node_new_str(buf, buf + len);
6305 CHECK_NULL_RETURN_MEMERR(snode);
6307 /* char-class expanded multi-char only
6308 compare with string folded at match time. */
6309 NODE_STRING_SET_AMBIG(snode);
6312 r = onig_node_str_cat(snode, buf, buf + len);
6314 onig_node_free(snode);
6320 *(iarg->ptail) = onig_node_new_alt(snode, NULL_NODE);
6321 CHECK_NULL_RETURN_MEMERR(*(iarg->ptail));
6322 iarg->ptail = &(NODE_CDR((*(iarg->ptail))));
6330 parse_exp(Node** np, OnigToken* tok, int term, UChar** src, UChar* end,
6333 int r, len, group = 0;
6338 if (tok->type == (enum TokenSyms )term)
6341 switch (tok->type) {
6345 *np = node_new_empty();
6349 case TK_SUBEXP_OPEN:
6350 r = parse_enclosure(np, tok, TK_SUBEXP_CLOSE, src, end, env);
6351 if (r < 0) return r;
6352 if (r == 1) group = 1;
6353 else if (r == 2) { /* option only */
6355 OnigOptionType prev = env->options;
6357 env->options = ENCLOSURE_(*np)->o.options;
6358 r = fetch_token(tok, src, end, env);
6359 if (r < 0) return r;
6360 r = parse_subexp(&target, tok, term, src, end, env);
6361 env->options = prev;
6363 onig_node_free(target);
6366 NODE_BODY(*np) = target;
6371 case TK_SUBEXP_CLOSE:
6372 if (! IS_SYNTAX_BV(env->syntax, ONIG_SYN_ALLOW_UNMATCHED_CLOSE_SUBEXP))
6373 return ONIGERR_UNMATCHED_CLOSE_PARENTHESIS;
6375 if (tok->escaped) goto tk_raw_byte;
6382 *np = node_new_str(tok->backp, *src);
6383 CHECK_NULL_RETURN_MEMERR(*np);
6386 r = fetch_token(tok, src, end, env);
6387 if (r < 0) return r;
6388 if (r != TK_STRING) break;
6390 r = onig_node_str_cat(*np, tok->backp, *src);
6391 if (r < 0) return r;
6403 *np = node_new_str_raw_char((UChar )tok->u.c);
6404 CHECK_NULL_RETURN_MEMERR(*np);
6407 if (len >= ONIGENC_MBC_MINLEN(env->enc)) {
6408 if (len == enclen(env->enc, STR_(*np)->s)) {//should not enclen_end()
6409 r = fetch_token(tok, src, end, env);
6410 NODE_STRING_CLEAR_RAW(*np);
6415 r = fetch_token(tok, src, end, env);
6416 if (r < 0) return r;
6417 if (r != TK_RAW_BYTE) {
6418 /* Don't use this, it is wrong for little endian encodings. */
6419 #ifdef USE_PAD_TO_SHORT_BYTE_CHAR
6421 if (len < ONIGENC_MBC_MINLEN(env->enc)) {
6422 rem = ONIGENC_MBC_MINLEN(env->enc) - len;
6423 (void )node_str_head_pad(STR_(*np), rem, (UChar )0);
6424 if (len + rem == enclen(env->enc, STR_(*np)->s)) {
6425 NODE_STRING_CLEAR_RAW(*np);
6430 return ONIGERR_TOO_SHORT_MULTI_BYTE_STRING;
6433 r = node_str_cat_char(*np, (UChar )tok->u.c);
6434 if (r < 0) return r;
6443 UChar buf[ONIGENC_CODE_TO_MBC_MAXLEN];
6444 int num = ONIGENC_CODE_TO_MBC(env->enc, tok->u.code, buf);
6445 if (num < 0) return num;
6446 #ifdef NUMBERED_CHAR_IS_NOT_CASE_AMBIG
6447 *np = node_new_str_raw(buf, buf + num);
6449 *np = node_new_str(buf, buf + num);
6451 CHECK_NULL_RETURN_MEMERR(*np);
6457 OnigCodePoint end_op[2];
6458 UChar *qstart, *qend, *nextp;
6460 end_op[0] = (OnigCodePoint )MC_ESC(env->syntax);
6461 end_op[1] = (OnigCodePoint )'E';
6463 qend = find_str_position(end_op, 2, qstart, end, &nextp, env->enc);
6464 if (IS_NULL(qend)) {
6467 *np = node_new_str(qstart, qend);
6468 CHECK_NULL_RETURN_MEMERR(*np);
6475 switch (tok->u.prop.ctype) {
6476 case ONIGENC_CTYPE_WORD:
6477 *np = node_new_ctype(tok->u.prop.ctype, tok->u.prop.not, env->options);
6478 CHECK_NULL_RETURN_MEMERR(*np);
6481 case ONIGENC_CTYPE_SPACE:
6482 case ONIGENC_CTYPE_DIGIT:
6483 case ONIGENC_CTYPE_XDIGIT:
6487 *np = node_new_cclass();
6488 CHECK_NULL_RETURN_MEMERR(*np);
6490 add_ctype_to_cc(cc, tok->u.prop.ctype, 0, env);
6491 if (tok->u.prop.not != 0) NCCLASS_SET_NOT(cc);
6496 return ONIGERR_PARSER_BUG;
6502 case TK_CHAR_PROPERTY:
6503 r = parse_char_property(np, tok, src, end, env);
6504 if (r != 0) return r;
6511 r = parse_char_class(np, tok, src, end, env);
6512 if (r != 0) return r;
6515 if (IS_IGNORECASE(env->options)) {
6516 IApplyCaseFoldArg iarg;
6520 iarg.alt_root = NULL_NODE;
6521 iarg.ptail = &(iarg.alt_root);
6523 r = ONIGENC_APPLY_ALL_CASE_FOLD(env->enc, env->case_fold_flag,
6524 i_apply_case_fold, &iarg);
6526 onig_node_free(iarg.alt_root);
6529 if (IS_NOT_NULL(iarg.alt_root)) {
6530 Node* work = onig_node_new_alt(*np, iarg.alt_root);
6531 if (IS_NULL(work)) {
6532 onig_node_free(iarg.alt_root);
6533 return ONIGERR_MEMORY;
6542 *np = node_new_anychar();
6543 CHECK_NULL_RETURN_MEMERR(*np);
6546 case TK_ANYCHAR_ANYTIME:
6547 *np = node_new_anychar();
6548 CHECK_NULL_RETURN_MEMERR(*np);
6549 qn = node_new_quantifier(0, REPEAT_INFINITE, 0);
6550 CHECK_NULL_RETURN_MEMERR(qn);
6551 NODE_BODY(qn) = *np;
6556 len = tok->u.backref.num;
6557 *np = node_new_backref(len,
6558 (len > 1 ? tok->u.backref.refs : &(tok->u.backref.ref1)),
6559 tok->u.backref.by_name,
6560 #ifdef USE_BACKREF_WITH_LEVEL
6561 tok->u.backref.exist_level,
6562 tok->u.backref.level,
6565 CHECK_NULL_RETURN_MEMERR(*np);
6571 int gnum = tok->u.call.gnum;
6573 *np = node_new_call(tok->u.call.name, tok->u.call.name_end,
6574 gnum, tok->u.call.by_number);
6575 CHECK_NULL_RETURN_MEMERR(*np);
6577 if (tok->u.call.by_number != 0 && gnum == 0) {
6578 env->has_call_zero = 1;
6587 IS_WORD_ASCII(env->options) && IS_WORD_ANCHOR_TYPE(tok->u.anchor) ? 1 : 0;
6588 *np = onig_node_new_anchor(tok->u.anchor, ascii_mode);
6594 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_CONTEXT_INDEP_REPEAT_OPS)) {
6595 if (IS_SYNTAX_BV(env->syntax, ONIG_SYN_CONTEXT_INVALID_REPEAT_OPS))
6596 return ONIGERR_TARGET_OF_REPEAT_OPERATOR_NOT_SPECIFIED;
6598 *np = node_new_empty();
6606 r = node_new_keep(np, env);
6607 if (r < 0) return r;
6610 case TK_GENERAL_NEWLINE:
6611 r = node_new_general_newline(np, env);
6612 if (r < 0) return r;
6616 r = node_new_no_newline(np, env);
6617 if (r < 0) return r;
6620 case TK_TRUE_ANYCHAR:
6621 r = node_new_true_anychar(np, env);
6622 if (r < 0) return r;
6625 case TK_EXTENDED_GRAPHEME_CLUSTER:
6626 r = make_extended_grapheme_cluster(np, env);
6627 if (r < 0) return r;
6631 return ONIGERR_PARSER_BUG;
6639 r = fetch_token(tok, src, end, env);
6640 if (r < 0) return r;
6643 if (r == TK_OP_REPEAT || r == TK_INTERVAL) {
6644 if (is_invalid_quantifier_target(*targetp))
6645 return ONIGERR_TARGET_OF_REPEAT_OPERATOR_INVALID;
6647 qn = node_new_quantifier(tok->u.repeat.lower, tok->u.repeat.upper,
6648 (r == TK_INTERVAL ? 1 : 0));
6649 CHECK_NULL_RETURN_MEMERR(qn);
6650 QUANT_(qn)->greedy = tok->u.repeat.greedy;
6651 r = set_quantifier(qn, *targetp, group, env);
6657 if (tok->u.repeat.possessive != 0) {
6659 en = node_new_enclosure(ENCLOSURE_STOP_BACKTRACK);
6662 return ONIGERR_MEMORY;
6674 else if (r == 2) { /* split case: /abc+/ */
6677 *targetp = node_new_list(*targetp, NULL);
6678 if (IS_NULL(*targetp)) {
6680 return ONIGERR_MEMORY;
6682 tmp = NODE_CDR(*targetp) = node_new_list(qn, NULL);
6685 return ONIGERR_MEMORY;
6687 targetp = &(NODE_CAR(tmp));
6697 parse_branch(Node** top, OnigToken* tok, int term, UChar** src, UChar* end,
6701 Node *node, **headp;
6704 r = parse_exp(&node, tok, term, src, end, env);
6706 onig_node_free(node);
6710 if (r == TK_EOT || r == term || r == TK_ALT) {
6714 *top = node_new_list(node, NULL);
6715 headp = &(NODE_CDR(*top));
6716 while (r != TK_EOT && r != term && r != TK_ALT) {
6717 r = parse_exp(&node, tok, term, src, end, env);
6719 onig_node_free(node);
6723 if (NODE_TYPE(node) == NODE_LIST) {
6725 while (IS_NOT_NULL(NODE_CDR(node))) node = NODE_CDR(node);
6726 headp = &(NODE_CDR(node));
6729 *headp = node_new_list(node, NULL);
6730 headp = &(NODE_CDR(*headp));
6738 /* term_tok: TK_EOT or TK_SUBEXP_CLOSE */
6740 parse_subexp(Node** top, OnigToken* tok, int term, UChar** src, UChar* end,
6744 Node *node, **headp;
6748 if (env->parse_depth > ParseDepthLimit)
6749 return ONIGERR_PARSE_DEPTH_LIMIT_OVER;
6750 r = parse_branch(&node, tok, term, src, end, env);
6752 onig_node_free(node);
6759 else if (r == TK_ALT) {
6760 *top = onig_node_new_alt(node, NULL);
6761 headp = &(NODE_CDR(*top));
6762 while (r == TK_ALT) {
6763 r = fetch_token(tok, src, end, env);
6764 if (r < 0) return r;
6765 r = parse_branch(&node, tok, term, src, end, env);
6767 onig_node_free(node);
6770 *headp = onig_node_new_alt(node, NULL);
6771 headp = &(NODE_CDR(*headp));
6774 if (tok->type != (enum TokenSyms )term)
6778 onig_node_free(node);
6780 if (term == TK_SUBEXP_CLOSE)
6781 return ONIGERR_END_PATTERN_WITH_UNMATCHED_PARENTHESIS;
6783 return ONIGERR_PARSER_BUG;
6791 parse_regexp(Node** top, UChar** src, UChar* end, ScanEnv* env)
6796 r = fetch_token(&tok, src, end, env);
6797 if (r < 0) return r;
6798 r = parse_subexp(top, &tok, TK_EOT, src, end, env);
6799 if (r < 0) return r;
6806 make_call_zero_body(Node* node, ScanEnv* env, Node** rnode)
6810 Node* x = node_new_memory(0 /* 0: is not named */);
6811 CHECK_NULL_RETURN_MEMERR(x);
6813 NODE_BODY(x) = node;
6814 ENCLOSURE_(x)->m.regnum = 0;
6815 r = scan_env_set_mem_node(env, 0, x);
6827 onig_parse_tree(Node** root, const UChar* pattern, const UChar* end,
6828 regex_t* reg, ScanEnv* env)
6835 scan_env_clear(env);
6836 env->options = reg->options;
6837 env->case_fold_flag = reg->case_fold_flag;
6838 env->enc = reg->enc;
6839 env->syntax = reg->syntax;
6840 env->pattern = (UChar* )pattern;
6841 env->pattern_end = (UChar* )end;
6846 if (! ONIGENC_IS_VALID_MBC_STRING(env->enc, pattern, end))
6847 return ONIGERR_INVALID_WIDE_CHAR_VALUE;
6849 p = (UChar* )pattern;
6850 r = parse_regexp(root, &p, (UChar* )end, env);
6853 if (r != 0) return r;
6855 if (env->has_call_zero != 0) {
6857 r = make_call_zero_body(*root, env, &zero_node);
6858 if (r != 0) return r;
6864 reg->num_mem = env->num_mem;
6869 onig_scan_env_set_error_string(ScanEnv* env, int ecode ARG_UNUSED,
6870 UChar* arg, UChar* arg_end)
6873 env->error_end = arg_end;