]> granicus.if.org Git - php/commitdiff
- MFH: Fix Bug #45923 (mb_st[r]ripos() offset not handled correctly)
authorMoriyoshi Koizumi <moriyoshi@php.net>
Sat, 14 Feb 2009 07:35:01 +0000 (07:35 +0000)
committerMoriyoshi Koizumi <moriyoshi@php.net>
Sat, 14 Feb 2009 07:35:01 +0000 (07:35 +0000)
NEWS
ext/mbstring/libmbfl/mbfl/mbfilter.c
ext/mbstring/mbstring.c
ext/mbstring/tests/bug45923.phpt [new file with mode: 0644]

diff --git a/NEWS b/NEWS
index d33970c042c29a8d825ab9a14af9cc1bd71c9d04..996b871b8f7c86a661131e85d6db69221da7acfb 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -1,6 +1,7 @@
 PHP                                                                        NEWS
 |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
 ?? Feb 2009, PHP 5.2.9
+- Fixed Bug #45923 (mb_st[r]ripos() offset not handled correctly). (Moriyoshi)
 
 12 Feb 2009, PHP 5.2.9RC2
 - Fixed bug #47353 (crash when creating a lot of objects in object destructor).
index a2c117d2a300dd36a5d2d9714d0af9afa2d0c75b..907fa272b61274a78baa60e60a396168d20cdd57 100644 (file)
@@ -905,7 +905,7 @@ mbfl_strpos(
        }
 
        if (offset < 0) {
-               negative_offset = -offset-1;
+               negative_offset = -offset - pc.needle_len;
                offset = 0;
        }
 
index ffd79f0e91b5344f104c514cb5c124d0f8f27d15..b1011da945ef80f9b19c99d43b4dce984507fc7e 100644 (file)
@@ -1653,12 +1653,12 @@ PHP_FUNCTION(mb_strpos)
                }
        }
 
-       if (offset < 0 || (unsigned long)offset > (unsigned long)mbfl_strlen(&haystack)) {
-               php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset not contained in string.");
+       if (offset < 0 || offset > mbfl_strlen(&haystack)) {
+               php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset not contained in string");
                RETURN_FALSE;
        }
        if (needle.len == 0) {
-               php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty delimiter.");
+               php_error_docref(NULL TSRMLS_CC, E_WARNING, "Empty delimiter");
                RETURN_FALSE;
        }
 
@@ -1670,17 +1670,17 @@ PHP_FUNCTION(mb_strpos)
                case 1:
                        break;
                case 2:
-                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Needle has not positive length.");
+                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Needle has not positive length");
                        break;
                case 4:
-                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown encoding or conversion error.");
+                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown encoding or conversion error");
                        break;
                case 8:
-                       php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Argument is empty.");
+                       php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Argument is empty");
                        break;
                default:
-                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown error in mb_strpos.");
-                       break;                  
+                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown error in mb_strpos");
+                       break;
                }
                RETVAL_FALSE;
        }
@@ -1767,10 +1767,13 @@ PHP_FUNCTION(mb_strrpos)
                RETURN_FALSE;
        }
 
-       if ((offset > 0 && offset > mbfl_strlen(&haystack)) ||
-               (offset < 0 && -offset > mbfl_strlen(&haystack))) {
-               php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Offset is greater than the length of haystack string");
-               RETURN_FALSE;
+       {
+               int haystack_char_len = mbfl_strlen(&haystack);
+               if ((offset > 0 && offset > haystack_char_len) ||
+                       (offset < 0 && -offset > haystack_char_len)) {
+                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset is greater than the length of haystack string");
+                       RETURN_FALSE;
+               }
        }
 
        n = mbfl_strpos(&haystack, &needle, offset, 1);
@@ -1824,10 +1827,6 @@ PHP_FUNCTION(mb_strripos)
                RETURN_FALSE;
        }
 
-       if(offset > old_haystack_len){
-               RETURN_FALSE;
-       }
-
        n = php_mb_stripos(1, old_haystack, old_haystack_len, old_needle, old_needle_len, offset, from_encoding TSRMLS_CC);
 
        if (n >= 0) {
@@ -1987,7 +1986,7 @@ PHP_FUNCTION(mb_stristr)
                RETURN_FALSE;
        }
 
- n = php_mb_stripos(0, haystack.val, haystack.len, needle.val, needle.len, 0, from_encoding TSRMLS_CC);
      n = php_mb_stripos(0, haystack.val, haystack.len, needle.val, needle.len, 0, from_encoding TSRMLS_CC);
 
        if (n <0) {
                RETURN_FALSE;
@@ -4310,9 +4309,21 @@ MBSTRING_API int php_mb_stripos(int mode, char *old_haystack, int old_haystack_l
                        break;
                }
 
-               if (offset < 0 || (unsigned long)offset > haystack.len) {
-                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset not contained in string.");
-                       break;
+               {
+                       int haystack_char_len = mbfl_strlen(&haystack);
+
+                       if (mode) {
+                               if ((offset > 0 && offset > haystack_char_len) ||
+                                       (offset < 0 && -offset > haystack_char_len)) {
+                                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset is greater than the length of haystack string");
+                                       break;
+                               }
+                       } else {
+                               if (offset < 0 || offset > haystack_char_len) {
+                                       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Offset not contained in string");
+                                       break;
+                               }
+                       }
                }
 
                n = mbfl_strpos(&haystack, &needle, offset, mode);
@@ -4326,7 +4337,7 @@ MBSTRING_API int php_mb_stripos(int mode, char *old_haystack, int old_haystack_l
                efree(needle.val);
        }
 
- return n;
      return n;
 }
 /* }}} */
 
diff --git a/ext/mbstring/tests/bug45923.phpt b/ext/mbstring/tests/bug45923.phpt
new file mode 100644 (file)
index 0000000..2d184ab
--- /dev/null
@@ -0,0 +1,202 @@
+--TEST--
+Bug #45923 (mb_st[r]ripos() offset not handled correctly)
+--SKIPIF--
+<?php extension_loaded('mbstring') or die('skip mbstring not available'); ?>
+--INI--
+mbstring.internal_encoding=UTF-8
+--FILE--
+<?php
+var_dump(strpos("abc abc abc", "abc", 0));
+var_dump(strpos("abc abc abc", "abc", 3));
+var_dump(strpos("abc abc abc", "abc", 6));
+var_dump(strpos("abc abc abc", "abc", 9));
+var_dump(strpos("abc abc abc", "abc", 11));
+var_dump(strpos("abc abc abc", "abc", 12));
+var_dump(strpos("abc abc abc", "abc", -1));
+var_dump(strpos("abc abc abc", "abc", -3));
+var_dump(strpos("abc abc abc", "abc", -6));
+
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 0));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 3));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 6));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 9));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 11));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", 12));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", -1));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", -3));
+var_dump(mb_strpos("●○◆ ●○◆ ●○◆", "●○◆", -6));
+
+var_dump(stripos("abc abc abc", "abc", 0));
+var_dump(stripos("abc abc abc", "abc", 3));
+var_dump(stripos("abc abc abc", "abc", 6));
+var_dump(stripos("abc abc abc", "abc", 9));
+var_dump(stripos("abc abc abc", "abc", 11));
+var_dump(stripos("abc abc abc", "abc", 12));
+var_dump(stripos("abc abc abc", "abc", -1));
+var_dump(stripos("abc abc abc", "abc", -3));
+var_dump(stripos("abc abc abc", "abc", -6));
+
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 0));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 3));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 6));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 9));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 11));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", 12));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", -1));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", -3));
+var_dump(mb_stripos("●○◆ ●○◆ ●○◆", "●○◆", -6));
+
+var_dump(strrpos("abc abc abc", "abc", 0));
+var_dump(strrpos("abc abc abc", "abc", 3));
+var_dump(strrpos("abc abc abc", "abc", 6));
+var_dump(strrpos("abc abc abc", "abc", 9));
+var_dump(strrpos("abc abc abc", "abc", 11));
+var_dump(strrpos("abc abc abc", "abc", 12));
+var_dump(strrpos("abc abc abc", "abc", -1));
+var_dump(strrpos("abc abc abc", "abc", -3));
+var_dump(strrpos("abc abc abc", "abc", -6));
+
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 0));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 3));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 6));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 9));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 11));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", 12));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", -1));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", -3));
+var_dump(mb_strrpos("●○◆ ●○◆ ●○◆", "●○◆", -6));
+
+var_dump(strripos("abc abc abc", "abc", 0));
+var_dump(strripos("abc abc abc", "abc", 3));
+var_dump(strripos("abc abc abc", "abc", 6));
+var_dump(strripos("abc abc abc", "abc", 9));
+var_dump(strripos("abc abc abc", "abc", 11));
+var_dump(strripos("abc abc abc", "abc", 12));
+var_dump(strripos("abc abc abc", "abc", -1));
+var_dump(strripos("abc abc abc", "abc", -3));
+var_dump(strripos("abc abc abc", "abc", -6));
+
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 0));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 3));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 6));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 9));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 11));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", 12));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", -1));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", -3));
+var_dump(mb_strripos("●○◆ ●○◆ ●○◆", "●○◆", -6));
+
+?>
+--EXPECTF--
+int(0)
+int(4)
+int(8)
+bool(false)
+bool(false)
+
+Warning: strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: strpos(): Offset not contained in string in %s on line %d
+bool(false)
+int(0)
+int(4)
+int(8)
+bool(false)
+bool(false)
+
+Warning: mb_strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_strpos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_strpos(): Offset not contained in string in %s on line %d
+bool(false)
+int(0)
+int(4)
+int(8)
+bool(false)
+bool(false)
+
+Warning: stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: stripos(): Offset not contained in string in %s on line %d
+bool(false)
+int(0)
+int(4)
+int(8)
+bool(false)
+bool(false)
+
+Warning: mb_stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_stripos(): Offset not contained in string in %s on line %d
+bool(false)
+
+Warning: mb_stripos(): Offset not contained in string in %s on line %d
+bool(false)
+int(8)
+int(8)
+int(8)
+bool(false)
+bool(false)
+
+Warning: strrpos(): Offset is greater than the length of haystack string in %s on line %d
+bool(false)
+int(8)
+int(8)
+int(4)
+int(8)
+int(8)
+int(8)
+bool(false)
+bool(false)
+
+Warning: mb_strrpos(): Offset is greater than the length of haystack string in %s on line %d
+bool(false)
+int(8)
+int(8)
+int(4)
+int(8)
+int(8)
+int(8)
+bool(false)
+bool(false)
+
+Warning: strripos(): Offset is greater than the length of haystack string in %s on line %d
+bool(false)
+int(8)
+int(8)
+int(4)
+int(8)
+int(8)
+int(8)
+bool(false)
+bool(false)
+
+Warning: mb_strripos(): Offset is greater than the length of haystack string in %s on line %d
+bool(false)
+int(8)
+int(8)
+int(4)