@@ -570,80 +570,85 @@ static const scan_data_t zero_scan_data =
570
570
REPORT_LOCATION_ARGS(offset)); \
571
571
} STMT_END
572
572
573
+ /* These have asserts in them because of [perl #122671] Many warnings in
574
+ * regcomp.c can occur twice. If they get output in pass1 and later in that
575
+ * pass, the pattern has to be converted to UTF-8 and the pass restarted, they
576
+ * would get output again. So they should be output in pass2, and these
577
+ * asserts make sure new warnings follow that paradigm. */
573
578
574
579
/* m is not necessarily a "literal string", in this macro */
575
580
#define reg_warn_non_literal_string(loc, m) STMT_START { \
576
581
const IV offset = loc - RExC_precomp; \
577
- Perl_warner(aTHX_ packWARN(WARN_REGEXP), "%s" REPORT_LOCATION, \
582
+ __ASSERT_(PASS2) Perl_warner(aTHX_ packWARN(WARN_REGEXP), "%s" REPORT_LOCATION, \
578
583
m, REPORT_LOCATION_ARGS(offset)); \
579
584
} STMT_END
580
585
581
586
#define ckWARNreg(loc,m) STMT_START { \
582
587
const IV offset = loc - RExC_precomp; \
583
- Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
588
+ __ASSERT_(PASS2) Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
584
589
REPORT_LOCATION_ARGS(offset)); \
585
590
} STMT_END
586
591
587
592
#define vWARN_dep(loc, m) STMT_START { \
588
593
const IV offset = loc - RExC_precomp; \
589
- Perl_warner(aTHX_ packWARN(WARN_DEPRECATED), m REPORT_LOCATION, \
594
+ __ASSERT_(PASS2) Perl_warner(aTHX_ packWARN(WARN_DEPRECATED), m REPORT_LOCATION, \
590
595
REPORT_LOCATION_ARGS(offset)); \
591
596
} STMT_END
592
597
593
598
#define ckWARNdep(loc,m) STMT_START { \
594
599
const IV offset = loc - RExC_precomp; \
595
- Perl_ck_warner_d(aTHX_ packWARN(WARN_DEPRECATED), \
600
+ __ASSERT_(PASS2) Perl_ck_warner_d(aTHX_ packWARN(WARN_DEPRECATED), \
596
601
m REPORT_LOCATION, \
597
602
REPORT_LOCATION_ARGS(offset)); \
598
603
} STMT_END
599
604
600
605
#define ckWARNregdep(loc,m) STMT_START { \
601
606
const IV offset = loc - RExC_precomp; \
602
- Perl_ck_warner_d(aTHX_ packWARN2(WARN_DEPRECATED, WARN_REGEXP), \
607
+ __ASSERT_(PASS2) Perl_ck_warner_d(aTHX_ packWARN2(WARN_DEPRECATED, WARN_REGEXP), \
603
608
m REPORT_LOCATION, \
604
609
REPORT_LOCATION_ARGS(offset)); \
605
610
} STMT_END
606
611
607
612
#define ckWARN2reg_d(loc,m, a1) STMT_START { \
608
613
const IV offset = loc - RExC_precomp; \
609
- Perl_ck_warner_d(aTHX_ packWARN(WARN_REGEXP), \
614
+ __ASSERT_(PASS2) Perl_ck_warner_d(aTHX_ packWARN(WARN_REGEXP), \
610
615
m REPORT_LOCATION, \
611
616
a1, REPORT_LOCATION_ARGS(offset)); \
612
617
} STMT_END
613
618
614
619
#define ckWARN2reg(loc, m, a1) STMT_START { \
615
620
const IV offset = loc - RExC_precomp; \
616
- Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
621
+ __ASSERT_(PASS2) Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
617
622
a1, REPORT_LOCATION_ARGS(offset)); \
618
623
} STMT_END
619
624
620
625
#define vWARN3(loc, m, a1, a2) STMT_START { \
621
626
const IV offset = loc - RExC_precomp; \
622
- Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
627
+ __ASSERT_(PASS2) Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
623
628
a1, a2, REPORT_LOCATION_ARGS(offset)); \
624
629
} STMT_END
625
630
626
631
#define ckWARN3reg(loc, m, a1, a2) STMT_START { \
627
632
const IV offset = loc - RExC_precomp; \
628
- Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
633
+ __ASSERT_(PASS2) Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
629
634
a1, a2, REPORT_LOCATION_ARGS(offset)); \
630
635
} STMT_END
631
636
632
637
#define vWARN4(loc, m, a1, a2, a3) STMT_START { \
633
638
const IV offset = loc - RExC_precomp; \
634
- Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
639
+ __ASSERT_(PASS2) Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
635
640
a1, a2, a3, REPORT_LOCATION_ARGS(offset)); \
636
641
} STMT_END
637
642
638
643
#define ckWARN4reg(loc, m, a1, a2, a3) STMT_START { \
639
644
const IV offset = loc - RExC_precomp; \
640
- Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
645
+ __ASSERT_(PASS2) Perl_ck_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
641
646
a1, a2, a3, REPORT_LOCATION_ARGS(offset)); \
642
647
} STMT_END
643
648
644
649
#define vWARN5(loc, m, a1, a2, a3, a4) STMT_START { \
645
650
const IV offset = loc - RExC_precomp; \
646
- Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
651
+ __ASSERT_(PASS2) Perl_warner(aTHX_ packWARN(WARN_REGEXP), m REPORT_LOCATION, \
647
652
a1, a2, a3, a4, REPORT_LOCATION_ARGS(offset)); \
648
653
} STMT_END
649
654
@@ -9380,7 +9385,7 @@ S_parse_lparen_question_flags(pTHX_ RExC_state_t *pRExC_state)
9380
9385
/*NOTREACHED*/
9381
9386
case ONCE_PAT_MOD: /* 'o' */
9382
9387
case GLOBAL_PAT_MOD: /* 'g' */
9383
- if (SIZE_ONLY && ckWARN(WARN_REGEXP)) {
9388
+ if (PASS2 && ckWARN(WARN_REGEXP)) {
9384
9389
const I32 wflagbit = *RExC_parse == 'o'
9385
9390
? WASTED_O
9386
9391
: WASTED_G;
@@ -9400,7 +9405,7 @@ S_parse_lparen_question_flags(pTHX_ RExC_state_t *pRExC_state)
9400
9405
break;
9401
9406
9402
9407
case CONTINUE_PAT_MOD: /* 'c' */
9403
- if (SIZE_ONLY && ckWARN(WARN_REGEXP)) {
9408
+ if (PASS2 && ckWARN(WARN_REGEXP)) {
9404
9409
if (! (wastedflags & WASTED_C) ) {
9405
9410
wastedflags |= WASTED_GC;
9406
9411
/* diag_listed_as: Useless (?-%s) - don't use /%s modifier in regex; marked by <-- HERE in m/%s/ */
@@ -9415,7 +9420,7 @@ S_parse_lparen_question_flags(pTHX_ RExC_state_t *pRExC_state)
9415
9420
break;
9416
9421
case KEEPCOPY_PAT_MOD: /* 'p' */
9417
9422
if (flagsp == &negflags) {
9418
- if (SIZE_ONLY )
9423
+ if (PASS2 )
9419
9424
ckWARNreg(RExC_parse + 1,"Useless use of (?-p)");
9420
9425
} else {
9421
9426
*flagsp |= RXf_PMf_KEEPCOPY;
@@ -10547,7 +10552,6 @@ S_regpiece(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
10547
10552
if (max < min) { /* If can't match, warn and optimize to fail
10548
10553
unconditionally */
10549
10554
if (SIZE_ONLY) {
10550
- ckWARNreg(RExC_parse, "Quantifier {n,m} with n > m can't match");
10551
10555
10552
10556
/* We can't back off the size because we have to reserve
10553
10557
* enough space for all the things we are about to throw
@@ -10556,6 +10560,7 @@ S_regpiece(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
10556
10560
RExC_size = PREVOPER(RExC_size) - regarglen[(U8)OPFAIL];
10557
10561
}
10558
10562
else {
10563
+ ckWARNreg(RExC_parse, "Quantifier {n,m} with n > m can't match");
10559
10564
RExC_emit = orig_emit;
10560
10565
}
10561
10566
ret = reg_node(pRExC_state, OPFAIL);
@@ -10565,7 +10570,7 @@ S_regpiece(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
10565
10570
&& RExC_parse < RExC_end
10566
10571
&& (*RExC_parse == '?' || *RExC_parse == '+'))
10567
10572
{
10568
- if (SIZE_ONLY ) {
10573
+ if (PASS2 ) {
10569
10574
ckWARN2reg(RExC_parse + 1,
10570
10575
"Useless use of greediness modifier '%c'",
10571
10576
*RExC_parse);
@@ -10837,7 +10842,7 @@ S_grok_bslash_N(pTHX_ RExC_state_t *pRExC_state, regnode** node_p,
10837
10842
*node_p = reg_node(pRExC_state,NOTHING);
10838
10843
}
10839
10844
else if (in_char_class) {
10840
- if (SIZE_ONLY && in_char_class) {
10845
+ if (PASS2 && in_char_class) {
10841
10846
if (strict) {
10842
10847
RExC_parse++; /* Position after the "}" */
10843
10848
vFAIL("Zero length \\N{}");
@@ -11430,7 +11435,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
11430
11435
ret = reg_node(pRExC_state, CANY);
11431
11436
RExC_seen |= REG_CANY_SEEN;
11432
11437
*flagp |= HASWIDTH|SIMPLE;
11433
- if (SIZE_ONLY ) {
11438
+ if (PASS2 ) {
11434
11439
ckWARNdep(RExC_parse+1, "\\C is deprecated");
11435
11440
}
11436
11441
goto finish_meta_pat;
@@ -11930,7 +11935,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
11930
11935
bool valid = grok_bslash_o(&p,
11931
11936
&result,
11932
11937
&error_msg,
11933
- TRUE , /* out warnings */
11938
+ PASS2 , /* out warnings */
11934
11939
FALSE, /* not strict */
11935
11940
TRUE, /* Output warnings
11936
11941
for non-
@@ -11959,7 +11964,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
11959
11964
bool valid = grok_bslash_x(&p,
11960
11965
&result,
11961
11966
&error_msg,
11962
- TRUE , /* out warnings */
11967
+ PASS2 , /* out warnings */
11963
11968
FALSE, /* not strict */
11964
11969
TRUE, /* Output warnings
11965
11970
for non-
@@ -11982,7 +11987,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
11982
11987
}
11983
11988
case 'c':
11984
11989
p++;
11985
- ender = grok_bslash_c(*p++, SIZE_ONLY );
11990
+ ender = grok_bslash_c(*p++, PASS2 );
11986
11991
break;
11987
11992
case '8': case '9': /* must be a backreference */
11988
11993
--p;
@@ -12021,7 +12026,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
12021
12026
REQUIRE_UTF8;
12022
12027
}
12023
12028
p += numlen;
12024
- if (SIZE_ONLY /* like \08, \178 */
12029
+ if (PASS2 /* like \08, \178 */
12025
12030
&& numlen < 3
12026
12031
&& p < RExC_end
12027
12032
&& isDIGIT(*p) && ckWARN(WARN_REGEXP))
@@ -12038,7 +12043,7 @@ S_regatom(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth)
12038
12043
if (! RExC_override_recoding) {
12039
12044
SV* enc = PL_encoding;
12040
12045
ender = reg_recode((const char)(U8)ender, &enc);
12041
- if (!enc && SIZE_ONLY )
12046
+ if (!enc && PASS2 )
12042
12047
ckWARNreg(p, "Invalid escape in the specified encoding");
12043
12048
REQUIRE_UTF8;
12044
12049
}
@@ -12772,16 +12777,17 @@ S_handle_regex_sets(pTHX_ RExC_state_t *pRExC_state, SV** return_invlist,
12772
12777
* upon an unescaped ']' that isn't one ending a regclass. To do both
12773
12778
* these things, we need to realize that something preceded by a backslash
12774
12779
* is escaped, so we have to keep track of backslashes */
12775
- if (SIZE_ONLY) {
12776
- UV depth = 0; /* how many nested (?[...]) constructs */
12777
-
12780
+ if (PASS2) {
12778
12781
Perl_ck_warner_d(aTHX_
12779
12782
packWARN(WARN_EXPERIMENTAL__REGEX_SETS),
12780
12783
"The regex_sets feature is experimental" REPORT_LOCATION,
12781
12784
UTF8fARG(UTF, (RExC_parse - RExC_precomp), RExC_precomp),
12782
12785
UTF8fARG(UTF,
12783
12786
RExC_end - RExC_start - (RExC_parse - RExC_precomp),
12784
12787
RExC_precomp + (RExC_parse - RExC_precomp)));
12788
+ }
12789
+ else {
12790
+ UV depth = 0; /* how many nested (?[...]) constructs */
12785
12791
12786
12792
while (RExC_parse < RExC_end) {
12787
12793
SV* current = NULL;
@@ -13282,7 +13288,9 @@ S_add_above_Latin1_folds(pTHX_ RExC_state_t *pRExC_state, const U8 cp, SV** invl
13282
13288
default:
13283
13289
/* Use deprecated warning to increase the chances of this being
13284
13290
* output */
13285
- ckWARN2reg_d(RExC_parse, "Perl folding rules are not up-to-date for 0x%02X; please use the perlbug utility to report;", cp);
13291
+ if (PASS2) {
13292
+ ckWARN2reg_d(RExC_parse, "Perl folding rules are not up-to-date for 0x%02X; please use the perlbug utility to report;", cp);
13293
+ }
13286
13294
break;
13287
13295
}
13288
13296
}
@@ -13750,8 +13758,8 @@ S_regclass(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth,
13750
13758
bool valid = grok_bslash_o(&RExC_parse,
13751
13759
&value,
13752
13760
&error_msg,
13753
- SIZE_ONLY , /* warnings in pass
13754
- 1 only */
13761
+ PASS2 , /* warnings only in
13762
+ pass 2 */
13755
13763
strict,
13756
13764
silence_non_portable,
13757
13765
UTF);
@@ -13770,7 +13778,7 @@ S_regclass(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth,
13770
13778
bool valid = grok_bslash_x(&RExC_parse,
13771
13779
&value,
13772
13780
&error_msg,
13773
- TRUE , /* Output warnings */
13781
+ PASS2 , /* Output warnings */
13774
13782
strict,
13775
13783
silence_non_portable,
13776
13784
UTF);
@@ -13782,7 +13790,7 @@ S_regclass(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth,
13782
13790
goto recode_encoding;
13783
13791
break;
13784
13792
case 'c':
13785
- value = grok_bslash_c(*RExC_parse++, SIZE_ONLY );
13793
+ value = grok_bslash_c(*RExC_parse++, PASS2 );
13786
13794
break;
13787
13795
case '0': case '1': case '2': case '3': case '4':
13788
13796
case '5': case '6': case '7':
@@ -13822,7 +13830,7 @@ S_regclass(pTHX_ RExC_state_t *pRExC_state, I32 *flagp, U32 depth,
13822
13830
if (strict) {
13823
13831
vFAIL("Invalid escape in the specified encoding");
13824
13832
}
13825
- else if (SIZE_ONLY ) {
13833
+ else if (PASS2 ) {
13826
13834
ckWARNreg(RExC_parse,
13827
13835
"Invalid escape in the specified encoding");
13828
13836
}
0 commit comments