| Ticket UUID: | b73f1296966202b2beeb14fec5534dec6a408012 | ||
| Title: | regexp -all misses an empty match at the end of the string | ||
| Type: | Bug | Created on: | 2026-10-11 08:18:34 |
| Submitter: | serhiy.storchaka | Assigned to: | |
| Subsystem: | 43. Regexp | Severity: | Minor |
| Priority: | 5 Medium | Last modified: | 2026-10-11 08:21:44 |
| Status: | Open | Closed by: | |
| Resolution: | None | Closed on: | |
| Version: | 8.6.18, 9.0.5, 9.1.0 | ||
| Description: | ||||
|
regexp -all does not try to match at the end of the string, so an RE that can match the empty string there misses its last match. regsub -all does try there, so the two disagree:
regexp -all {a*} ab ;# 2, but regsub -all {a*} ab <&> gives <a><><> (3 matches)
regexp -all -inline -indices -line {$} "a\n" ;# {1 0}, but the empty line at the end also matches: {1 0} {2 1}
PostgreSQL, Python, Perl, Java, Ruby and JavaScript all report the match at the end (3 matches for the first example). Tests regexp-23.5, 23.7 and 23.9, added for [2826551fff], expect it too, but are marked knownBug.
The cause is the end of the -all loop in Tcl_RegexpObjCmd(): it stops when the next offset reaches the end of the string (offset >= stringLength), while Tcl_RegsubObjCmd() loops while offset <= wlen. Fixing it changes the number of matches that regexp -all reports for such REs, and several existing tests (regexp-18.8 to 18.10, 23.2, 23.3, 26.10 to 26.13) that expect the current results. | ||||
| User Comments: | ||||
serhiy.storchaka added on 2026-10-11 08:21:44:
Proposed fix in branch regexp-all-end-of-string: the -all loop also tries at the end of the string, as regsub -all does. The knownBug marks are removed from regexp-23.5, 23.7 and 23.9, and the tests that expected the old results are updated. Together with the fix for [471101ffff] (branch regexp-all-search-start), zero-width REs like \y, \m or $ then give the same matches with -all as in other RE engines. | ||||
