@@ -267,6 +267,13 @@ class preg_replacement_parser {
267267 }
268268};
269269
270+ template <size_t N>
271+ void log_regex_error (const char (&msg)[N], int32_t regex_error) noexcept {
272+ std::array<char , ERROR_BUFFER_LENGTH> buffer{};
273+ pcre2_get_error_message_8 (regex_error, reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
274+ kphp::log::warning (" {}: {}" , msg, buffer.data ());
275+ }
276+
270277bool compile_regex (RegexInfo& regex_info) noexcept {
271278 const vk::final_action finalizer{[®ex_info]() noexcept {
272279 if (regex_info.regex_code != nullptr ) [[likely]] {
@@ -654,9 +661,7 @@ bool replace_regex(RegexInfo& regex_info, uint64_t limit) noexcept {
654661 reinterpret_cast <PCRE2_UCHAR8*>(runtime_ctx.static_SB .buffer ()), std::addressof (output_length));
655662
656663 if (regex_info.replace_count < 0 ) [[unlikely]] {
657- std::array<char , ERROR_BUFFER_LENGTH> buffer{};
658- pcre2_get_error_message_8 (regex_info.replace_count , reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
659- kphp::log::warning (" pcre2_substitute error {}" , buffer.data ());
664+ log_regex_error (" pcre2_substitute error {}" , regex_info.replace_count );
660665 return false ;
661666 }
662667 } else { // replace only 'limit' times
@@ -669,9 +674,7 @@ bool replace_regex(RegexInfo& regex_info, uint64_t limit) noexcept {
669674 for (; regex_info.replace_count < limit; ++regex_info.replace_count ) {
670675 auto expected_opt_match_view{pcre2_matcher.next ()};
671676 if (!expected_opt_match_view.has_value ()) [[unlikely]] {
672- std::array<char , ERROR_BUFFER_LENGTH> buffer{};
673- pcre2_get_error_message_8 (expected_opt_match_view.error (), reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
674- kphp::log::warning (" can't replace by pcre2 regex due to match error: {}" , buffer.data ());
677+ log_regex_error (" can't replace by pcre2 regex due to match error: {}" , expected_opt_match_view.error ());
675678 return false ;
676679 }
677680 auto opt_match_view{*expected_opt_match_view};
@@ -726,9 +729,7 @@ std::optional<array<mixed>> split_regex(RegexInfo& regex_info, int64_t limit, bo
726729 for (size_t out_parts_count{1 }; limit == kphp::regex::PREG_NOLIMIT || out_parts_count < limit;) {
727730 auto expected_opt_match_view{pcre2_matcher.next ()};
728731 if (!expected_opt_match_view.has_value ()) [[unlikely]] {
729- std::array<char , ERROR_BUFFER_LENGTH> buffer{};
730- pcre2_get_error_message_8 (expected_opt_match_view.error (), reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
731- kphp::log::warning (" can't split by pcre2 regex due to match error: {}" , buffer.data ());
732+ log_regex_error (" can't split by pcre2 regex due to match error: {}" , expected_opt_match_view.error ());
732733 return std::nullopt ;
733734 }
734735 auto opt_match_view{*expected_opt_match_view};
@@ -761,21 +762,22 @@ std::optional<array<mixed>> split_regex(RegexInfo& regex_info, int64_t limit, bo
761762 if (delim_capture) {
762763 for (size_t i{1 }; i < match_view.size (); i++) {
763764 auto opt_submatch{match_view.get_group (i)};
764- auto string_view {opt_submatch.value_or (std::string_view{})};
765- const auto size{string_view .size ()};
765+ auto submatch_string_view {opt_submatch.value_or (std::string_view{})};
766+ const auto size{submatch_string_view .size ()};
766767 if (!no_empty || size != 0 ) {
767768 string val;
768769 if (opt_submatch.has_value ()) [[likely]] {
769- val = string{string_view .data (), static_cast <string::size_type>(size)};
770+ val = string{submatch_string_view .data (), static_cast <string::size_type>(size)};
770771 }
771772
772773 mixed output_val;
773774 if (offset_capture) {
774- output_val = array<mixed>::create (std::move (val), opt_submatch
775- .transform ([®ex_info](auto string_view) noexcept {
776- return static_cast <int64_t >(std::distance (regex_info.subject .data (), string_view.data ()));
777- })
778- .value_or (-1 ));
775+ output_val =
776+ array<mixed>::create (std::move (val), opt_submatch
777+ .transform ([®ex_info](auto submatch_string_view) noexcept {
778+ return static_cast <int64_t >(std::distance (regex_info.subject .data (), submatch_string_view.data ()));
779+ })
780+ .value_or (-1 ));
779781 } else {
780782 output_val = std::move (val);
781783 }
@@ -833,9 +835,7 @@ Optional<int64_t> f$preg_match(const string& pattern, const string& subject, Opt
833835 // The return from pcre2_match() is one more than the highest numbered capturing pair that has been set
834836 // (for example, 1 if there are no captures), zero if the vector of offsets is too small, or a negative error code for no match and other errors.
835837 if (ret_code < 0 && ret_code != PCRE2_ERROR_NOMATCH) [[unlikely]] {
836- std::array<char , ERROR_BUFFER_LENGTH> buffer{};
837- pcre2_get_error_message_8 (ret_code, reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
838- kphp::log::warning (" can't match by pcre2 regex due to error: {}" , buffer.data ());
838+ log_regex_error (" can't match by pcre2 regex due to error: {}" , ret_code);
839839 return false ;
840840 }
841841 regex_info.match_count = ret_code != PCRE2_ERROR_NOMATCH ? ret_code : 0 ;
@@ -903,9 +903,7 @@ Optional<int64_t> f$preg_match_all(const string& pattern, const string& subject,
903903 expected_opt_match_view = pcre2_matcher.next ();
904904 }
905905 if (!expected_opt_match_view.has_value ()) [[unlikely]] {
906- std::array<char , ERROR_BUFFER_LENGTH> buffer{};
907- pcre2_get_error_message_8 (expected_opt_match_view.error (), reinterpret_cast <PCRE2_UCHAR8*>(buffer.data ()), buffer.size ());
908- kphp::log::warning (" can't find all matches due to match error: {}" , buffer.data ());
906+ log_regex_error (" can't find all matches due to match error: {}" , expected_opt_match_view.error ());
909907 return false ;
910908 }
911909
0 commit comments