re_intuit_start(): merge two similar code branches
authorDavid Mitchell <davem@iabyn.com>
Thu, 26 Dec 2013 22:00:24 +0000 (22:00 +0000)
committerDavid Mitchell <davem@iabyn.com>
Fri, 7 Feb 2014 22:39:35 +0000 (22:39 +0000)
When the check string is anchored at a fixed offset from the start
of the string (e.g. /^..abc/), there are two similar code branches
that do a quick memNE() reject - the difference being whether SvTAIL() is
true, i.e. whether the pattern ends with $ and may match a \n.

Merge the common bits of the two branches. Technically this makes the
non-SvTAIL() branch slightly less efficient, since it will always retrieve
SvCUR(check) even when its not needed, but in practice it will already be
in the cache since we have to access SvPVX(check), and the I-cache misses
will have been reduced by reducing the code size.

It also removes one label.

regexec.c

index 7c56623..e52a315 100644 (file)
--- a/regexec.c
+++ b/regexec.c
@@ -708,13 +708,14 @@ Perl_re_intuit_start(pTHX_
                                      See [perl #115242] */
             {
                /* Substring at constant offset from beg-of-str... */
-               SSize_t slen;
+               SSize_t slen = SvCUR(check);
 
                s = HOP3c(strpos, prog->check_offset_min, strend);
            
                if (SvTAIL(check)) {
-                   slen = SvCUR(check);        /* >= 1 */
-
+                    /* In this case, the regex is anchored at the end too,
+                     * so the lengths must match exactly, give or take a \n.
+                    * NB: slen >= 1 since the last char of check is \n */
                    if (   strend - s > slen || strend - s < slen - 1
                       || (strend - s == slen && strend[-1] != '\n'))
                     {
@@ -724,19 +725,14 @@ Perl_re_intuit_start(pTHX_
                     }
                     /* Now should match s[0..slen-2] */
                     slen--;
-                    if (slen && (*SvPVX_const(check) != *s
-                        || (slen > 1 && memNE(SvPVX_const(check), s, slen))))
-                    {
-                      report_neq:
-                        DEBUG_EXECUTE_r(PerlIO_printf(Perl_debug_log,
-                                        "String not equal...\n"));
-                        goto fail_finish;
-                    }
                 }
-                else if (*SvPVX_const(check) != *s
-                         || ((slen = SvCUR(check)) > 1
-                             && memNE(SvPVX_const(check), s, slen)))
-                    goto report_neq;
+                if (slen && (*SvPVX_const(check) != *s
+                    || (slen > 1 && memNE(SvPVX_const(check), s, slen))))
+                {
+                    DEBUG_EXECUTE_r(PerlIO_printf(Perl_debug_log,
+                                    "String not equal...\n"));
+                    goto fail_finish;
+                }
 
                 check_at = s;
                 goto success_at_start;