} STMT_END
void
+
+
+/* This function assumes that pat has the same utf8-ness as sv.
+ * It's the caller's responsibility to ensure that this is so.
+ */
+
Perl_sv_vcatpvfn_flags(pTHX_ SV *const sv, const char *const pat, const STRLEN patlen,
va_list *const args, SV **const svargs, const I32 svmax, bool *const maybe_tainted,
const U32 flags)
Perl_warner(aTHX_ packWARN(WARN_PRINTF), "%" SVf, SVfARG(msg)); /* yes, this is reentrant */
}
- /* output mangled stuff ... */
- if (c == '\0')
- --q;
- eptr = p;
- elen = q - p;
-
- /* ... right here, because formatting flags should not apply */
- SvGROW(sv, SvCUR(sv) + elen + 1);
- p = SvEND(sv);
- Copy(eptr, p, elen, char);
- p += elen;
- *p = '\0';
- SvCUR_set(sv, p - SvPVX_const(sv));
+ /* mangled format: output the '%', then continue from the
+ * character following that */
+ sv_catpvn_nomg(sv, p, 1);
+ q = p + 1;
svix = osvix;
continue; /* not "break" */
}
>%*2$1d< >[12, 3]< >%*2$1d INVALID REDUNDANT<
>%0v2.2d< >''< ><
>%vc,%d< >[63, 64, 65]< >%vc,63 INVALID REDUNDANT<
->%v%,%d< >[63, 64, 65]< >%v%,63 INVALID REDUNDANT<
+>%v%,%d< >[63, 64, 65]< >%v%,63 INVALID INVALID REDUNDANT<
>%vd,%d< >["\x1", 2, 3]< >1,2 REDUNDANT<
>%vf,%d< >[1, 2, 3]< >%vf,1 INVALID REDUNDANT<
>%vF,%d< >[1, 2, 3]< >%vF,1 INVALID REDUNDANT<
}
}
+{
+ # handle utf8 correctly when skipping invalid format
+ my $w_red = 0;
+ my $w_inv = 0;
+ my $w_other = 0;
+ local $SIG{__WARN__} = sub {
+ if ($_[0] =~ /^Invalid conversion/) {
+ $w_inv++;
+ }
+ elsif ($_[0] =~ /^Redundant argument/) {
+ $w_red++;
+ }
+ else {
+ $w_other++;
+ }
+ };
+
+ use warnings;
+ my $s = sprintf "%s%\xc4\x80%s", "\x{102}", "\xc4\x83";
+ is($s, "\x{102}%\xc4\x80\xc4\x83", "utf8 for invalid format");
+ is($w_inv, 1, "utf8 for invalid format: invalid warnings");
+ is($w_red, 0, "utf8 for invalid format: redundant warnings");
+ is($w_other, 0, "utf8 for invalid format: other warnings");
+}
done_testing();