summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore4
-rw-r--r--CODING_STANDARDS30
-rw-r--r--Makefile.global1
-rw-r--r--NEWS221
-rw-r--r--README.EXTENSIONS8
-rw-r--r--README.EXT_SKEL30
-rw-r--r--README.GIT-RULES8
-rw-r--r--README.RELEASE_PROCESS157
-rw-r--r--README.SUBMITTING_PATCH11
-rw-r--r--README.TESTING2
-rw-r--r--TSRM/tsrm_config.w32.h9
-rw-r--r--TSRM/tsrm_config_common.h2
-rw-r--r--TSRM/tsrm_nw.c2
-rw-r--r--TSRM/tsrm_nw.h2
-rw-r--r--TSRM/tsrm_virtual_cwd.c2
-rw-r--r--TSRM/tsrm_virtual_cwd.h2
-rw-r--r--TSRM/tsrm_win32.c2
-rw-r--r--TSRM/tsrm_win32.h2
-rwxr-xr-xUPGRADING3
-rw-r--r--Zend/Makefile.am2
-rw-r--r--Zend/Zend.dsp4
-rw-r--r--Zend/ZendTS.dsp4
-rw-r--r--Zend/tests/bug41421.phpt2
-rw-r--r--Zend/tests/bug65784.phpt62
-rw-r--r--Zend/tests/bug65969.phpt10
-rw-r--r--Zend/tests/bug66218.phpt21
-rw-r--r--Zend/tests/bug66286.phpt26
-rw-r--r--Zend/tests/generators/bug66041.phpt17
-rw-r--r--Zend/tests/generators/throw_caught.phpt2
-rw-r--r--Zend/tests/generators/throw_rethrow.phpt2
-rw-r--r--Zend/zend.c8
-rw-r--r--Zend/zend.h2
-rw-r--r--Zend/zend_API.c2
-rw-r--r--Zend/zend_API.h2
-rw-r--r--Zend/zend_alloc.c4
-rw-r--r--Zend/zend_alloc.h2
-rw-r--r--Zend/zend_build.h2
-rw-r--r--Zend/zend_builtin_functions.c68
-rw-r--r--Zend/zend_builtin_functions.h2
-rw-r--r--Zend/zend_closures.c2
-rw-r--r--Zend/zend_closures.h2
-rw-r--r--Zend/zend_compile.c4
-rw-r--r--Zend/zend_compile.h2
-rw-r--r--Zend/zend_config.nw.h2
-rw-r--r--Zend/zend_config.w32.h11
-rw-r--r--Zend/zend_constants.c2
-rw-r--r--Zend/zend_constants.h2
-rw-r--r--Zend/zend_default_classes.c2
-rw-r--r--Zend/zend_dynamic_array.c2
-rw-r--r--Zend/zend_dynamic_array.h2
-rw-r--r--Zend/zend_errors.h2
-rw-r--r--Zend/zend_exceptions.c63
-rw-r--r--Zend/zend_exceptions.h2
-rw-r--r--Zend/zend_execute.c5
-rw-r--r--Zend/zend_execute.h2
-rw-r--r--Zend/zend_execute_API.c10
-rw-r--r--Zend/zend_extensions.c2
-rw-r--r--Zend/zend_extensions.h2
-rw-r--r--Zend/zend_float.c2
-rw-r--r--Zend/zend_float.h2
-rw-r--r--Zend/zend_gc.c2
-rw-r--r--Zend/zend_gc.h2
-rw-r--r--Zend/zend_generators.c148
-rw-r--r--Zend/zend_generators.h4
-rw-r--r--Zend/zend_globals.h2
-rw-r--r--Zend/zend_globals_macros.h2
-rw-r--r--Zend/zend_hash.c2
-rw-r--r--Zend/zend_hash.h2
-rw-r--r--Zend/zend_highlight.c4
-rw-r--r--Zend/zend_highlight.h2
-rw-r--r--Zend/zend_indent.c2
-rw-r--r--Zend/zend_indent.h2
-rw-r--r--Zend/zend_ini.c2
-rw-r--r--Zend/zend_ini.h2
-rw-r--r--Zend/zend_ini_parser.y2
-rw-r--r--Zend/zend_ini_scanner.c2
-rw-r--r--Zend/zend_ini_scanner.h2
-rw-r--r--Zend/zend_ini_scanner.l2
-rw-r--r--Zend/zend_interfaces.c2
-rw-r--r--Zend/zend_interfaces.h2
-rw-r--r--Zend/zend_istdiostream.h2
-rw-r--r--Zend/zend_iterators.c2
-rw-r--r--Zend/zend_iterators.h2
-rw-r--r--Zend/zend_language_parser.y2
-rw-r--r--Zend/zend_language_scanner.c4
-rw-r--r--Zend/zend_language_scanner.h2
-rw-r--r--Zend/zend_language_scanner.l2
-rw-r--r--Zend/zend_language_scanner_defs.h2
-rw-r--r--Zend/zend_list.c2
-rw-r--r--Zend/zend_list.h2
-rw-r--r--Zend/zend_llist.c2
-rw-r--r--Zend/zend_llist.h2
-rw-r--r--Zend/zend_modules.h2
-rw-r--r--Zend/zend_multibyte.c2
-rw-r--r--Zend/zend_multibyte.h2
-rw-r--r--Zend/zend_multiply.h2
-rw-r--r--Zend/zend_object_handlers.c6
-rw-r--r--Zend/zend_object_handlers.h2
-rw-r--r--Zend/zend_objects.c2
-rw-r--r--Zend/zend_objects.h2
-rw-r--r--Zend/zend_objects_API.c2
-rw-r--r--Zend/zend_objects_API.h2
-rw-r--r--Zend/zend_opcode.c17
-rw-r--r--Zend/zend_operators.c2
-rw-r--r--Zend/zend_operators.h13
-rw-r--r--Zend/zend_ptr_stack.c2
-rw-r--r--Zend/zend_ptr_stack.h2
-rw-r--r--Zend/zend_qsort.c2
-rw-r--r--Zend/zend_qsort.h2
-rw-r--r--Zend/zend_sprintf.c2
-rw-r--r--Zend/zend_stack.c2
-rw-r--r--Zend/zend_stack.h2
-rw-r--r--Zend/zend_static_allocator.c2
-rw-r--r--Zend/zend_static_allocator.h2
-rw-r--r--Zend/zend_stream.c2
-rw-r--r--Zend/zend_stream.h2
-rw-r--r--Zend/zend_string.c2
-rw-r--r--Zend/zend_string.h2
-rw-r--r--Zend/zend_strtod.c3
-rw-r--r--Zend/zend_strtod.h2
-rw-r--r--Zend/zend_ts_hash.c2
-rw-r--r--Zend/zend_ts_hash.h2
-rw-r--r--Zend/zend_types.h2
-rw-r--r--Zend/zend_variables.c2
-rw-r--r--Zend/zend_variables.h2
-rw-r--r--Zend/zend_vm.h2
-rw-r--r--Zend/zend_vm_def.h61
-rw-r--r--Zend/zend_vm_execute.h886
-rw-r--r--Zend/zend_vm_gen.php44
-rw-r--r--Zend/zend_vm_opcodes.c193
-rw-r--r--Zend/zend_vm_opcodes.h9
-rwxr-xr-xbuild/buildcheck.sh4
-rw-r--r--configure.in4
-rw-r--r--ext/bcmath/bcmath.c2
-rw-r--r--ext/bcmath/php_bcmath.h2
-rw-r--r--ext/bz2/bz2.c2
-rw-r--r--ext/bz2/bz2_filter.c2
-rw-r--r--ext/bz2/php_bz2.h2
-rw-r--r--ext/calendar/cal_unix.c2
-rw-r--r--ext/calendar/calendar.c2
-rw-r--r--ext/calendar/easter.c2
-rw-r--r--ext/com_dotnet/com_com.c2
-rw-r--r--ext/com_dotnet/com_dotnet.c2
-rw-r--r--ext/com_dotnet/com_extension.c2
-rw-r--r--ext/com_dotnet/com_handlers.c2
-rw-r--r--ext/com_dotnet/com_iterator.c2
-rw-r--r--ext/com_dotnet/com_misc.c2
-rw-r--r--ext/com_dotnet/com_olechar.c2
-rw-r--r--ext/com_dotnet/com_persist.c2
-rw-r--r--ext/com_dotnet/com_saproxy.c2
-rw-r--r--ext/com_dotnet/com_typeinfo.c2
-rw-r--r--ext/com_dotnet/com_variant.c2
-rw-r--r--ext/com_dotnet/com_wrapper.c2
-rw-r--r--ext/com_dotnet/php_com_dotnet.h2
-rw-r--r--ext/com_dotnet/php_com_dotnet_internal.h2
-rw-r--r--ext/ctype/ctype.c2
-rw-r--r--ext/ctype/php_ctype.h2
-rw-r--r--ext/curl/curl_file.c2
-rw-r--r--ext/curl/interface.c183
-rw-r--r--ext/curl/multi.c2
-rw-r--r--ext/curl/php_curl.h4
-rw-r--r--ext/curl/share.c2
-rw-r--r--ext/curl/tests/bug48203_multi.phpt3
-rw-r--r--ext/curl/tests/bug54798.phpt5
-rw-r--r--ext/curl/tests/bug61948-win32.phpt4
-rw-r--r--ext/curl/tests/bug66109.phpt31
-rw-r--r--ext/curl/tests/curl_file_deleted_before_curl_close.phpt3
-rw-r--r--ext/curl/tests/curl_setopt_basic002.phpt1
-rw-r--r--ext/curl/tests/responder/get.php3
-rw-r--r--ext/date/lib/astro.c2
-rw-r--r--ext/date/lib/dow.c14
-rw-r--r--ext/date/lib/fallbackmap.h82
-rw-r--r--ext/date/lib/interval.c105
-rw-r--r--ext/date/lib/parse_date.c20
-rw-r--r--ext/date/lib/parse_date.re20
-rw-r--r--ext/date/lib/parse_iso_intervals.c6
-rw-r--r--ext/date/lib/parse_iso_intervals.re2
-rw-r--r--ext/date/lib/parse_tz.c2
-rw-r--r--ext/date/lib/timelib.c2
-rw-r--r--ext/date/lib/timelib.h7
-rw-r--r--ext/date/lib/timelib_structs.h8
-rw-r--r--ext/date/lib/timezonedb.h730
-rw-r--r--ext/date/lib/tm2unixtime.c2
-rw-r--r--ext/date/lib/unixtime2tm.c39
-rw-r--r--ext/date/php_date.c211
-rw-r--r--ext/date/php_date.h13
-rw-r--r--ext/date/tests/DateTimeZone_clone_basic1.phpt8
-rw-r--r--ext/date/tests/DateTimeZone_construct_basic.phpt4
-rw-r--r--ext/date/tests/DateTimeZone_construct_variation1.phpt8
-rw-r--r--ext/date/tests/DateTimeZone_serialize_type_2.phpt12
-rw-r--r--ext/date/tests/DateTimeZone_serialize_type_3.phpt4
-rw-r--r--ext/date/tests/DateTime_format_basic2.phpt2
-rw-r--r--ext/date/tests/DateTime_verify.phpt4
-rw-r--r--ext/date/tests/bug44780.phpt10
-rw-r--r--ext/date/tests/bug45543.phpt34
-rw-r--r--ext/date/tests/bug52063.phpt4
-rw-r--r--ext/date/tests/bug53879.phpt16
-rw-r--r--ext/date/tests/bug63391.phpt20
-rw-r--r--ext/date/tests/bug65371.phpt22
-rw-r--r--ext/date/tests/date_constants.phpt4
-rw-r--r--ext/date/tests/forward-transition-construction.phpt27
-rw-r--r--ext/date/tests/gmdate_variation13.phpt4
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-ba.phpt96
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd1.phpt48
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd2.phpt56
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bs.phpt92
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fa.phpt58
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fd.phpt58
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fs.phpt67
-rw-r--r--ext/date/tests/rfc-datetime_and_daylight_saving_time-type3.phpt399
-rw-r--r--ext/date/tests/strtotime3-64bit.phpt2
-rw-r--r--ext/date/tests/test-parse-from-format.phpt4
-rw-r--r--ext/date/tests/timezone_open_basic1.phpt6
-rw-r--r--ext/date/tests/timezone_open_variation1.phpt12
-rw-r--r--ext/dba/dba.c2
-rw-r--r--ext/dba/dba_cdb.c2
-rw-r--r--ext/dba/dba_db1.c2
-rw-r--r--ext/dba/dba_db2.c2
-rw-r--r--ext/dba/dba_db3.c2
-rw-r--r--ext/dba/dba_db4.c2
-rw-r--r--ext/dba/dba_dbm.c2
-rw-r--r--ext/dba/dba_flatfile.c2
-rw-r--r--ext/dba/dba_gdbm.c2
-rw-r--r--ext/dba/dba_inifile.c2
-rw-r--r--ext/dba/dba_ndbm.c2
-rw-r--r--ext/dba/dba_qdbm.c2
-rw-r--r--ext/dba/dba_tcadb.c2
-rw-r--r--ext/dba/libcdb/cdb.c2
-rw-r--r--ext/dba/libcdb/cdb.h2
-rw-r--r--ext/dba/libcdb/cdb_make.c2
-rw-r--r--ext/dba/libcdb/cdb_make.h2
-rw-r--r--ext/dba/libcdb/uint32.c2
-rw-r--r--ext/dba/libcdb/uint32.h2
-rw-r--r--ext/dba/libflatfile/flatfile.c2
-rw-r--r--ext/dba/libflatfile/flatfile.h2
-rw-r--r--ext/dba/libinifile/inifile.c2
-rw-r--r--ext/dba/libinifile/inifile.h2
-rw-r--r--ext/dba/php_dba.h2
-rw-r--r--ext/dba/php_tcadb.h2
-rw-r--r--ext/dom/attr.c2
-rw-r--r--ext/dom/cdatasection.c2
-rw-r--r--ext/dom/characterdata.c2
-rw-r--r--ext/dom/comment.c2
-rw-r--r--ext/dom/document.c21
-rw-r--r--ext/dom/documentfragment.c2
-rw-r--r--ext/dom/documenttype.c2
-rw-r--r--ext/dom/dom_ce.h2
-rw-r--r--ext/dom/dom_fe.h2
-rw-r--r--ext/dom/dom_iterators.c2
-rw-r--r--ext/dom/dom_properties.h2
-rw-r--r--ext/dom/domconfiguration.c2
-rw-r--r--ext/dom/domerror.c2
-rw-r--r--ext/dom/domerrorhandler.c2
-rw-r--r--ext/dom/domexception.c2
-rw-r--r--ext/dom/domimplementation.c2
-rw-r--r--ext/dom/domimplementationlist.c2
-rw-r--r--ext/dom/domimplementationsource.c2
-rw-r--r--ext/dom/domlocator.c2
-rw-r--r--ext/dom/domstringlist.c2
-rw-r--r--ext/dom/element.c2
-rw-r--r--ext/dom/entity.c2
-rw-r--r--ext/dom/entityreference.c2
-rw-r--r--ext/dom/namednodemap.c2
-rw-r--r--ext/dom/namelist.c2
-rw-r--r--ext/dom/node.c2
-rw-r--r--ext/dom/nodelist.c2
-rw-r--r--ext/dom/notation.c2
-rw-r--r--ext/dom/php_dom.c2
-rw-r--r--ext/dom/php_dom.h2
-rw-r--r--ext/dom/processinginstruction.c2
-rw-r--r--ext/dom/string_extend.c2
-rw-r--r--ext/dom/tests/bug65196.phpt26
-rw-r--r--ext/dom/text.c2
-rw-r--r--ext/dom/typeinfo.c2
-rw-r--r--ext/dom/userdatahandler.c2
-rw-r--r--ext/dom/xml_common.h2
-rw-r--r--ext/dom/xpath.c2
-rw-r--r--ext/enchant/enchant.c2
-rw-r--r--ext/enchant/php_enchant.h2
-rw-r--r--ext/ereg/ereg.c2
-rw-r--r--ext/ereg/php_ereg.h2
-rw-r--r--ext/ereg/php_regex.h2
-rw-r--r--ext/exif/exif.c9
-rw-r--r--ext/exif/php_exif.h2
-rw-r--r--ext/fileinfo/fileinfo.c2
-rw-r--r--ext/fileinfo/libmagic.patch161
-rw-r--r--ext/fileinfo/libmagic/ascmagic.c2
-rw-r--r--ext/fileinfo/libmagic/file.h2
-rw-r--r--ext/fileinfo/libmagic/funcs.c2
-rw-r--r--ext/fileinfo/libmagic/softmagic.c60
-rw-r--r--ext/fileinfo/php_fileinfo.h4
-rw-r--r--ext/fileinfo/tests/cve-2014-1943.phpt39
-rw-r--r--ext/fileinfo/tests/magic4
-rw-r--r--ext/filter/callback_filter.c2
-rw-r--r--ext/filter/filter.c2
-rw-r--r--ext/filter/filter_private.h2
-rw-r--r--ext/filter/logical_filters.c4
-rw-r--r--ext/filter/php_filter.h2
-rw-r--r--ext/filter/sanitizing_filters.c2
-rw-r--r--ext/filter/tests/bug53150.phpt4
-rw-r--r--ext/ftp/ftp.c6
-rw-r--r--ext/ftp/ftp.h2
-rw-r--r--ext/ftp/php_ftp.c6
-rw-r--r--ext/ftp/php_ftp.h2
-rw-r--r--ext/ftp/tests/ftp_fget_basic1.phpt4
-rw-r--r--ext/ftp/tests/ftp_fget_basic2.phpt4
-rw-r--r--ext/ftp/tests/ftp_fget_basic3.phpt4
-rw-r--r--ext/ftp/tests/ftp_nb_fget_basic1.phpt4
-rw-r--r--ext/ftp/tests/ftp_nb_fget_basic2.phpt4
-rw-r--r--ext/ftp/tests/ftp_nb_fget_basic3.phpt4
-rw-r--r--ext/ftp/tests/ftp_nb_get_large.phpt4
-rw-r--r--ext/gd/config.m427
-rw-r--r--ext/gd/gd.c183
-rw-r--r--ext/gd/gd_ctx.c2
-rw-r--r--ext/gd/libgd/gd_crop.c53
-rw-r--r--ext/gd/libgd/xbm.c2
-rw-r--r--ext/gd/php_gd.h2
-rw-r--r--ext/gd/tests/bug66356.phpt40
-rw-r--r--ext/gettext/gettext.c2
-rw-r--r--ext/gettext/php_gettext.h2
-rw-r--r--ext/gmp/gmp.c2
-rw-r--r--ext/gmp/php_gmp.h2
-rw-r--r--ext/hash/hash.c2
-rw-r--r--ext/hash/hash_adler32.c2
-rw-r--r--ext/hash/hash_crc32.c2
-rw-r--r--ext/hash/hash_fnv.c2
-rw-r--r--ext/hash/hash_gost.c2
-rw-r--r--ext/hash/hash_haval.c2
-rw-r--r--ext/hash/hash_joaat.c2
-rw-r--r--ext/hash/hash_md.c2
-rw-r--r--ext/hash/hash_ripemd.c2
-rw-r--r--ext/hash/hash_sha.c2
-rw-r--r--ext/hash/hash_snefru.c2
-rw-r--r--ext/hash/hash_tiger.c2
-rw-r--r--ext/hash/hash_whirlpool.c2
-rw-r--r--ext/hash/php_hash.h2
-rw-r--r--ext/hash/php_hash_adler32.h2
-rw-r--r--ext/hash/php_hash_crc32.h2
-rw-r--r--ext/hash/php_hash_crc32_tables.h2
-rw-r--r--ext/hash/php_hash_fnv.h2
-rw-r--r--ext/hash/php_hash_gost.h2
-rw-r--r--ext/hash/php_hash_haval.h2
-rw-r--r--ext/hash/php_hash_joaat.h2
-rw-r--r--ext/hash/php_hash_md.h2
-rw-r--r--ext/hash/php_hash_ripemd.h2
-rw-r--r--ext/hash/php_hash_sha.h2
-rw-r--r--ext/hash/php_hash_snefru.h2
-rw-r--r--ext/hash/php_hash_snefru_tables.h2
-rw-r--r--ext/hash/php_hash_tiger.h2
-rw-r--r--ext/hash/php_hash_tiger_tables.h2
-rw-r--r--ext/hash/php_hash_types.h2
-rw-r--r--ext/hash/php_hash_whirlpool.h2
-rw-r--r--ext/hash/php_hash_whirlpool_tables.h2
-rw-r--r--ext/iconv/iconv.c2
-rw-r--r--ext/iconv/php_iconv.h2
-rw-r--r--ext/imap/php_imap.c2
-rw-r--r--ext/imap/php_imap.h2
-rw-r--r--ext/interbase/ibase_blobs.c2
-rw-r--r--ext/interbase/ibase_events.c2
-rw-r--r--ext/interbase/ibase_query.c2
-rw-r--r--ext/interbase/ibase_service.c2
-rw-r--r--ext/interbase/interbase.c2
-rw-r--r--ext/interbase/php_ibase_includes.h2
-rw-r--r--ext/interbase/php_ibase_udf.c2
-rw-r--r--ext/interbase/php_interbase.h2
-rw-r--r--ext/intl/config.w321
-rw-r--r--ext/json/json.c34
-rw-r--r--ext/json/php_json.h4
-rw-r--r--ext/json/tests/bug64874_part1.phpt117
-rw-r--r--ext/ldap/ldap.c367
-rw-r--r--ext/ldap/php_ldap.h12
-rw-r--r--ext/ldap/tests/ldap_modify_batch_basic.phpt109
-rw-r--r--ext/ldap/tests/ldap_modify_batch_error.phpt104
-rw-r--r--ext/libxml/libxml.c6
-rw-r--r--ext/libxml/php_libxml.h2
-rw-r--r--ext/mbstring/mb_gpc.c2
-rw-r--r--ext/mbstring/mbstring.c2
-rw-r--r--ext/mbstring/mbstring.h2
-rw-r--r--ext/mbstring/php_mbregex.c2
-rw-r--r--ext/mbstring/php_mbregex.h2
-rw-r--r--ext/mbstring/php_unicode.c2
-rw-r--r--ext/mbstring/php_unicode.h2
-rw-r--r--ext/mbstring/tests/zend_multibyte-01.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-02.phpt16
-rw-r--r--ext/mbstring/tests/zend_multibyte-03.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-04.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-05.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-06.phpt16
-rw-r--r--ext/mbstring/tests/zend_multibyte-07.phpt11
-rw-r--r--ext/mbstring/tests/zend_multibyte-08.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-09.phpt11
-rw-r--r--ext/mbstring/tests/zend_multibyte-10.phpt8
-rw-r--r--ext/mbstring/tests/zend_multibyte-11.phpt8
-rw-r--r--ext/mbstring/tests/zend_multibyte-12.phpt8
-rw-r--r--ext/mbstring/tests/zend_multibyte-13.phpt9
-rw-r--r--ext/mbstring/tests/zend_multibyte-14.phpt9
-rw-r--r--ext/mcrypt/mcrypt.c2
-rw-r--r--ext/mcrypt/mcrypt_filter.c2
-rw-r--r--ext/mcrypt/php_mcrypt.h2
-rw-r--r--ext/mcrypt/php_mcrypt_filter.h2
-rw-r--r--ext/mssql/php_mssql.c2
-rw-r--r--ext/mssql/php_mssql.h2
-rw-r--r--ext/mysql/php_mysql.c2
-rw-r--r--ext/mysql/php_mysql.h2
-rw-r--r--ext/mysql/php_mysql_structs.h2
-rw-r--r--ext/mysqli/mysqli.c11
-rw-r--r--ext/mysqli/mysqli_api.c12
-rw-r--r--ext/mysqli/mysqli_driver.c2
-rw-r--r--ext/mysqli/mysqli_embedded.c2
-rw-r--r--ext/mysqli/mysqli_exception.c2
-rw-r--r--ext/mysqli/mysqli_fe.c2
-rw-r--r--ext/mysqli/mysqli_fe.h2
-rw-r--r--ext/mysqli/mysqli_libmysql.h2
-rw-r--r--ext/mysqli/mysqli_nonapi.c4
-rw-r--r--ext/mysqli/mysqli_priv.h2
-rw-r--r--ext/mysqli/mysqli_prop.c2
-rw-r--r--ext/mysqli/mysqli_report.c2
-rw-r--r--ext/mysqli/mysqli_result_iterator.c2
-rw-r--r--ext/mysqli/mysqli_warning.c2
-rw-r--r--ext/mysqli/php_mysqli.h2
-rw-r--r--ext/mysqli/php_mysqli_structs.h6
-rw-r--r--ext/mysqli/tests/bug66043.phpt24
-rw-r--r--ext/mysqli/tests/bug66124.phpt101
-rw-r--r--ext/mysqli/tests/bug66762.phpt26
-rw-r--r--ext/mysqlnd/CREDITS2
-rw-r--r--ext/mysqlnd/mysqlnd.c17
-rw-r--r--ext/mysqlnd/mysqlnd.h4
-rw-r--r--ext/mysqlnd/mysqlnd_alloc.c2
-rw-r--r--ext/mysqlnd/mysqlnd_alloc.h2
-rw-r--r--ext/mysqlnd/mysqlnd_auth.c2
-rw-r--r--ext/mysqlnd/mysqlnd_block_alloc.c2
-rw-r--r--ext/mysqlnd/mysqlnd_block_alloc.h2
-rw-r--r--ext/mysqlnd/mysqlnd_bt.c2
-rw-r--r--ext/mysqlnd/mysqlnd_charset.c2
-rw-r--r--ext/mysqlnd/mysqlnd_charset.h2
-rw-r--r--ext/mysqlnd/mysqlnd_debug.c2
-rw-r--r--ext/mysqlnd/mysqlnd_debug.h2
-rw-r--r--ext/mysqlnd/mysqlnd_driver.c2
-rw-r--r--ext/mysqlnd/mysqlnd_enum_n_def.h8
-rw-r--r--ext/mysqlnd/mysqlnd_ext_plugin.c2
-rw-r--r--ext/mysqlnd/mysqlnd_ext_plugin.h2
-rw-r--r--ext/mysqlnd/mysqlnd_libmysql_compat.h2
-rw-r--r--ext/mysqlnd/mysqlnd_loaddata.c2
-rw-r--r--ext/mysqlnd/mysqlnd_net.c2
-rw-r--r--ext/mysqlnd/mysqlnd_net.h2
-rw-r--r--ext/mysqlnd/mysqlnd_plugin.c2
-rw-r--r--ext/mysqlnd/mysqlnd_priv.h2
-rw-r--r--ext/mysqlnd/mysqlnd_ps.c5
-rw-r--r--ext/mysqlnd/mysqlnd_ps_codec.c43
-rw-r--r--ext/mysqlnd/mysqlnd_result.c13
-rw-r--r--ext/mysqlnd/mysqlnd_result.h2
-rw-r--r--ext/mysqlnd/mysqlnd_result_meta.c2
-rw-r--r--ext/mysqlnd/mysqlnd_result_meta.h2
-rw-r--r--ext/mysqlnd/mysqlnd_reverse_api.c2
-rw-r--r--ext/mysqlnd/mysqlnd_reverse_api.h2
-rw-r--r--ext/mysqlnd/mysqlnd_statistics.c2
-rw-r--r--ext/mysqlnd/mysqlnd_statistics.h2
-rw-r--r--ext/mysqlnd/mysqlnd_structs.h2
-rw-r--r--ext/mysqlnd/mysqlnd_wireprotocol.c7
-rw-r--r--ext/mysqlnd/mysqlnd_wireprotocol.h2
-rw-r--r--ext/mysqlnd/php_mysqlnd.c2
-rw-r--r--ext/mysqlnd/php_mysqlnd.h2
-rw-r--r--ext/oci8/oci8.c2
-rw-r--r--ext/oci8/oci8_collection.c2
-rw-r--r--ext/oci8/oci8_interface.c2
-rw-r--r--ext/oci8/oci8_lob.c2
-rw-r--r--ext/oci8/oci8_statement.c2
-rw-r--r--ext/oci8/php_oci8.h2
-rw-r--r--ext/oci8/php_oci8_int.h2
-rw-r--r--ext/oci8/tests/drcp_cclass1.phpt14
-rw-r--r--ext/oci8/tests/lob_015.phpt2
-rw-r--r--ext/odbc/birdstep.c2
-rw-r--r--ext/odbc/php_birdstep.h2
-rw-r--r--ext/odbc/php_odbc.c2
-rw-r--r--ext/odbc/php_odbc.h2
-rw-r--r--ext/odbc/php_odbc_includes.h2
-rw-r--r--ext/opcache/Optimizer/block_pass.c60
-rw-r--r--ext/opcache/Optimizer/pass1_5.c23
-rw-r--r--ext/opcache/Optimizer/zend_optimizer.c643
-rw-r--r--ext/opcache/Optimizer/zend_optimizer.h98
-rw-r--r--ext/opcache/Optimizer/zend_optimizer_internal.h172
-rw-r--r--ext/opcache/README12
-rw-r--r--ext/opcache/ZendAccelerator.c177
-rw-r--r--ext/opcache/ZendAccelerator.h7
-rw-r--r--ext/opcache/shared_alloc_mmap.c2
-rw-r--r--ext/opcache/shared_alloc_posix.c2
-rw-r--r--ext/opcache/shared_alloc_shm.c2
-rw-r--r--ext/opcache/shared_alloc_win32.c2
-rw-r--r--ext/opcache/tests/blacklist-win32.phpt34
-rw-r--r--ext/opcache/tests/blacklist.phpt2
-rw-r--r--ext/opcache/tests/bug65559.phpt22
-rw-r--r--ext/opcache/tests/bug65915.phpt26
-rw-r--r--ext/opcache/tests/bug66176.phpt19
-rw-r--r--ext/opcache/tests/bug66461.phpt15
-rw-r--r--ext/opcache/tests/bug66474.phpt18
-rw-r--r--ext/opcache/tests/is_script_cached.phpt15
-rw-r--r--ext/opcache/tests/issue0115.phpt48
-rw-r--r--ext/opcache/tests/issue0140.phpt43
-rw-r--r--ext/opcache/tests/issue0149.phpt35
-rw-r--r--ext/opcache/tests/opcache-2.blacklist2
-rw-r--r--ext/opcache/tests/php_cli_server.inc47
-rw-r--r--ext/opcache/tests/revalidate_path_01.phpt61
-rw-r--r--ext/opcache/zend_accelerator_blacklist.c2
-rw-r--r--ext/opcache/zend_accelerator_blacklist.h2
-rw-r--r--ext/opcache/zend_accelerator_debug.c2
-rw-r--r--ext/opcache/zend_accelerator_debug.h2
-rw-r--r--ext/opcache/zend_accelerator_hash.c2
-rw-r--r--ext/opcache/zend_accelerator_hash.h2
-rw-r--r--ext/opcache/zend_accelerator_module.c61
-rw-r--r--ext/opcache/zend_accelerator_module.h2
-rw-r--r--ext/opcache/zend_accelerator_util_funcs.c16
-rw-r--r--ext/opcache/zend_accelerator_util_funcs.h2
-rw-r--r--ext/opcache/zend_persist.c2
-rw-r--r--ext/opcache/zend_persist.h2
-rw-r--r--ext/opcache/zend_persist_calc.c14
-rw-r--r--ext/opcache/zend_shared_alloc.c2
-rw-r--r--ext/opcache/zend_shared_alloc.h2
-rwxr-xr-x[-rw-r--r--]ext/openssl/openssl.c39
-rw-r--r--ext/openssl/php_openssl.h2
-rw-r--r--ext/openssl/tests/bug64802.phpt1
-rw-r--r--ext/openssl/tests/bug66501.phpt22
-rw-r--r--ext/openssl/tests/cve-2013-6420.crt29
-rw-r--r--ext/openssl/tests/cve-2013-6420.phpt18
-rw-r--r--ext/openssl/xp_ssl.c6
-rw-r--r--ext/pcntl/pcntl.c2
-rw-r--r--ext/pcntl/php_pcntl.h2
-rw-r--r--ext/pcntl/php_signal.c2
-rw-r--r--ext/pcntl/php_signal.h2
-rw-r--r--ext/pcre/pcrelib/AUTHORS6
-rw-r--r--ext/pcre/pcrelib/ChangeLog378
-rw-r--r--ext/pcre/pcrelib/HACKING269
-rw-r--r--ext/pcre/pcrelib/LICENCE6
-rw-r--r--ext/pcre/pcrelib/NEWS71
-rw-r--r--ext/pcre/pcrelib/README113
-rw-r--r--ext/pcre/pcrelib/config.h4
-rw-r--r--ext/pcre/pcrelib/doc/pcre.txt4105
-rw-r--r--ext/pcre/pcrelib/pcre.h50
-rw-r--r--ext/pcre/pcrelib/pcre_chartables.c2
-rw-r--r--ext/pcre/pcrelib/pcre_compile.c3619
-rw-r--r--ext/pcre/pcrelib/pcre_config.c4
-rw-r--r--ext/pcre/pcrelib/pcre_exec.c959
-rw-r--r--ext/pcre/pcrelib/pcre_fullinfo.c16
-rw-r--r--ext/pcre/pcrelib/pcre_internal.h459
-rw-r--r--ext/pcre/pcrelib/pcre_maketables.c27
-rw-r--r--ext/pcre/pcrelib/pcre_study.c86
-rw-r--r--ext/pcre/pcrelib/pcre_tables.c15
-rw-r--r--ext/pcre/pcrelib/pcre_ucd.c753
-rw-r--r--ext/pcre/pcrelib/pcre_valid_utf8.c15
-rw-r--r--ext/pcre/pcrelib/pcre_xclass.c101
-rw-r--r--ext/pcre/pcrelib/pcreposix.c12
-rw-r--r--ext/pcre/pcrelib/testdata/grepbinarybin0 -> 45 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/grepfilelist3
-rw-r--r--ext/pcre/pcrelib/testdata/grepinput315
-rw-r--r--ext/pcre/pcrelib/testdata/grepinput84
-rw-r--r--ext/pcre/pcrelib/testdata/grepinputv4
-rw-r--r--ext/pcre/pcrelib/testdata/grepoutput38
-rw-r--r--ext/pcre/pcrelib/testdata/grepoutput84
-rw-r--r--ext/pcre/pcrelib/testdata/grepoutputN18
-rw-r--r--ext/pcre/pcrelib/testdata/greppatN42
-rw-r--r--ext/pcre/pcrelib/testdata/saved16bin0 -> 86 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved16BE-1bin0 -> 410 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved16BE-2bin0 -> 344 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved16LE-1bin0 -> 410 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved16LE-2bin0 -> 344 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved32bin0 -> 108 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved32BE-1bin0 -> 552 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved32BE-2bin0 -> 456 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved32LE-1bin0 -> 552 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved32LE-2bin0 -> 456 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/saved8bin0 -> 77 bytes
-rw-r--r--ext/pcre/pcrelib/testdata/testinput1467
-rw-r--r--ext/pcre/pcrelib/testdata/testinput10108
-rw-r--r--ext/pcre/pcrelib/testdata/testinput11135
-rw-r--r--ext/pcre/pcrelib/testdata/testinput1290
-rw-r--r--ext/pcre/pcrelib/testdata/testinput139
-rw-r--r--ext/pcre/pcrelib/testdata/testinput14343
-rw-r--r--ext/pcre/pcrelib/testdata/testinput15366
-rw-r--r--ext/pcre/pcrelib/testdata/testinput1635
-rw-r--r--ext/pcre/pcrelib/testdata/testinput17307
-rw-r--r--ext/pcre/pcrelib/testdata/testinput18300
-rw-r--r--ext/pcre/pcrelib/testdata/testinput1922
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2455
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2019
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2126
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2223
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2320
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2411
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2544
-rw-r--r--ext/pcre/pcrelib/testdata/testinput2614
-rw-r--r--ext/pcre/pcrelib/testdata/testinput32
-rw-r--r--ext/pcre/pcrelib/testdata/testinput495
-rw-r--r--ext/pcre/pcrelib/testdata/testinput519
-rw-r--r--ext/pcre/pcrelib/testdata/testinput6180
-rw-r--r--ext/pcre/pcrelib/testdata/testinput7166
-rw-r--r--ext/pcre/pcrelib/testdata/testinput889
-rw-r--r--ext/pcre/pcrelib/testdata/testinput924
-rw-r--r--ext/pcre/pcrelib/testdata/testinputEBC121
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput1678
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput10581
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput11-16712
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput11-32712
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput11-8712
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput12179
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput1322
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput14530
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput151139
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput16121
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput17558
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput18-161026
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput18-321023
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput1988
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput22150
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput2024
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput21-16100
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput21-32100
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput22-1681
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput22-3281
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput2346
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput2413
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput2593
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput2617
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput32
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput4172
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput566
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput6339
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput7835
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput8451
-rw-r--r--ext/pcre/pcrelib/testdata/testoutput9114
-rw-r--r--ext/pcre/pcrelib/testdata/testoutputEBC182
-rw-r--r--ext/pcre/pcrelib/testdata/wintestinput391
-rw-r--r--ext/pcre/pcrelib/testdata/wintestoutput3166
-rw-r--r--ext/pcre/pcrelib/ucp.h5
-rw-r--r--ext/pcre/php_pcre.c2
-rw-r--r--ext/pcre/php_pcre.h2
-rw-r--r--ext/pcre/tests/bug37911.phpt2
-rw-r--r--ext/pcre/tests/grep2.phpt10
-rw-r--r--ext/pcre/tests/match_flags3.phpt2
-rw-r--r--ext/pdo/pdo.c2
-rw-r--r--ext/pdo/pdo_dbh.c10
-rw-r--r--ext/pdo/pdo_sql_parser.c25
-rw-r--r--ext/pdo/pdo_sql_parser.re23
-rw-r--r--ext/pdo/pdo_sqlstate.c2
-rw-r--r--ext/pdo/pdo_stmt.c2
-rw-r--r--ext/pdo/php_pdo.h2
-rw-r--r--ext/pdo/php_pdo_driver.h2
-rw-r--r--ext/pdo/php_pdo_int.h2
-rw-r--r--ext/pdo/tests/bug65946.phpt32
-rw-r--r--ext/pdo_dblib/dblib_driver.c2
-rw-r--r--ext/pdo_dblib/dblib_stmt.c2
-rw-r--r--ext/pdo_dblib/pdo_dblib.c2
-rw-r--r--ext/pdo_dblib/php_pdo_dblib.h2
-rw-r--r--ext/pdo_dblib/php_pdo_dblib_int.h2
-rw-r--r--ext/pdo_firebird/firebird_driver.c2
-rw-r--r--ext/pdo_firebird/firebird_statement.c2
-rw-r--r--ext/pdo_firebird/pdo_firebird.c2
-rw-r--r--ext/pdo_firebird/php_pdo_firebird.h2
-rw-r--r--ext/pdo_firebird/php_pdo_firebird_int.h2
-rw-r--r--ext/pdo_mysql/mysql_driver.c2
-rw-r--r--ext/pdo_mysql/mysql_statement.c2
-rw-r--r--ext/pdo_mysql/pdo_mysql.c9
-rw-r--r--ext/pdo_mysql/php_pdo_mysql.h2
-rw-r--r--ext/pdo_mysql/php_pdo_mysql_int.h2
-rw-r--r--ext/pdo_mysql/tests/bug66141.phpt38
-rw-r--r--ext/pdo_oci/oci_driver.c2
-rw-r--r--ext/pdo_oci/oci_statement.c2
-rw-r--r--ext/pdo_oci/pdo_oci.c2
-rw-r--r--ext/pdo_oci/php_pdo_oci.h2
-rw-r--r--ext/pdo_oci/php_pdo_oci_int.h2
-rw-r--r--ext/pdo_odbc/odbc_driver.c2
-rw-r--r--ext/pdo_odbc/odbc_stmt.c7
-rw-r--r--ext/pdo_odbc/pdo_odbc.c2
-rw-r--r--ext/pdo_odbc/php_pdo_odbc.h2
-rw-r--r--ext/pdo_odbc/php_pdo_odbc_int.h2
-rw-r--r--ext/pdo_pgsql/pdo_pgsql.c2
-rw-r--r--ext/pdo_pgsql/pgsql_driver.c33
-rw-r--r--ext/pdo_pgsql/pgsql_statement.c2
-rw-r--r--ext/pdo_pgsql/php_pdo_pgsql.h2
-rw-r--r--ext/pdo_pgsql/php_pdo_pgsql_int.h2
-rw-r--r--ext/pdo_pgsql/tests/bug62479.phpt56
-rw-r--r--ext/pdo_sqlite/pdo_sqlite.c2
-rw-r--r--ext/pdo_sqlite/php_pdo_sqlite.h2
-rw-r--r--ext/pdo_sqlite/php_pdo_sqlite_int.h2
-rw-r--r--ext/pdo_sqlite/sqlite_driver.c2
-rw-r--r--ext/pdo_sqlite/sqlite_statement.c2
-rw-r--r--ext/pdo_sqlite/tests/bug66033.phpt33
-rw-r--r--ext/pgsql/pgsql.c618
-rw-r--r--ext/pgsql/php_pgsql.h6
-rw-r--r--ext/phar/dirstream.c2
-rw-r--r--ext/phar/dirstream.h2
-rw-r--r--ext/phar/func_interceptors.c2
-rw-r--r--ext/phar/func_interceptors.h2
-rw-r--r--ext/phar/phar.1.in2
-rw-r--r--ext/phar/phar.c96
-rw-r--r--ext/phar/phar_internal.h61
-rw-r--r--ext/phar/phar_object.c80
-rw-r--r--ext/phar/phar_path_check.c2
-rw-r--r--ext/phar/pharzip.h2
-rw-r--r--ext/phar/php_phar.h2
-rw-r--r--ext/phar/stream.c14
-rw-r--r--ext/phar/stream.h2
-rw-r--r--ext/phar/stub.h2
-rw-r--r--ext/phar/tar.c2
-rw-r--r--ext/phar/tar.h2
-rw-r--r--ext/phar/util.c301
-rw-r--r--ext/phar/zip.c12
-rw-r--r--ext/posix/php_posix.h2
-rw-r--r--ext/posix/posix.c2
-rw-r--r--ext/pspell/php_pspell.h2
-rw-r--r--ext/pspell/pspell.c2
-rw-r--r--ext/readline/php_readline.h2
-rw-r--r--ext/readline/readline.c12
-rw-r--r--ext/readline/readline_cli.c2
-rw-r--r--ext/readline/readline_cli.h2
-rw-r--r--ext/readline/tests/libedit_callback_handler_install_001.phpt26
-rw-r--r--ext/readline/tests/libedit_callback_handler_remove_001.phpt22
-rw-r--r--ext/readline/tests/libedit_info_001.phpt43
-rw-r--r--ext/readline/tests/libedit_write_history_001.phpt29
-rw-r--r--ext/readline/tests/readline_callback_handler_install_001.phpt4
-rw-r--r--ext/readline/tests/readline_callback_handler_remove_001.phpt4
-rw-r--r--ext/readline/tests/readline_info_001.phpt4
-rw-r--r--ext/readline/tests/readline_write_history_001.phpt4
-rw-r--r--ext/recode/php_recode.h2
-rw-r--r--ext/recode/recode.c2
-rw-r--r--ext/reflection/php_reflection.c68
-rw-r--r--ext/reflection/php_reflection.h2
-rw-r--r--ext/reflection/tests/ReflectionClass_getStaticPropertyValue_001_2_4.phpt2
-rw-r--r--ext/reflection/tests/ReflectionClass_setStaticPropertyValue_001_2_4.phpt2
-rw-r--r--ext/reflection/tests/ReflectionExtension_bug66218.phpt21
-rw-r--r--ext/session/mod_files.c5
-rw-r--r--ext/session/mod_files.h2
-rw-r--r--ext/session/mod_mm.c3
-rw-r--r--ext/session/mod_mm.h2
-rw-r--r--ext/session/mod_user.c2
-rw-r--r--ext/session/mod_user.h2
-rw-r--r--ext/session/mod_user_class.c2
-rw-r--r--ext/session/php_session.h2
-rw-r--r--ext/session/session.c67
-rw-r--r--ext/session/tests/bug60634.phpt1
-rw-r--r--ext/session/tests/bug60634_error_4.phpt1
-rw-r--r--ext/session/tests/bug66481-win32.phpt17
-rw-r--r--ext/session/tests/bug66481.phpt18
-rw-r--r--ext/session/tests/session_name_error.phpt2
-rw-r--r--ext/shmop/php_shmop.h2
-rw-r--r--ext/shmop/shmop.c2
-rw-r--r--ext/simplexml/php_simplexml.h2
-rw-r--r--ext/simplexml/php_simplexml_exports.h2
-rw-r--r--ext/simplexml/simplexml.c2
-rw-r--r--ext/simplexml/sxe.c2
-rw-r--r--ext/simplexml/sxe.h2
-rw-r--r--ext/snmp/php_snmp.h2
-rw-r--r--ext/snmp/snmp.c10
-rw-r--r--ext/soap/php_encoding.c2
-rw-r--r--ext/soap/php_encoding.h2
-rw-r--r--ext/soap/php_http.c2
-rw-r--r--ext/soap/php_http.h2
-rw-r--r--ext/soap/php_packet_soap.c2
-rw-r--r--ext/soap/php_packet_soap.h2
-rw-r--r--ext/soap/php_schema.c2
-rw-r--r--ext/soap/php_schema.h2
-rw-r--r--ext/soap/php_sdl.c2
-rw-r--r--ext/soap/php_sdl.h2
-rw-r--r--ext/soap/php_soap.h2
-rw-r--r--ext/soap/php_xml.c2
-rw-r--r--ext/soap/php_xml.h2
-rw-r--r--ext/soap/soap.c228
-rw-r--r--ext/soap/tests/bugs/bug66112.phpt36
-rw-r--r--ext/soap/tests/bugs/bug66112.wsdl42
-rw-r--r--ext/sockets/config.m421
-rw-r--r--ext/sockets/multicast.c2
-rw-r--r--ext/sockets/multicast.h2
-rw-r--r--ext/sockets/php_sockets.h6
-rw-r--r--ext/sockets/sockaddr_conv.c6
-rw-r--r--ext/sockets/sockets.c5
-rw-r--r--ext/sockets/unix_socket_constants.h2
-rw-r--r--ext/sockets/win32_socket_constants.h2
-rw-r--r--ext/spl/php_spl.c2
-rw-r--r--ext/spl/php_spl.h2
-rw-r--r--ext/spl/spl_array.c2
-rw-r--r--ext/spl/spl_array.h2
-rw-r--r--ext/spl/spl_directory.c2
-rw-r--r--ext/spl/spl_directory.h2
-rw-r--r--ext/spl/spl_dllist.c2
-rw-r--r--ext/spl/spl_dllist.h2
-rw-r--r--ext/spl/spl_engine.c2
-rw-r--r--ext/spl/spl_engine.h2
-rw-r--r--ext/spl/spl_exceptions.c2
-rw-r--r--ext/spl/spl_exceptions.h2
-rw-r--r--ext/spl/spl_fixedarray.c2
-rw-r--r--ext/spl/spl_fixedarray.h2
-rw-r--r--ext/spl/spl_functions.c2
-rw-r--r--ext/spl/spl_functions.h2
-rw-r--r--ext/spl/spl_heap.c2
-rw-r--r--ext/spl/spl_heap.h2
-rw-r--r--ext/spl/spl_iterators.c2
-rw-r--r--ext/spl/spl_iterators.h2
-rw-r--r--ext/spl/spl_observer.c2
-rw-r--r--ext/spl/spl_observer.h2
-rw-r--r--ext/spl/tests/SplFileObject_getflags_basic.phpt6
-rw-r--r--ext/spl/tests/SplFileObject_getflags_error001.phpt6
-rw-r--r--ext/spl/tests/SplFileObject_getflags_error002.phpt6
-rw-r--r--ext/spl/tests/SplFileObject_rewind_error001.phpt6
-rw-r--r--ext/spl/tests/bug54291.phpt2
-rw-r--r--ext/spl/tests/class_implements_variation.phpt10
-rw-r--r--ext/spl/tests/class_uses_variation.phpt10
-rw-r--r--ext/sqlite3/php_sqlite3.h2
-rw-r--r--ext/sqlite3/php_sqlite3_structs.h2
-rw-r--r--ext/sqlite3/sqlite3.c2
-rw-r--r--ext/standard/array.c2
-rw-r--r--ext/standard/assert.c2
-rw-r--r--ext/standard/base64.c2
-rw-r--r--ext/standard/base64.h2
-rw-r--r--ext/standard/basic_functions.c6
-rw-r--r--ext/standard/basic_functions.h2
-rw-r--r--ext/standard/browscap.c2
-rw-r--r--ext/standard/crc32.c2
-rw-r--r--ext/standard/crc32.h2
-rw-r--r--ext/standard/credits.c2
-rw-r--r--ext/standard/credits.h2
-rw-r--r--ext/standard/credits_ext.h10
-rw-r--r--ext/standard/crypt.c2
-rw-r--r--ext/standard/css.c2
-rw-r--r--ext/standard/css.h2
-rw-r--r--ext/standard/cyr_convert.c2
-rw-r--r--ext/standard/cyr_convert.h2
-rw-r--r--ext/standard/datetime.c2
-rw-r--r--ext/standard/datetime.h2
-rw-r--r--ext/standard/dir.c2
-rw-r--r--ext/standard/dl.c2
-rw-r--r--ext/standard/dl.h2
-rw-r--r--ext/standard/dns.c2
-rw-r--r--ext/standard/dns_win32.c2
-rw-r--r--ext/standard/exec.c2
-rw-r--r--ext/standard/exec.h2
-rw-r--r--ext/standard/file.c2
-rw-r--r--ext/standard/file.h2
-rw-r--r--ext/standard/filestat.c2
-rw-r--r--ext/standard/filters.c2
-rw-r--r--ext/standard/flock_compat.c2
-rw-r--r--ext/standard/flock_compat.h2
-rw-r--r--ext/standard/formatted_print.c2
-rw-r--r--ext/standard/fsock.c2
-rw-r--r--ext/standard/fsock.h2
-rw-r--r--ext/standard/ftok.c2
-rw-r--r--ext/standard/ftp_fopen_wrapper.c2
-rw-r--r--ext/standard/head.c2
-rw-r--r--ext/standard/head.h2
-rw-r--r--ext/standard/html.c2
-rw-r--r--ext/standard/html.h2
-rw-r--r--ext/standard/html_tables.h2
-rw-r--r--ext/standard/html_tables/html_table_gen.php3
-rw-r--r--ext/standard/http.c2
-rw-r--r--ext/standard/http_fopen_wrapper.c2
-rw-r--r--ext/standard/image.c2
-rw-r--r--ext/standard/incomplete_class.c2
-rw-r--r--ext/standard/info.c2
-rw-r--r--ext/standard/info.h2
-rw-r--r--ext/standard/iptc.c2
-rw-r--r--ext/standard/lcg.c2
-rw-r--r--ext/standard/levenshtein.c2
-rw-r--r--ext/standard/link.c2
-rw-r--r--ext/standard/link_win32.c2
-rw-r--r--ext/standard/mail.c4
-rw-r--r--ext/standard/math.c2
-rw-r--r--ext/standard/md5.c2
-rw-r--r--ext/standard/md5.h2
-rw-r--r--ext/standard/metaphone.c2
-rw-r--r--ext/standard/microtime.c2
-rw-r--r--ext/standard/microtime.h2
-rw-r--r--ext/standard/pack.c2
-rw-r--r--ext/standard/pack.h2
-rw-r--r--ext/standard/pageinfo.c2
-rw-r--r--ext/standard/pageinfo.h2
-rw-r--r--ext/standard/password.c2
-rw-r--r--ext/standard/php_array.h2
-rw-r--r--ext/standard/php_assert.h2
-rw-r--r--ext/standard/php_browscap.h2
-rw-r--r--ext/standard/php_crypt.h2
-rw-r--r--ext/standard/php_crypt_r.c2
-rw-r--r--ext/standard/php_crypt_r.h2
-rw-r--r--ext/standard/php_dir.h2
-rw-r--r--ext/standard/php_dns.h2
-rw-r--r--ext/standard/php_ext_syslog.h2
-rw-r--r--ext/standard/php_filestat.h2
-rw-r--r--ext/standard/php_fopen_wrapper.c2
-rw-r--r--ext/standard/php_fopen_wrappers.h2
-rw-r--r--ext/standard/php_ftok.h2
-rw-r--r--ext/standard/php_http.h2
-rw-r--r--ext/standard/php_image.h2
-rw-r--r--ext/standard/php_incomplete_class.h2
-rw-r--r--ext/standard/php_iptc.h2
-rw-r--r--ext/standard/php_lcg.h2
-rw-r--r--ext/standard/php_link.h2
-rw-r--r--ext/standard/php_mail.h2
-rw-r--r--ext/standard/php_math.h2
-rw-r--r--ext/standard/php_metaphone.h2
-rw-r--r--ext/standard/php_password.h2
-rw-r--r--ext/standard/php_rand.h2
-rw-r--r--ext/standard/php_smart_str.h2
-rw-r--r--ext/standard/php_smart_str_public.h2
-rw-r--r--ext/standard/php_standard.h2
-rw-r--r--ext/standard/php_string.h4
-rw-r--r--ext/standard/php_type.h2
-rw-r--r--ext/standard/php_uuencode.h2
-rw-r--r--ext/standard/php_var.h2
-rw-r--r--ext/standard/php_versioning.h2
-rw-r--r--ext/standard/proc_open.c39
-rw-r--r--ext/standard/proc_open.h2
-rw-r--r--ext/standard/quot_print.c2
-rw-r--r--ext/standard/quot_print.h2
-rw-r--r--ext/standard/rand.c2
-rw-r--r--ext/standard/scanf.c2
-rw-r--r--ext/standard/scanf.h2
-rw-r--r--ext/standard/sha1.c2
-rw-r--r--ext/standard/sha1.h2
-rw-r--r--ext/standard/soundex.c2
-rw-r--r--ext/standard/streamsfuncs.c2
-rw-r--r--ext/standard/streamsfuncs.h2
-rw-r--r--ext/standard/string.c26
-rw-r--r--ext/standard/syslog.c2
-rw-r--r--ext/standard/tests/array/each.phptbin9570 -> 9574 bytes
-rw-r--r--ext/standard/tests/class_object/class_exists_variation_001.phpt5
-rw-r--r--ext/standard/tests/class_object/trait_exists_variation_001.phpt5
-rw-r--r--ext/standard/tests/file/007_error.phpt4
-rw-r--r--ext/standard/tests/file/basename_bug66395-win32.phpt18
-rw-r--r--ext/standard/tests/file/basename_bug66395_variation2-win32.phpt38
-rw-r--r--ext/standard/tests/file/bug66509.phpt15
-rw-r--r--ext/standard/tests/file/fgets_socket_variation1.phpt12
-rw-r--r--ext/standard/tests/file/fgets_socket_variation2.phpt12
-rw-r--r--ext/standard/tests/file/fgetss_error.phpt2
-rw-r--r--ext/standard/tests/file/file_put_contents_variation9.phpt8
-rw-r--r--ext/standard/tests/file/fread_socket_variation1.phpt15
-rw-r--r--ext/standard/tests/file/ftruncate_error.phpt2
-rw-r--r--ext/standard/tests/general_functions/bug41445_1.phpt2
-rw-r--r--ext/standard/tests/general_functions/bug66094.phpt12
-rw-r--r--ext/standard/tests/general_functions/floatval.phpt8
-rw-r--r--ext/standard/tests/general_functions/gettype_settype_basic.phpt32
-rw-r--r--ext/standard/tests/general_functions/print_r.phpt12
-rw-r--r--ext/standard/tests/general_functions/strval.phpt4
-rw-r--r--ext/standard/tests/general_functions/type.phpt8
-rw-r--r--ext/standard/tests/general_functions/var_dump.phpt8
-rw-r--r--ext/standard/tests/general_functions/var_export-locale.phpt2
-rw-r--r--ext/standard/tests/general_functions/var_export_basic3.phpt2
-rw-r--r--ext/standard/tests/general_functions/var_export_basic5.phpt2
-rw-r--r--ext/standard/tests/mail/bug51604.phpt4
-rw-r--r--ext/standard/tests/mail/bug66535.phpt43
-rw-r--r--ext/standard/tests/mail/mail_basic.phpt6
-rw-r--r--ext/standard/tests/mail/mail_basic2.phpt4
-rw-r--r--ext/standard/tests/mail/mail_basic3.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic4.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic5.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic_alt1-win32.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic_alt2-win32.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic_alt3-win32.phpt2
-rw-r--r--ext/standard/tests/mail/mail_basic_alt4-win32.phpt2
-rw-r--r--ext/standard/tests/mail/mail_variation1.phpt2
-rw-r--r--ext/standard/tests/mail/mail_variation2.phpt4
-rw-r--r--ext/standard/tests/mail/mail_variation_alt1-win32.phpt2
-rw-r--r--ext/standard/tests/mail/mail_variation_alt2-win32.phpt2
-rw-r--r--ext/standard/tests/math/tan_basiclong_64bit.phpt37
-rw-r--r--ext/standard/tests/network/fsockopen_basic.phpt10
-rw-r--r--ext/standard/tests/network/fsockopen_variation1.phpt10
-rw-r--r--ext/standard/tests/network/shutdown.phpt18
-rw-r--r--ext/standard/tests/network/socket_get_status_basic.phpt14
-rw-r--r--ext/standard/tests/network/tcp4loop.phpt13
-rw-r--r--ext/standard/tests/network/tcp6loop.phpt14
-rw-r--r--ext/standard/tests/network/udp6loop.phpt14
-rw-r--r--ext/standard/tests/serialize/serialization_error_002.phpt52
-rw-r--r--ext/standard/tests/streams/bug60602.phpt57
-rw-r--r--ext/standard/tests/streams/stream_set_timeout_error.phpt12
-rw-r--r--ext/standard/tests/strings/bug33605.phpt4
-rw-r--r--ext/standard/tests/strings/bug65947.phpt17
-rw-r--r--ext/standard/tests/strings/implode1.phptbin5875 -> 5877 bytes
-rw-r--r--ext/standard/tests/strings/substr_compare.phpt7
-rw-r--r--ext/standard/tests/strings/vfprintf_basic1.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic2.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic3.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic4.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic5.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic6.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic7.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic7_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic8.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_basic9.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation10.phptbin2963 -> 2979 bytes
-rw-r--r--ext/standard/tests/strings/vfprintf_variation11.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation11_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation12.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation12_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation13.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation13_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation14.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation14_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation15.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation15_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation16.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation16_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation17.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation18.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation19.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation19_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation20.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation21.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation3.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation4.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation4_64bit.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation5.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation6.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation7.phptbin2391 -> 2406 bytes
-rw-r--r--ext/standard/tests/strings/vfprintf_variation8.phpt2
-rw-r--r--ext/standard/tests/strings/vfprintf_variation9.phptbin1857 -> 1872 bytes
-rw-r--r--ext/standard/tests/time/strptime_basic.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_001.phpt11
-rw-r--r--ext/standard/tests/url/parse_url_basic_002.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_003.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_004.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_005.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_006.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_007.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_008.phpt4
-rw-r--r--ext/standard/tests/url/parse_url_basic_009.phpt4
-rw-r--r--ext/standard/tests/url/urls.inc4
-rw-r--r--ext/standard/type.c2
-rw-r--r--ext/standard/uniqid.c2
-rw-r--r--ext/standard/uniqid.h2
-rw-r--r--ext/standard/url.c2
-rw-r--r--ext/standard/url.h2
-rw-r--r--ext/standard/url_scanner_ex.c2
-rw-r--r--ext/standard/url_scanner_ex.h2
-rw-r--r--ext/standard/user_filters.c2
-rw-r--r--ext/standard/uuencode.c2
-rw-r--r--ext/standard/var.c2
-rw-r--r--ext/standard/var_unserializer.c2
-rw-r--r--ext/standard/versioning.c2
-rw-r--r--ext/sybase_ct/config.w327
-rw-r--r--ext/sybase_ct/php_sybase_ct.c2
-rw-r--r--ext/sybase_ct/php_sybase_ct.h2
-rw-r--r--ext/sysvmsg/php_sysvmsg.h2
-rw-r--r--ext/sysvmsg/sysvmsg.c2
-rw-r--r--ext/sysvsem/php_sysvsem.h2
-rw-r--r--ext/sysvsem/sysvsem.c2
-rw-r--r--ext/sysvshm/php_sysvshm.h2
-rw-r--r--ext/sysvshm/sysvshm.c2
-rw-r--r--ext/tidy/php_tidy.h2
-rw-r--r--ext/tidy/tidy.c2
-rw-r--r--ext/tokenizer/php_tokenizer.h2
-rw-r--r--ext/tokenizer/tests/token_get_all_variation14.phpt2
-rw-r--r--ext/tokenizer/tokenizer.c2
-rw-r--r--ext/tokenizer/tokenizer_data.c2
-rwxr-xr-xext/tokenizer/tokenizer_data_gen.sh2
-rw-r--r--ext/wddx/php_wddx.h2
-rw-r--r--ext/wddx/php_wddx_api.h2
-rw-r--r--ext/wddx/wddx.c2
-rw-r--r--ext/xml/compat.c2
-rw-r--r--ext/xml/expat_compat.h2
-rw-r--r--ext/xml/php_xml.h2
-rw-r--r--ext/xml/xml.c2
-rw-r--r--ext/xmlreader/php_xmlreader.c2
-rw-r--r--ext/xmlreader/php_xmlreader.h2
-rw-r--r--ext/xmlrpc/php_xmlrpc.h2
-rw-r--r--ext/xmlrpc/xmlrpc-epi-php.c2
-rw-r--r--ext/xmlwriter/php_xmlwriter.c2
-rw-r--r--ext/xmlwriter/php_xmlwriter.h2
-rw-r--r--ext/xsl/php_xsl.c2
-rw-r--r--ext/xsl/php_xsl.h2
-rw-r--r--ext/xsl/tests/bug49634.phpt105
-rw-r--r--ext/xsl/tests/bug49634.xml1
-rw-r--r--ext/xsl/xsl_fe.h2
-rw-r--r--ext/xsl/xsltprocessor.c5
-rw-r--r--ext/zip/php_zip.c4
-rw-r--r--ext/zip/php_zip.h2
-rw-r--r--ext/zlib/php_zlib.h2
-rw-r--r--ext/zlib/tests/gzeof_variation1.phpt2
-rw-r--r--ext/zlib/tests/gzfile_basic.phpt4
-rw-r--r--ext/zlib/tests/gzfile_basic2.phpt4
-rw-r--r--ext/zlib/tests/gzopen_basic2.phpt2
-rw-r--r--ext/zlib/tests/gzputs_basic.phpt2
-rw-r--r--ext/zlib/tests/gzread_variation1.phpt2
-rw-r--r--ext/zlib/tests/gzwrite_basic.phpt2
-rw-r--r--ext/zlib/tests/gzwrite_error.phpt2
-rw-r--r--ext/zlib/tests/gzwrite_error2.phpt2
-rw-r--r--ext/zlib/tests/readgzfile_basic.phpt2
-rw-r--r--ext/zlib/tests/readgzfile_basic2.phpt2
-rw-r--r--ext/zlib/tests/zlib_wrapper_fflush_basic.phpt2
-rw-r--r--ext/zlib/tests/zlib_wrapper_ftruncate_basic.phpt2
-rw-r--r--ext/zlib/zlib.c2
-rw-r--r--ext/zlib/zlib_filter.c2
-rw-r--r--ext/zlib/zlib_fopen_wrapper.c2
-rw-r--r--main/SAPI.c45
-rw-r--r--main/SAPI.h2
-rw-r--r--main/fopen_wrappers.c2
-rw-r--r--main/fopen_wrappers.h2
-rw-r--r--main/getopt.c2
-rw-r--r--main/internal_functions_nw.c2
-rw-r--r--main/internal_functions_win32.c2
-rw-r--r--main/main.c21
-rw-r--r--main/network.c2
-rw-r--r--main/output.c2
-rw-r--r--main/php.h2
-rw-r--r--main/php_compat.h2
-rw-r--r--main/php_content_types.c2
-rw-r--r--main/php_content_types.h2
-rw-r--r--main/php_getopt.h2
-rw-r--r--main/php_globals.h2
-rw-r--r--main/php_ini.c108
-rw-r--r--main/php_ini.h2
-rw-r--r--main/php_main.h2
-rw-r--r--main/php_memory_streams.h2
-rw-r--r--main/php_network.h2
-rw-r--r--main/php_open_temporary_file.c2
-rw-r--r--main/php_open_temporary_file.h2
-rw-r--r--main/php_output.h2
-rw-r--r--main/php_reentrancy.h2
-rw-r--r--main/php_scandir.c2
-rw-r--r--main/php_scandir.h2
-rw-r--r--main/php_sprintf.c2
-rw-r--r--main/php_streams.h2
-rw-r--r--main/php_syslog.h2
-rw-r--r--main/php_ticks.c2
-rw-r--r--main/php_ticks.h2
-rw-r--r--main/php_variables.c2
-rw-r--r--main/php_variables.h2
-rw-r--r--main/php_version.h6
-rw-r--r--main/reentrancy.c2
-rw-r--r--main/rfc1867.c2
-rw-r--r--main/rfc1867.h2
-rw-r--r--main/snprintf.c2
-rw-r--r--main/snprintf.h2
-rw-r--r--main/spprintf.c2
-rw-r--r--main/spprintf.h2
-rw-r--r--main/streams/cast.c2
-rw-r--r--main/streams/filter.c2
-rw-r--r--main/streams/glob_wrapper.c2
-rw-r--r--main/streams/memory.c2
-rw-r--r--main/streams/mmap.c2
-rw-r--r--main/streams/php_stream_context.h2
-rw-r--r--main/streams/php_stream_filter_api.h2
-rw-r--r--main/streams/php_stream_glob_wrapper.h2
-rw-r--r--main/streams/php_stream_mmap.h2
-rw-r--r--main/streams/php_stream_plain_wrapper.h2
-rw-r--r--main/streams/php_stream_transport.h2
-rw-r--r--main/streams/php_stream_userspace.h2
-rw-r--r--main/streams/php_streams_int.h2
-rw-r--r--main/streams/plain_wrapper.c14
-rw-r--r--main/streams/streams.c2
-rw-r--r--main/streams/transports.c2
-rw-r--r--main/streams/userspace.c2
-rw-r--r--main/streams/xp_socket.c4
-rw-r--r--main/strlcat.c2
-rw-r--r--main/strlcpy.c2
-rw-r--r--main/win32_internal_function_disabled.h2
-rw-r--r--main/win95nt.h2
-rwxr-xr-xmakedist2
-rw-r--r--netware/start.c2
-rw-r--r--php.ini-development35
-rw-r--r--php.ini-production35
-rwxr-xr-xrun-tests.php4
-rw-r--r--sapi/aolserver/aolserver.c2
-rw-r--r--sapi/apache/libpre.c2
-rw-r--r--sapi/apache/mod_php5.c2
-rw-r--r--sapi/apache/mod_php5.h2
-rw-r--r--sapi/apache/php_apache.c2
-rw-r--r--sapi/apache/php_apache_http.h2
-rw-r--r--sapi/apache/sapi_apache.c2
-rw-r--r--sapi/apache2filter/apache_config.c2
-rw-r--r--sapi/apache2filter/php_apache.h2
-rw-r--r--sapi/apache2filter/php_functions.c2
-rw-r--r--sapi/apache2filter/sapi_apache2.c2
-rw-r--r--sapi/apache2handler/apache_config.c2
-rw-r--r--sapi/apache2handler/mod_php5.c2
-rw-r--r--sapi/apache2handler/php_apache.h2
-rw-r--r--sapi/apache2handler/php_functions.c2
-rw-r--r--sapi/apache2handler/sapi_apache2.c2
-rw-r--r--sapi/apache_hooks/mod_php5.c2
-rw-r--r--sapi/apache_hooks/mod_php5.h2
-rw-r--r--sapi/apache_hooks/php_apache.c2
-rw-r--r--sapi/apache_hooks/sapi_apache.c2
-rw-r--r--sapi/caudium/caudium.c2
-rw-r--r--sapi/cgi/cgi_main.c10
-rw-r--r--sapi/cgi/fastcgi.c2
-rw-r--r--sapi/cgi/fastcgi.h2
-rw-r--r--sapi/cli/cli.h2
-rw-r--r--sapi/cli/php.1.in11
-rw-r--r--sapi/cli/php_cli.c4
-rw-r--r--sapi/cli/php_cli_process_title.c2
-rw-r--r--sapi/cli/php_cli_process_title.h2
-rw-r--r--sapi/cli/php_cli_server.c117
-rw-r--r--sapi/cli/php_cli_server.h2
-rw-r--r--sapi/cli/ps_title.c2
-rw-r--r--sapi/cli/ps_title.h2
-rw-r--r--sapi/cli/tests/php_cli_server_019.phpt68
-rw-r--r--sapi/continuity/capi.c2
-rw-r--r--sapi/embed/php_embed.c2
-rw-r--r--sapi/embed/php_embed.h2
-rw-r--r--sapi/fpm/fpm/events/devpoll.c2
-rw-r--r--sapi/fpm/fpm/events/devpoll.h2
-rw-r--r--sapi/fpm/fpm/events/epoll.c2
-rw-r--r--sapi/fpm/fpm/events/epoll.h2
-rw-r--r--sapi/fpm/fpm/events/kqueue.c2
-rw-r--r--sapi/fpm/fpm/events/kqueue.h2
-rw-r--r--sapi/fpm/fpm/events/poll.c2
-rw-r--r--sapi/fpm/fpm/events/poll.h2
-rw-r--r--sapi/fpm/fpm/events/port.c2
-rw-r--r--sapi/fpm/fpm/events/port.h2
-rw-r--r--sapi/fpm/fpm/events/select.c2
-rw-r--r--sapi/fpm/fpm/events/select.h2
-rw-r--r--sapi/fpm/fpm/fastcgi.c2
-rw-r--r--sapi/fpm/fpm/fastcgi.h2
-rw-r--r--sapi/fpm/fpm/fpm_conf.c3
-rw-r--r--sapi/fpm/fpm/fpm_conf.h1
-rw-r--r--sapi/fpm/fpm/fpm_env.c4
-rw-r--r--sapi/fpm/fpm/fpm_main.c6
-rw-r--r--sapi/fpm/php-fpm.conf.in9
-rw-r--r--sapi/isapi/php5isapi.c2
-rw-r--r--sapi/litespeed/lsapi_main.c6
-rw-r--r--sapi/litespeed/lsapidef.h2
-rw-r--r--sapi/litespeed/lsapilib.c2
-rw-r--r--sapi/litespeed/lsapilib.h2
-rw-r--r--sapi/milter/php_milter.c4
-rw-r--r--sapi/nsapi/nsapi.c2
-rw-r--r--sapi/phttpd/php_phttpd.h2
-rw-r--r--sapi/phttpd/phttpd.c2
-rw-r--r--sapi/pi3web/pi3web_sapi.c2
-rw-r--r--sapi/roxen/roxen.c2
-rw-r--r--sapi/thttpd/php_thttpd.h2
-rw-r--r--sapi/thttpd/thttpd.c2
-rw-r--r--sapi/tux/php_tux.c2
-rw-r--r--sapi/webjames/php_webjames.h2
-rw-r--r--sapi/webjames/webjames.c2
-rw-r--r--tests/classes/autoload_021.phpt13
-rw-r--r--tests/classes/bug65768.phpt36
-rw-r--r--tests/lang/bug24640.phpt1
-rw-r--r--tests/lang/operators/bitwiseShiftLeft_variationStr.phpt842
-rw-r--r--tests/lang/operators/bitwiseShiftLeft_variationStr2.phpt18
-rw-r--r--tests/lang/operators/bitwiseShiftRight_variationStr.phpt54
-rw-r--r--tests/lang/operators/bitwiseShiftRight_variationStr2.phpt18
-rw-r--r--tests/security/open_basedir_linkinfo.phpt1
-rw-r--r--tests/security/open_basedir_readlink.phpt1
-rw-r--r--tests/strings/001.phpt19
-rw-r--r--win32/build/config.w322
-rw-r--r--win32/build/deplister.c2
-rw-r--r--win32/build/libs_version.txt6
-rw-r--r--win32/globals.c2
-rw-r--r--win32/grp.h2
-rw-r--r--win32/php_win32_globals.h2
-rw-r--r--win32/select.c2
-rw-r--r--win32/select.h2
-rw-r--r--win32/sockets.c2
-rw-r--r--win32/sockets.h2
-rw-r--r--win32/syslog.h2
-rw-r--r--win32/time.h2
-rw-r--r--win32/winutil.c2
-rw-r--r--win32/winutil.h2
1252 files changed, 31196 insertions, 11281 deletions
diff --git a/.gitignore b/.gitignore
index cf615c6e92..8d0e7565f2 100644
--- a/.gitignore
+++ b/.gitignore
@@ -206,6 +206,8 @@ ext/pdo_sqlite/sqlite3.h
ext/pdo_sqlite/tests/*.db
ext/pdo_sqlite/tests/*.tmp
ext/phar/phar.phar
+ext/phar/phar.1
+ext/phar/phar.phar.1
ext/pspell/tests/*.tmp
ext/reflection/xml
ext/reflection/html
@@ -237,12 +239,14 @@ sapi/apache/libphp5.module
sapi/apache2handler/libphp5.module
sapi/apache_hooks/libphp5.module
sapi/cgi/php-cgi
+sapi/cgi/php-cgi.1
sapi/cli/php.1
sapi/fpm/php-fpm
sapi/fpm/php-fpm.1
sapi/fpm/init.d.php-fpm
sapi/fpm/php-fpm.conf
sapi/fpm/fpm/php-cgi
+sapi/phpdbg/phpdbg
scripts/php-config
scripts/phpize
scripts/man1/*.1
diff --git a/CODING_STANDARDS b/CODING_STANDARDS
index 5ceacdc4dc..bebc951452 100644
--- a/CODING_STANDARDS
+++ b/CODING_STANDARDS
@@ -59,8 +59,8 @@ Exceptions:
you're calling.
7. When commenting out code using a #if statement, do NOT use 0 only. Instead
- use "<svn username here>_0". For example, #if FOO_0, where FOO is your
- svn user foo. This allows easier tracking of why code was commented out,
+ use "<git username here>_0". For example, #if FOO_0, where FOO is your
+ git user foo. This allows easier tracking of why code was commented out,
especially in bundled libraries.
8. Do not define functions that are not available. For instance, if a
@@ -82,7 +82,7 @@ Exceptions:
library may need to control or free the memory, or when the memory in
question needs to survive between multiple requests.
-Naming Conventions
+User Functions/Methods Naming Conventions
------------------
1. Function names for user-level functions should be enclosed with in
@@ -163,6 +163,26 @@ Naming Conventions
'foobar'
'foo_bar'
+Internal Function Naming Convensions
+----------------------
+
+1. Functions that are part of the external API should be named
+ 'php_modulename_function()' to avoid symbol collision. They should be in
+ lowercase, with words underscore delimited. Exposed API must be defined
+ in 'php_modulename.h'.
+
+ PHPAPI char *php_session_create_id(PS_CREATE_SID_ARGS);
+
+ Unexposed module function should be static and should not be defined in
+ 'php_modulename.h'.
+
+ static int php_session_destroy(TSRMLS_D)
+
+2. Main module source file must be named 'modulename.c'.
+
+3. Header file that is used by other sources must be named 'php_modulename.h'.
+
+
Syntax and indentation
----------------------
@@ -181,9 +201,9 @@ Syntax and indentation
of PHP or one of its standard modules, please maintain the K&R
style. This applies to just about everything, starting with
indentation and comment styles and up to function declaration
- syntax. Also see Indentstyle_.
+ syntax. Also see Indentstyle.
-.. _Indentstyle: http://www.catb.org/~esr/jargon/html/I/indent-style.html
+ Indentstyle: http://www.catb.org/~esr/jargon/html/I/indent-style.html
3. Be generous with whitespace and braces. Keep one empty line between the
variable declaration section and the statements in a block, as well as
diff --git a/Makefile.global b/Makefile.global
index 05c5d151b7..40fadccbc8 100644
--- a/Makefile.global
+++ b/Makefile.global
@@ -115,6 +115,7 @@ clean:
find . -name \*.la -o -name \*.a | xargs rm -f
find . -name \*.so | xargs rm -f
find . -name .libs -a -type d|xargs rm -rf
+ find . -name \*.1 | xargs rm -f
rm -f libphp$(PHP_MAJOR_VERSION).la $(SAPI_CLI_PATH) $(SAPI_CGI_PATH) $(SAPI_MILTER_PATH) $(SAPI_LITESPEED_PATH) $(SAPI_FPM_PATH) $(OVERALL_TARGET) modules/* libs/*
distclean: clean
diff --git a/NEWS b/NEWS
index 0c8a15a5f9..bae6860dda 100644
--- a/NEWS
+++ b/NEWS
@@ -1,8 +1,199 @@
PHP NEWS
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
-?? ??? 2013, PHP 5.5.6
+?? ??? 2014, PHP 5.5.11
+
+- MySQLi:
+ . Fixed bug #66762i (Segfault in mysqli_stmt::bind_result() when link closed)
+ (Remi)
+
+- Mail:
+ . Fixed bug #66535 (Don't add newline after X-PHP-Originating-Script) (Tjerk)
+
+- cURL:
+ . Fixed bug #66109 (Can't reset CURLOPT_CUSTOMREQUEST to default behaviour) (Tjerk)
+
+- Core:
+ . Allow zero length comparison in substr_compare() (Tjerk)
+ . Fixed bug #60602 (proc_open() changes environment array) (Tjerk)
+
+?? ??? 2014, PHP 5.5.10
+
+- Core:
+ . Fixed Request #66574i (Allow multiple paths in php_ini_scanned_path). (Remi)
+
+- Date:
+ . Fixed bug #45528 (Allow the DateTimeZone constructor to accept timezones
+ per offset too). (Derick)
+
+- Fileinfo:
+ . Bug #66731 (file: infinite recursion) (CVE-2014-1943). (Remi)
+ . Fixed bug #66820 (out-of-bounds memory access in fileinfo). (Remi)
+
+- FPM:
+ . Added clear_env configuration directive to disable clearenv() call.
+ (Github PR# 598, Paul Annesley)
+
+- GD
+ . Fixed bug #66714 ( imageconvolution breakage). (Brad Daily)
+
+- JSON:
+ . Fixed bug #65753 (JsonSerializeable couldn't implement on module extension)
+ (chobieeee@php.net)
+
+- LDAP:
+ . Implemented ldap_modify_batch (https://wiki.php.net/rfc/ldap_modify_batch).
+ (Ondřej Hošek)
+
+- OPCache
+ . Added function opcache_is_script_cached(). (Danack)
+ . Added information about interned strings usage. (Terry, Julien, Dmitry)
+
+- Openssl:
+ . Fixed bug #66501 (Add EC key support to php_openssl_is_private_key).
+ (Mark Zedwood)
+
+- PCRE:
+ . Upgraded to PCRE 8.34. (Anatol)
+
+- Pgsql:
+ . Added warning for dangerous client encoding and remove possible injections
+ for pg_insert()/pg_update()/pg_delete()/pg_select(). (Yasuo)
+
+
+06 Feb 2014, PHP 5.5.9
+
+- Core:
+ . Fixed bug #66509 (copy() arginfo has changed starting from 5.4). (willfitch)
+
+- GD:
+ . Fixed bug #66356 (Heap Overflow Vulnerability in imagecrop()).
+ (Laruence, Remi)
+
+- OPCache:
+ . Fixed bug #66474 (Optimizer bug in constant string to boolean conversion).
+ (Dmitry)
+ . Fixed bug #66461 (PHP crashes if opcache.interned_strings_buffer=0).
+ (Dmitry)
+ . Fixed bug #66298 (ext/opcache/Optimizer/zend_optimizer.c has dos-style
+ ^M as lineend). (Laruence)
+
+- PDO_pgsql:
+ . Fixed bug #62479 (PDO-psql cannot connect if password contains
+spaces) (willfitch, iliaa)
+
+- Readline
+ . Fixed Bug #66412 (readline_clear_history() with libedit causes segfault after
+ #65714). (Remi)
+
+- Session
+ . Fixed bug #66469 (Session module is sending multiple set-cookie headers when
+ session.use_strict_mode=1) (Yasuo)
+ . Fixed bug #66481 (Segfaults on session_name()).
+ (cmcdermottroe at engineyard dot com, Yasuo)
+
+- Standard
+ . Fixed bug #66395 (basename function doesn't remove drive letter). (Anatol)
+
+- Sockets:
+ . Fixed bug #66381 (__ss_family was changed on AIX 5.3). (Felipe)
+
+- Zend Engine
+ . Fixed bug #66009 (Failed compilation of PHP extension with C++ std
+ library using VS 2012). (Anatol)
+
+09 Jan 2014, PHP 5.5.8
+
+- Core:
+ . Disallowed JMP into a finally block. (Laruence)
+ . Added validation of class names in the autoload process. (Dmitry)
+ . Fixed invalid C code in zend_strtod.c. (Lior Kaplan)
+ . Fixed ZEND_MM_MEM_TYPE=mmap_zero. (Dmitry, Tony)
+ . Fixed bug #66041 (list() fails to unpack yielded ArrayAccess object).
+ (Nikita)
+ . Fixed bug #65764 (generators/throw_rethrow FAIL with
+ ZEND_COMPILE_EXTENDED_INFO). (Nikita)
+ . Fixed bug #61645 (fopen and O_NONBLOCK). (Mike)
+ . Fixed bug #66218 (zend_register_functions breaks reflection). (Remi)
+
+- Date:
+ . Fixed bug #66060 (Heap buffer over-read in DateInterval) (CVE-2013-6712).
+ (Remi)
+ . Fixed bug #65768 (DateTimeImmutable::diff does not work). (Nikita Nefedov)
+
+- DOM:
+ . Fixed bug #65196 (Passing DOMDocumentFragment to DOMDocument::saveHTML()
+ Produces invalid Markup). (Mike)
+
+- Exif:
+ . Fixed bug #65873 (Integer overflow in exif_read_data()). (Stas)
+
+- Filter:
+ . Fixed bug #66229 (128.0.0.0/16 isn't reserved any longer). (Adam)
+
+- GD:
+ . Fixed bug #64405 (Use freetype-config for determining freetype2 dir(s)).
+ (Adam)
+
+- PDO_odbc:
+ . Fixed bug #66311 (Stack smashing protection kills PDO/ODBC queries).
+ (michael at orlitzky dot com)
+
+- MySQLi:
+ . Fixed bug #65486 (mysqli_poll() is broken on win x64). (Anatol)
+
+- OPCache:
+ . Fixed revalidate_path=1 behavior to avoid caching of symlinks values.
+ (Dmitry)
+ . Fixed Issue #140: "opcache.enable_file_override" doesn't respect
+ "opcache.revalidate_freq". (Dmitry).
+
+- SNMP:
+ . Fixed SNMP_ERR_TOOBIG handling for bulk walk operations. (Boris Lytochkin)
+
+- SOAP
+ . Fixed bug #66112 (Use after free condition in SOAP extension).
+ (martin dot koegler at brz dot gv dot at)
+
+- Sockets:
+ . Fixed bug #65923 (ext/socket assumes AI_V4MAPPED is defined). (Felipe)
+
+- XSL
+ . Fixed bug #49634 (Segfault throwing an exception in a XSL registered
+ function). (Mike)
+
+- ZIP:
+ . Fixed Bug #66321 (ZipArchive::open() ze_obj->filename_len not real). (Remi)
+
+12 Dec 2013, PHP 5.5.7
+
+- CLI server:
+ . Added some MIME types to the CLI web server (Chris Jones)
+ . Implemented FR #65917 (getallheaders() is not supported by the built-in web
+ server) - also implements apache_response_headers() (Andrea Faulds)
- Core:
+ . Fixed bug #66094 (unregister_tick_function tries to cast a Closure to a
+ string). (Laruence)
+ . Fixed bug #65969 (Chain assignment with T_LIST failure). (Dmitry)
+
+- OPCache
+ . Fixed bug #66176 (Invalid constant substitution). (Dmitry)
+ . Fixed bug #65915 (Inconsistent results with require return value). (Dmitry)
+ . Fixed bug #65559 (Opcache: cache not cleared if changes occur while
+ running). (Dmitry)
+
+- readline
+ . Fixed Bug #65714 (PHP cli forces the tty to cooked mode). (Remi)
+
+- Openssl:
+ . Fixed memory corruption in openssl_x509_parse() (CVE-2013-6420).
+ (Stefan Esser).
+
+14 Nov 2013, PHP 5.5.6
+
+- Core:
+ . Fixed bug #65947 (basename is no more working after fgetcsv in certain
+ situation). (Laruence)
. Improved performance of array_merge() and func_get_args() by eliminating
useless copying. (Dmitry)
. Fixed bug #65939 (Space before ";" breaks php.ini parsing).
@@ -14,13 +205,28 @@ PHP NEWS
- FPM:
. Changed default listen() backlog to 65535. (Tony)
+- JSON
+ . Fixed whitespace part of bug #64874 ("json_decode handles whitespace and
+ case-sensitivity incorrectly"). (Andrea Faulds)
+
+- MySQLi:
+ . Fixed bug #66043 (Segfault calling bind_param() on mysqli). (Laruence)
+
- OPcache
. Increased limit for opcache.max_accelerated_files to 1,000,000. (Chris)
+ . Fixed issue #115 (path issue when using phar). (Dmitry)
+ . Fixed issue #149 (Phar mount points not working with OPcache enabled).
+ (Dmitry)
- ODBC
. Fixed bug #65950 (Field name truncation if the field name is bigger than
32 characters). (patch submitted by: michael dot y at zend dot com, Yasuo)
+- PDO:
+ . Fixed bug #66033 (Segmentation Fault when constructor of PDO statement
+ throws an exception). (Laruence)
+ . Fixed bug 65946 (sql_parser permanently converts values bound to strings)
+
- Standard:
. Fixed bug #64760 (var_export() does not use full precision for floating-point
numbers) (Yasuo)
@@ -71,7 +277,6 @@ PHP NEWS
imap). (ryotakatsuki at gmail dot com)
- OPcache:
- . Fixed issue #115 (path issue when using phar). (Laruence)
. Added support for GNU Hurd. (Svante Signell)
. Added function opcache_compile_file() to load PHP scripts into cache
without execution. (Julien)
@@ -465,6 +670,12 @@ PHP NEWS
CURLOPT_RTSP_REQUEST, CURLOPT_RESOLVE, CURLOPT_ACCEPT_ENCODING,
CURLOPT_TRANSFER_ENCODING, CURLOPT_DNS_SERVERS and CURLOPT_USE_SSL.
(Pierrick)
+ . Added new functions curl_escape, curl_multi_setopt, curl_multi_strerror
+ curl_pause, curl_reset, curl_share_close, curl_share_init,
+ curl_share_setopt curl_strerror and curl_unescape. (Pierrick)
+ . Addes new curl options CURLOPT_TELNETOPTIONS, CURLOPT_GSSAPI_DELEGATION,
+ CURLOPT_ACCEPTTIMEOUT_MS, CURLOPT_SSL_OPTIONS, CURLOPT_TCP_KEEPALIVE,
+ CURLOPT_TCP_KEEPIDLE and CURLOPT_TCP_KEEPINTVL. (Pierrick)
. Fixed bug #55635 (CURLOPT_BINARYTRANSFER no longer used. The constant
still exists for backward compatibility but is doing nothing). (Pierrick)
. Fixed bug #54995 (Missing CURLINFO_RESPONSE_CODE support). (Pierrick)
@@ -472,12 +683,6 @@ PHP NEWS
- DateTime
. Added DateTimeImmutable - a variant of DateTime that only returns the
modified state instead of changing itself. (Derick)
- . Added new functions curl_escape, curl_multi_setopt, curl_multi_strerror
- curl_pause, curl_reset, curl_share_close, curl_share_init,
- curl_share_setopt curl_strerror and curl_unescape. (Pierrick)
- . Addes new curl options CURLOPT_TELNETOPTIONS, CURLOPT_GSSAPI_DELEGATION,
- CURLOPT_ACCEPTTIMEOUT_MS, CURLOPT_SSL_OPTIONS, CURLOPT_TCP_KEEPALIVE,
- CURLOPT_TCP_KEEPIDLE and CURLOPT_TCP_KEEPINTVL. (Pierrick)
. Fixed bug #64825 (Invalid free when unserializing DateTimeZone).
(Anatol)
. Fixed bug #64359 (strftime crash with VS2012). (Anatol)
diff --git a/README.EXTENSIONS b/README.EXTENSIONS
index 06d6cdd85f..e802af8329 100644
--- a/README.EXTENSIONS
+++ b/README.EXTENSIONS
@@ -1,3 +1,11 @@
+This file describes extension module API details. Refer to
+README.EXT_SKEL to create extension skeleton files. Refer to
+Hacker's Guide for PHP internals.
+
+http://www.php.net/manual/en/internals2.php
+
+
+
Between PHP 4.0.6 and 4.1.0, the Zend module struct changed in a way
that broke both source and binary compatibility. If you are
maintaining a third party extension, here's how to update it:
diff --git a/README.EXT_SKEL b/README.EXT_SKEL
index d44fcc5c6a..42df006d24 100644
--- a/README.EXT_SKEL
+++ b/README.EXT_SKEL
@@ -45,12 +45,29 @@ HOW TO USE IT
--proto=filename.
+SOURCE AND HEADER FILE NAME
+
+ ./ext_skel generates 'module_name.c' and 'php_module_name.h' as main source
+ and header files. Keep these names.
+
+ Module functions (User functions) must be named
+
+ module_name_function()
+
+ When you need to expose module functions to other modules, expose functions
+ strictly needed by others. Exposed internal function must be named
+
+ php_module_name_function()
+
+ See also CODING_STANDARDS.
+
+
FORMAT OF FUNCTION DEFINITIONS FILE
All the definitions must be on one line. In it's simplest form, it's just
the function name, e.g.
- my_function
+ module_name_function
but then you'll be left with an almost empty function body without any
argument handling.
@@ -72,8 +89,9 @@ FORMAT OF FUNCTION DEFINITIONS FILE
An example:
- my_function(int arg1, int arg2 [, int arg3 [, int arg4]]) this is my 1st
+ module_name_function(int arg1, int arg2 [, int arg3 [, int arg4]])
+ Arguments arg1 and arg2 are required.
Arguments arg3 and arg4 are optional.
If possible, the function definition should also contain it's return type
@@ -133,15 +151,15 @@ EXAMPLE
The following _one_ line
- bool my_drawtext(resource image, string text, resource font, int x, int y [, int color])
+ bool module_name_drawtext(resource image, string text, resource font, int x, int y [, int color])
will create this function definition for you (note that there are a few
question marks to be replaced by you, and you must of course add your own
value definitions too):
-/* {{{ proto bool my_drawtext(resource image, string text, resource font, int x, int y [, int color])
+/* {{{ proto bool module_name_drawtext(resource image, string text, resource font, int x, int y [, int color])
*/
-PHP_FUNCTION(my_drawtext)
+PHP_FUNCTION(module_name_drawtext)
{
char *text = NULL;
int argc = ZEND_NUM_ARGS();
@@ -164,7 +182,7 @@ PHP_FUNCTION(my_drawtext)
ZEND_FETCH_RESOURCE(???, ???, font, font_id, "???", ???_rsrc_id);
}
- php_error(E_WARNING, "my_drawtext: not yet implemented");
+ php_error(E_WARNING, "module_name_drawtext: not yet implemented");
}
/* }}} */
diff --git a/README.GIT-RULES b/README.GIT-RULES
index 6e90aa97b6..3df9d17bcd 100644
--- a/README.GIT-RULES
+++ b/README.GIT-RULES
@@ -69,9 +69,11 @@ The next few rules are more of a technical nature::
branches) an empty merge should be done.
2. All news updates intended for public viewing, such as new features,
- bug fixes, improvements, etc., should go into the NEWS file of the
- *first* to be released version with the given change. In other words
- any NEWS file change only needs to done in one branch.
+ bug fixes, improvements, etc., should go into the NEWS file of *any
+ stable release* version with the given change. In other words,
+ news about a bug fix which went into PHP-5.4, PHP-5.5 and master
+ should be noted in both PHP-5.4/NEWS and PHP-5.5/NEWS but
+ not master, which is not a public released version yet.
3. Do not commit multiple file and dump all messages in one commit. If you
modified several unrelated files, commit each group separately and
diff --git a/README.RELEASE_PROCESS b/README.RELEASE_PROCESS
index 06f4724f7a..21305f2993 100644
--- a/README.RELEASE_PROCESS
+++ b/README.RELEASE_PROCESS
@@ -8,15 +8,16 @@ General notes and tips
1. Do not release on Fridays, Saturdays or Sundays
because the sysadmins can not upgrade stuff then.
-2. Package the day before a release. So if the release is to be on Thursday,
-package on Wednesday.
+2. Package two days before a release. So if the release is to be on Thursday,
+package on Tuesday. Think about timezones as well.
3. Ensure that Windows builds will work before packaging
-4. Follow all steps to the letter. When unclear ask previous RM's (Derick/Ilia)
-before proceeding. Ideally make sure that for the first releases one of the
-previous RM's is around to answer questions. For the steps related to the
-php/QA/bug websites try to have someone from the webmaster team (Bjori) on hand.
+4. Follow all steps to the letter. When unclear ask previous RM's (David/Julien/
+Johannes/Stas/Derick/Ilia) before proceeding. Ideally make sure that for the
+first releases one of the previous RM's is around to answer questions. For the
+steps related to the php/QA/bug websites try to have someone from the webmaster
+team (Bjori) on hand.
5. Verify the tags to be extra sure everything was tagged properly.
@@ -50,37 +51,47 @@ Rolling a non stable release (alpha/beta/RC)
2. run the "scripts/dev/credits" script in php-src and commit the changes in the
credits files in ext/standard.
-3. Checkout the release branch for this release (e.g., PHP-5.4.2).
+3. Checkout the release branch for this release (e.g., PHP-5.4.2) from the main branch.
4. Bump the version numbers in ``main/php_version.h``, ``configure.in`` and possibly ``NEWS``.
-Do not use abbreviations for alpha and beta.
+Do not use abbreviations for alpha and beta. Do not use dashes, you should
+``#define PHP_VERSION "5.4.22RC1"`` and not ``#define PHP_VERSION "5.4.22-RC1"``
-5. Commit these changes to the branch with ``git commit -a``.
+5. Compile and make test, with and without ZTS, using the right Bison version
+(for example, for 5.5, Bison 2.4.1 is used)
-6. Tag the repository with the version, e.g.:
+6. Check ./sapi/cli/php -v output for version matching.
+
+7. If all is right, commit the changes to the release branch with ``git commit -a``.
+
+8. Tag the repository release branch with the version, e.g.:
``git tag -u YOURKEYID php-5.4.2RC2``
-7. Push the changes to the main repo:
+9. Bump the version numbers in ``main/php_version.h``, ``configure.in`` and ``NEWS``
+in the *main* branch (PHP-5.4 for example) to prepare for the **next** version.
+F.e. if the RC is "5.4.1RC1" then the new one should be "5.4.2-dev" - regardless if we get
+a new RC or not. This is to make sure ``version_compare()`` can correctly work.
+Commit the changes to the main branch.
+
+10. Push the changes to the main repo, the tag, the main branch and the release branch :
``git push --tags origin HEAD``
+``git push origin {main branch}``
+``git push origin {release branch}``
-8. run: ``./makedist 5.4.2RC2``, this will export the tree, create configure
-and build three tarballs (gz,bz2 and xz). Make sure you use the same GNU Bison
-version as snaps. Recent bison version are known to break ZTS.
+11. run: ``PHPROOT=. ./makedist 5.4.2RC2``, this will export the tree, create configure
+and build three tarballs (gz, bz2 and xz).
-9. Copy those three tarballs to www.php.net, in your homedir there should be a
+12. Copy those tarballs (scp, rsync) to downloads.php.net, in your homedir there should be a
directory "downloads/". Copy them into there, so that the system can generate
-MD5 sums. If you do not have this directory, talk to Derick.
+MD5 sums. If you do not have this directory, talk to Derick or Dan.
-10. Now the RC can be found on http://downloads.php.net/yourname,
+13. Now the RC can be found on http://downloads.php.net/yourname,
f.e. http://downloads.php.net/derick/
-11. Once the release has been tagged, contact the PHP Windows development team
+14. Once the release has been tagged, contact the PHP Windows development team
(internals-win@lists.php.net) so that Windows binaries can be created. Once
those are made, they should be placed into the same directory as the source snapshots.
-12. Notify the documentation team if documentations for new features are
-not yet available but a stable release is imminent.
-
Getting the non stable release (alpha/beta/RC) announced
--------------------------------------------------------
@@ -90,10 +101,10 @@ pointing out "the location of the release" and "the possible release date of
either the next RC, or the final release".
2. Send an email (see example here http://news.php.net/php.pear.qa/5201) **To**
-``php-qa@lists.php.net`` and ``primary-qa-tests@lists.php.net``.
+``php-qa@lists.php.net`` and ``primary-qa-tester@lists.php.net``.
This email is to notify the selected projects about a new release so that they
can make sure their projects keep working. Make sure that you have been setup
-as a moderator for ``primary-qa-tests@lists.php.net`` by having someone (Wez,
+as a moderator for ``primary-qa-tester@lists.php.net`` by having someone (Hannes, Dan,
Derick) run the following commands for you:
``ssh lists.php.net``
@@ -109,9 +120,9 @@ Derick) run the following commands for you:
Note: Remember to update the MD5 checksum information.
-4. Update ``php.git/include/version.inc`` (x=major version number)
+4. Update ``web/php.git/include/version.inc`` (x=major version number)
- a. ``$PHP_x_RC`` = "5.4.0RC1"
+ a. ``$PHP_x_RC`` = "5.4.0RC1" (should be set to "false" before)
b. ``$PHP_x_RC_DATE`` = "06 September 2007"
@@ -122,70 +133,61 @@ Derick) run the following commands for you:
6. For the first RC, write the doc team (phpdoc@lists.php.net) about updating the
INSTALL and win32/install.txt files which are generated from the PHP manual sources.
-7. Publish the announce on www.php.net as well (for all releases, alpha, RCs or other)
-
Rolling a stable release
------------------------
-1. Check windows snapshot builder logs (http://snaps.php.net/win32/snapshot-STABLE.log f.e.)
-
-2. Bump the version numbers in ``main/php_version.h``, ``configure.in`` and possibly ``NEWS``.
+1. Checkout your release branch, you should have created when releasing previous RC
+and bump the version numbers in ``main/php_version.h``, ``configure.in`` and possibly ``NEWS``.
-3. **Merge** all related sections in NEWS (f.e. merge the 5.4.1RC1 and 5.4.0 sections)
+2. If a CVE commit needs to be merged to the release, then have it committed to
+the base branches and merged upwards as usual (f.e commit the CVE fix to 5.3,
+merge to 5.4, 5.5 etc...). Then you can cherry-pick it in your release branch.
+Don't forget to update NEWS manually in an extra commit then.
-4. Commit those changes
+3. Commit those changes
-5. run the "scripts/dev/credits" script in php-src and commit the changes in the
+4. run the "scripts/dev/credits" script in php-src and commit the changes in the
credits files in ext/standard.
-6. tag the repository with the version f.e. "``git tag -s php-5.4.1``"
-(of course, you need to change that to the version you're rolling an RC for).
-When making 5.X release, you need to tag the Zend directory separately!!
+5. Compile and make test, with and without ZTS, using the right Bison version
+(for example, for 5.5, Bison 2.4.1 is used)
-7. Bump up the version numbers in ``main/php_version.h``, ``configure.in`` and
-possibly ``NEWS`` again, to the **next** version. F.e. if the release candidate
-was "5.4.1RC1" then the new one should be "5.4.1RC2-dev" - regardless if we get
-a new RC or not. This is to make sure ``version_compare()`` can correctly work.
+6. Check ./sapi/cli/php -v output for version matching.
-8. Commit those changes
+7. tag the repository with the version f.e. "``git tag -s php-5.4.1``"
-9. Log in onto the snaps box and go into the correct tree (f.e. the PHP-5.4
-branch if you're rolling 5.5.x releases).
+8. Push the tag f.e. "``git push origin php-5.4.1``"
-10. You do not have to update the tree, but of course you can with "``git pull
-origin <branch>``".
+9. run: ``PHPROOT=. ./makedist php 5.4.1``, this will export the tag, create configure
+and build three tarballs (gz, bz2 and xz).
+Check if the pear files are updated (phar).
-11. run: ``./makedist php 5.4.1``, this will export the tree, create configure
-and build two tarballs (one gz and one bz2).
+10. Generate the GPG signature files for the archives.
+ ``gpg -u YOUREMAIL --armor --detach-sign php-X.Y.Z.tar.xxx``
-12. Commit those two tarballs to web/php-distributions.git, then update the git
- submodule reference in web/php.git:
- git submodule init;
+11. Commit and push all the tarballs and signature files to web/php-distributions.git,
+ then update the git submodule reference in web/php.git:
+ ``git submodule init;
git submodule update;
cd distributions;
git pull origin master;
cd ..;
git commit distributions;
- git push;
-
-13. Once the release has been tagged, contact the PHP Windows development team
-(internals-win@lists.php.net) so that Windows binaries can be created. Once
-those are made, they should be committed to SVN too.
+ git push;``
+This is to fetch the last commit id from php-distributions.git and commit this
+last commit id to web/php.git, then, mirrors will now sync
-14. Check if the pear files are updated (phar for 5.1+ or run pear/make-pear-bundle.php with 4.4)
-
-15. When making a final release, also remind the PHP Windows development team
-(internals-win@lists.php.net) to prepare the installer packages for Win32.
-
-16. Make sure proper documentation exists for all new features/changes.
-Coordinate the release with the PHP Documentation team.
+12. Once the release has been tagged, contact the PHP Windows development team
+(internals-win@lists.php.net) so that Windows binaries can be created.
Getting the stable release announced
------------------------------------
1. Run the bumpRelease script for phpweb on your local checkout
- a. ``php bin/bumpRelease 5`` (or ``php bin/bumpRelease 4`` for PHP4)
+ a. ``php bin/bumpRelease 5`` to create the release file (releases/x_y_z.php)
+ The release announcement file should list in detail security fixes and
+ changes in behavior (whether due to a bug fix or not).
b. In case multiple PHP minor versions are in active development you have
to manually copy the old information to include/releases.inc
@@ -205,7 +207,13 @@ Getting the stable release announced
f. if the windows builds aren't ready yet prefix the "windows" key with a dot (".windows")
-3. Update the ChangeLog file for the given major version
+3. Update phpweb/include/releases.php with the old release info
+ (updates the download archives)
+
+4. Update php-qa/include/release-qa.php and add the next version as an QARELEASE
+ (prepare for next RC)
+
+5. Update the ChangeLog file for the given major version
f.e. ``ChangeLog-5.php`` from the NEWS file
a. go over the list and put every element on one line
@@ -225,19 +233,10 @@ f.e. ``ChangeLog-5.php`` from the NEWS file
IV. ``s/Fixed PECL bug #\([0-9]\+\)/<?php peclbugfix(\1); ?>/``
V. ``s/FR #\([0-9]\+\)/FR <?php bugl(\1); ?>/``
+
+ e. You may want to try php-web/bin/news2html to automate this task
-4. ``cp releases/5_4_0.php releases/5_4_1.php``
-
-5. ``git add releases/5_4_1.php``
-
-6. Update the ``releases/*.php`` file with relevant data. The release
-announcement file should list in detail:
-
- a. security fixes,
-
- b. changes in behavior (whether due to a bug fix or not)
-
-7. Add a short notice to phpweb stating that there is a new release, and
+6. Add a short notice to phpweb stating that there is a new release, and
highlight the major important things (security fixes) and when it is important
to upgrade.
@@ -245,7 +244,11 @@ to upgrade.
b. Add the content for the news entry
-8. Commit all the changes.
+7. **Check mirrors have been synced before announcing or pushing news**
+ Try, f.e. http://www.php.net/get/php-5.5.1.tar.bz2/from/a/mirror
+ Try several mirrors, mirrors may update slowly (may take an hour)
+
+8. Commit all the changes to their respective git repos
9. Wait an hour or two, then send a mail to php-announce@lists.php.net,
php-general@lists.php.net and internals@lists.php.net with a text similar to
diff --git a/README.SUBMITTING_PATCH b/README.SUBMITTING_PATCH
index 63b7156f10..ee8e6bbaef 100644
--- a/README.SUBMITTING_PATCH
+++ b/README.SUBMITTING_PATCH
@@ -50,6 +50,17 @@ Please make the mail subject prefix "[PATCH]". If attaching a patch,
ensure it has a file extension of ".txt". This is because only MIME
attachments of type 'text/*' are accepted.
+The preferred way to propose PHP patch is sending pull request from
+github.
+
+https://github.com/php/php-src
+
+Fork the official PHP repository and send a pull request. A
+notification will be sent to the pull request mailing list. Sending a
+note to PHP Internals list (internals@lists.php.net) may help getting
+more feedback and quicker turnaround. You can also add pull requests
+to bug reports at http://bugs.php.net/.
+
PHP Documentation Patches
-------------------------
diff --git a/README.TESTING b/README.TESTING
index 5e0ee11be0..3ed5e6b2ab 100644
--- a/README.TESTING
+++ b/README.TESTING
@@ -2,7 +2,7 @@
------------------
Failed tests usually indicate a problem with your local system setup
and not within PHP itself (at least for official PHP release versions).
-You may decide to automaticaly submit a test summary to our QA workflow
+You may decide to automatically submit a test summary to our QA workflow
at the end of a test run.
Please do *not* submit a failed test as a bug or ask for help on why
it failed on your system without providing substantial backup information
diff --git a/TSRM/tsrm_config.w32.h b/TSRM/tsrm_config.w32.h
index 14c6443a03..1443e7cca9 100644
--- a/TSRM/tsrm_config.w32.h
+++ b/TSRM/tsrm_config.w32.h
@@ -2,6 +2,7 @@
#define TSRM_CONFIG_W32_H
#include <../main/config.w32.h>
+#include "Zend/zend_config.w32.h"
#define HAVE_UTIME 1
#define HAVE_ALLOCA 1
@@ -11,12 +12,4 @@
#include <stdlib.h>
#include <crtdbg.h>
-#undef inline
-#ifdef ZEND_WIN32_FORCE_INLINE
-# define inline __forceinline
-#else
-# define inline
-#endif
-
-
#endif
diff --git a/TSRM/tsrm_config_common.h b/TSRM/tsrm_config_common.h
index 83b6b9b02c..eba9c13488 100644
--- a/TSRM/tsrm_config_common.h
+++ b/TSRM/tsrm_config_common.h
@@ -2,7 +2,7 @@
#define TSRM_CONFIG_COMMON_H
#ifndef __CYGWIN__
-# if WINNT|WIN32
+# ifdef _WIN32
# define TSRM_WIN32
# endif
#endif
diff --git a/TSRM/tsrm_nw.c b/TSRM/tsrm_nw.c
index d9963faad1..8d591c0746 100644
--- a/TSRM/tsrm_nw.c
+++ b/TSRM/tsrm_nw.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/TSRM/tsrm_nw.h b/TSRM/tsrm_nw.h
index 1f93bd535d..ba03744a30 100644
--- a/TSRM/tsrm_nw.h
+++ b/TSRM/tsrm_nw.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/TSRM/tsrm_virtual_cwd.c b/TSRM/tsrm_virtual_cwd.c
index 3e211fa54f..f7a8ca5ec5 100644
--- a/TSRM/tsrm_virtual_cwd.c
+++ b/TSRM/tsrm_virtual_cwd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/TSRM/tsrm_virtual_cwd.h b/TSRM/tsrm_virtual_cwd.h
index 8aac4aa267..81efb0f8a3 100644
--- a/TSRM/tsrm_virtual_cwd.h
+++ b/TSRM/tsrm_virtual_cwd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/TSRM/tsrm_win32.c b/TSRM/tsrm_win32.c
index 2ec97be011..d8f8365112 100644
--- a/TSRM/tsrm_win32.c
+++ b/TSRM/tsrm_win32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/TSRM/tsrm_win32.h b/TSRM/tsrm_win32.h
index c77f69c7f1..dc5a3999dd 100644
--- a/TSRM/tsrm_win32.h
+++ b/TSRM/tsrm_win32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/UPGRADING b/UPGRADING
index 43e4118b21..7ede420883 100755
--- a/UPGRADING
+++ b/UPGRADING
@@ -299,6 +299,9 @@ PHP 5.5 UPGRADE NOTES
- IntlDateFormatter::getTimeZone()
- IntlDateFormatter::setTimeZone()
+- LDAP:
+ - ldap_modify_batch() (5.5.10)
+
- Sockets:
- socket_sendmsg()
- socket_recvmsg()
diff --git a/Zend/Makefile.am b/Zend/Makefile.am
index 6417f3eb14..cea5c17fa2 100644
--- a/Zend/Makefile.am
+++ b/Zend/Makefile.am
@@ -10,7 +10,7 @@ libZend_la_SOURCES=\
zend_ini_parser.y zend_ini_scanner.l \
zend_alloc.c zend_compile.c zend_constants.c zend_dynamic_array.c \
zend_execute.c zend_execute_API.c zend_highlight.c zend_llist.c \
- zend_opcode.c zend_operators.c zend_ptr_stack.c zend_stack.c \
+ zend_vm_opcodes.c zend_opcode.c zend_operators.c zend_ptr_stack.c zend_stack.c \
zend_variables.c zend.c zend_API.c zend_extensions.c zend_hash.c \
zend_list.c zend_indent.c zend_builtin_functions.c zend_sprintf.c \
zend_ini.c zend_qsort.c zend_objects.c zend_object_handlers.c \
diff --git a/Zend/Zend.dsp b/Zend/Zend.dsp
index 23ebd4532b..61bdab0875 100644
--- a/Zend/Zend.dsp
+++ b/Zend/Zend.dsp
@@ -261,6 +261,10 @@ SOURCE=.\zend_ts_hash.c
SOURCE=.\zend_variables.c
# End Source File
+# Begin Source File
+
+SOURCE=.\zend_vm_opcodes.c
+# End Source File
# End Group
# Begin Group "Header Files"
diff --git a/Zend/ZendTS.dsp b/Zend/ZendTS.dsp
index 3be2c58bed..0292fda667 100644
--- a/Zend/ZendTS.dsp
+++ b/Zend/ZendTS.dsp
@@ -291,6 +291,10 @@ SOURCE=.\zend_ts_hash.c
SOURCE=.\zend_variables.c
# End Source File
+# Begin Source File
+
+SOURCE=.\zend_vm_opcodes.c
+# End Source File
# End Group
# Begin Group "Header Files"
diff --git a/Zend/tests/bug41421.phpt b/Zend/tests/bug41421.phpt
index f10db10980..f39fb15dda 100644
--- a/Zend/tests/bug41421.phpt
+++ b/Zend/tests/bug41421.phpt
@@ -24,6 +24,6 @@ Warning: feof(): wrapper::stream_eof is not implemented! Assuming EOF in %s on l
Fatal error: Uncaught exception 'Exception' in %s:%d
Stack trace:
#0 [internal function]: wrapper->stream_eof()
-#1 %s(%d): feof(Resource id #6)
+#1 %s(%d): feof(Resource id #%d)
#2 {main}
thrown in %s on line %d
diff --git a/Zend/tests/bug65784.phpt b/Zend/tests/bug65784.phpt
new file mode 100644
index 0000000000..adc34113a5
--- /dev/null
+++ b/Zend/tests/bug65784.phpt
@@ -0,0 +1,62 @@
+--TEST--
+Fixed Bug #65784 (Segfault with finally)
+--XFAIL--
+This bug is not fixed in 5.5 due to ABI BC
+--FILE--
+<?php
+function foo1() {
+ try {
+ throw new Exception("not catch");
+ return true;
+ } finally {
+ try {
+ throw new Exception("catched");
+ } catch (Exception $e) {
+ }
+ }
+}
+try {
+ $foo = foo1();
+ var_dump($foo);
+} catch (Exception $e) {
+ do {
+ var_dump($e->getMessage());
+ } while ($e = $e->getPrevious());
+}
+
+function foo2() {
+ try {
+ try {
+ throw new Exception("catched");
+ return true;
+ } finally {
+ try {
+ throw new Exception("catched");
+ } catch (Exception $e) {
+ }
+ }
+ } catch (Exception $e) {
+ }
+}
+
+$foo = foo2();
+var_dump($foo);
+
+function foo3() {
+ try {
+ throw new Exception("not catched");
+ return true;
+ } finally {
+ try {
+ throw new NotExists();
+ } catch (Exception $e) {
+ }
+ }
+}
+
+$bar = foo3();
+--EXPECTF--
+string(9) "not catch"
+NULL
+
+Fatal error: Class 'NotExists' not found in %sbug65784.php on line %d
diff --git a/Zend/tests/bug65969.phpt b/Zend/tests/bug65969.phpt
new file mode 100644
index 0000000000..d5128322ae
--- /dev/null
+++ b/Zend/tests/bug65969.phpt
@@ -0,0 +1,10 @@
+--TEST--
+Bug #65969 (Chain assignment with T_LIST failure)
+--FILE--
+<?php
+$obj = new stdClass;
+list($a,$b) = $obj->prop = [1,2];
+var_dump($a,$b);
+--EXPECT--
+int(1)
+int(2)
diff --git a/Zend/tests/bug66218.phpt b/Zend/tests/bug66218.phpt
new file mode 100644
index 0000000000..af7a5ab1d0
--- /dev/null
+++ b/Zend/tests/bug66218.phpt
@@ -0,0 +1,21 @@
+--TEST--
+Bug #66218 zend_register_functions breaks reflection
+--SKIPIF--
+<?php
+if (PHP_SAPI != "cli") die("skip CLI only test");
+if (!function_exists("dl")) die("skip need dl");
+?>
+--FILE--
+<?php
+$tab = get_extension_funcs("standard");
+$fcts = array("dl");
+foreach ($fcts as $fct) {
+ if (in_array($fct, $tab)) {
+ echo "$fct Ok\n";
+ }
+}
+?>
+Done
+--EXPECTF--
+dl Ok
+Done
diff --git a/Zend/tests/bug66286.phpt b/Zend/tests/bug66286.phpt
new file mode 100644
index 0000000000..457e282402
--- /dev/null
+++ b/Zend/tests/bug66286.phpt
@@ -0,0 +1,26 @@
+--TEST--
+Bug #66286: Incorrect object comparison with inheritance
+--FILE--
+<?php
+
+abstract class first {
+ protected $someArray = array();
+}
+
+class second extends first {
+ protected $someArray = array();
+ protected $someValue = null;
+
+ public function __construct($someValue) {
+ $this->someValue = $someValue;
+ }
+}
+
+$objFirst = new second('123');
+$objSecond = new second('321');
+
+var_dump ($objFirst == $objSecond);
+
+?>
+--EXPECT--
+bool(false)
diff --git a/Zend/tests/generators/bug66041.phpt b/Zend/tests/generators/bug66041.phpt
new file mode 100644
index 0000000000..d944224134
--- /dev/null
+++ b/Zend/tests/generators/bug66041.phpt
@@ -0,0 +1,17 @@
+--TEST--
+Bug #66041: list() fails to unpack yielded ArrayAccess object
+--FILE--
+<?php
+function dumpElement() {
+ list($value) = yield;
+ var_dump($value);
+};
+
+$fixedArray = new SplFixedArray(1);
+$fixedArray[0] = 'the element';
+
+$generator = dumpElement();
+$generator->send($fixedArray);
+?>
+--EXPECT--
+string(11) "the element"
diff --git a/Zend/tests/generators/throw_caught.phpt b/Zend/tests/generators/throw_caught.phpt
index 0c3f8e9b2d..c5e9d81ebc 100644
--- a/Zend/tests/generators/throw_caught.phpt
+++ b/Zend/tests/generators/throw_caught.phpt
@@ -4,6 +4,7 @@ Generator::throw() where the exception is caught in the generator
<?php
function gen() {
+ echo "before yield\n";
try {
yield;
} catch (RuntimeException $e) {
@@ -18,6 +19,7 @@ var_dump($gen->throw(new RuntimeException('Test')));
?>
--EXPECTF--
+before yield
exception 'RuntimeException' with message 'Test' in %s:%d
Stack trace:
#0 {main}
diff --git a/Zend/tests/generators/throw_rethrow.phpt b/Zend/tests/generators/throw_rethrow.phpt
index 267f5f0db8..65044ee3f3 100644
--- a/Zend/tests/generators/throw_rethrow.phpt
+++ b/Zend/tests/generators/throw_rethrow.phpt
@@ -4,6 +4,7 @@ Generator::throw() where the generator throws a different exception
<?php
function gen() {
+ echo "before yield\n";
try {
yield;
} catch (RuntimeException $e) {
@@ -18,6 +19,7 @@ var_dump($gen->throw(new RuntimeException('throw')));
?>
--EXPECTF--
+before yield
Caught: exception 'RuntimeException' with message 'throw' in %s:%d
Stack trace:
#0 {main}
diff --git a/Zend/zend.c b/Zend/zend.c
index 11baf34c93..23b16ce234 100644
--- a/Zend/zend.c
+++ b/Zend/zend.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -43,10 +43,6 @@
# define GLOBAL_CONSTANTS_TABLE EG(zend_constants)
#endif
-#if defined(ZEND_WIN32) && ZEND_DEBUG
-BOOL WINAPI IsDebuggerPresent(VOID);
-#endif
-
/* true multithread-shared globals */
ZEND_API zend_class_entry *zend_standard_class_def = NULL;
ZEND_API int (*zend_printf)(const char *format, ...);
@@ -131,7 +127,7 @@ ZEND_API zval zval_used_for_init; /* True global variable */
/* version information */
static char *zend_version_info;
static uint zend_version_info_length;
-#define ZEND_CORE_VERSION_INFO "Zend Engine v" ZEND_VERSION ", Copyright (c) 1998-2013 Zend Technologies\n"
+#define ZEND_CORE_VERSION_INFO "Zend Engine v" ZEND_VERSION ", Copyright (c) 1998-2014 Zend Technologies\n"
#define PRINT_ZVAL_INDENT 4
static void print_hash(zend_write_func_t write_func, HashTable *ht, int indent, zend_bool is_object TSRMLS_DC) /* {{{ */
diff --git a/Zend/zend.h b/Zend/zend.h
index af653b15eb..d021dd6f6e 100644
--- a/Zend/zend.h
+++ b/Zend/zend.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_API.c b/Zend/zend_API.c
index b59faab284..a852246407 100644
--- a/Zend/zend_API.c
+++ b/Zend/zend_API.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_API.h b/Zend/zend_API.h
index ecc8d9acd9..59bcd59acb 100644
--- a/Zend/zend_API.h
+++ b/Zend/zend_API.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_alloc.c b/Zend/zend_alloc.c
index bf9d000437..bdcee5cbe4 100644
--- a/Zend/zend_alloc.c
+++ b/Zend/zend_alloc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -201,7 +201,7 @@ static int zend_mm_dev_zero_fd = -1;
static zend_mm_storage* zend_mm_mem_mmap_zero_init(void *params)
{
- if (zend_mm_dev_zero_fd != -1) {
+ if (zend_mm_dev_zero_fd == -1) {
zend_mm_dev_zero_fd = open("/dev/zero", O_RDWR, S_IRUSR | S_IWUSR);
}
if (zend_mm_dev_zero_fd >= 0) {
diff --git a/Zend/zend_alloc.h b/Zend/zend_alloc.h
index 0b4e74d897..05494ee37c 100644
--- a/Zend/zend_alloc.h
+++ b/Zend/zend_alloc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_build.h b/Zend/zend_build.h
index 152e1bd44a..bec174d5c7 100644
--- a/Zend/zend_build.h
+++ b/Zend/zend_build.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_builtin_functions.c b/Zend/zend_builtin_functions.c
index 6cbe0bc687..3ce28fa0fe 100644
--- a/Zend/zend_builtin_functions.c
+++ b/Zend/zend_builtin_functions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -461,17 +461,12 @@ ZEND_FUNCTION(func_get_args)
array_init_size(return_value, arg_count);
for (i=0; i<arg_count; i++) {
- zval *element, *arg;
+ zval *element;
- arg = *((zval **) (p-(arg_count-i)));
- if (!Z_ISREF_P(arg)) {
- element = arg;
- Z_ADDREF_P(element);
- } else {
- ALLOC_ZVAL(element);
- INIT_PZVAL_COPY(element, arg);
- zval_copy_ctor(element);
- }
+ ALLOC_ZVAL(element);
+ *element = **((zval **) (p-(arg_count-i)));
+ zval_copy_ctor(element);
+ INIT_PZVAL(element);
zend_hash_next_index_insert(return_value->value.ht, &element, sizeof(zval *), NULL);
}
}
@@ -2442,36 +2437,49 @@ ZEND_FUNCTION(extension_loaded)
Returns an array with the names of functions belonging to the named extension */
ZEND_FUNCTION(get_extension_funcs)
{
- char *extension_name;
- int extension_name_len;
+ char *extension_name, *lcname;
+ int extension_name_len, array;
zend_module_entry *module;
- const zend_function_entry *func;
-
+ HashPosition iterator;
+ zend_function *zif;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &extension_name, &extension_name_len) == FAILURE) {
return;
}
-
if (strncasecmp(extension_name, "zend", sizeof("zend"))) {
- char *lcname = zend_str_tolower_dup(extension_name, extension_name_len);
- if (zend_hash_find(&module_registry, lcname,
- extension_name_len+1, (void**)&module) == FAILURE) {
- efree(lcname);
- RETURN_FALSE;
- }
+ lcname = zend_str_tolower_dup(extension_name, extension_name_len);
+ } else {
+ lcname = estrdup("core");
+ }
+ if (zend_hash_find(&module_registry, lcname,
+ extension_name_len+1, (void**)&module) == FAILURE) {
efree(lcname);
+ RETURN_FALSE;
+ }
- if (!(func = module->functions)) {
- RETURN_FALSE;
- }
+ zend_hash_internal_pointer_reset_ex(CG(function_table), &iterator);
+ if (module->functions) {
+ /* avoid BC break, if functions list is empty, will return an empty array */
+ array_init(return_value);
+ array = 1;
} else {
- func = builtin_functions;
+ array = 0;
+ }
+ while (zend_hash_get_current_data_ex(CG(function_table), (void **) &zif, &iterator) == SUCCESS) {
+ if (zif->common.type==ZEND_INTERNAL_FUNCTION
+ && zif->internal_function.module == module) {
+ if (!array) {
+ array_init(return_value);
+ array = 1;
+ }
+ add_next_index_string(return_value, zif->common.function_name, 1);
+ }
+ zend_hash_move_forward_ex(CG(function_table), &iterator);
}
- array_init(return_value);
+ efree(lcname);
- while (func->fname) {
- add_next_index_string(return_value, func->fname, 1);
- func++;
+ if (!array) {
+ RETURN_FALSE;
}
}
/* }}} */
diff --git a/Zend/zend_builtin_functions.h b/Zend/zend_builtin_functions.h
index e1af53637d..3db0d2002b 100644
--- a/Zend/zend_builtin_functions.h
+++ b/Zend/zend_builtin_functions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_closures.c b/Zend/zend_closures.c
index 5faefbd224..fcea56d811 100644
--- a/Zend/zend_closures.c
+++ b/Zend/zend_closures.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_closures.h b/Zend/zend_closures.h
index 9d50641d21..fa66e9747d 100644
--- a/Zend/zend_closures.h
+++ b/Zend/zend_closures.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_compile.c b/Zend/zend_compile.c
index 60b9e3e653..b0a611cab1 100644
--- a/Zend/zend_compile.c
+++ b/Zend/zend_compile.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -2782,7 +2782,7 @@ void zend_do_yield(znode *result, znode *value, const znode *key, zend_bool is_v
SET_UNUSED(opline->op2);
}
- opline->result_type = IS_TMP_VAR;
+ opline->result_type = IS_VAR;
opline->result.var = get_temporary_variable(CG(active_op_array));
GET_NODE(result, opline->result);
}
diff --git a/Zend/zend_compile.h b/Zend/zend_compile.h
index 9c55b5ebe8..2a3d58e490 100644
--- a/Zend/zend_compile.h
+++ b/Zend/zend_compile.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_config.nw.h b/Zend/zend_config.nw.h
index 04f80bfe72..bbb2da6e72 100644
--- a/Zend/zend_config.nw.h
+++ b/Zend/zend_config.nw.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_config.w32.h b/Zend/zend_config.w32.h
index 73bd0525ba..6ea67602b4 100644
--- a/Zend/zend_config.w32.h
+++ b/Zend/zend_config.w32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -62,10 +62,15 @@ typedef unsigned int uint;
/* This will cause the compilation process to be MUCH longer, but will generate
* a much quicker PHP binary
*/
-#undef inline
#ifdef ZEND_WIN32_FORCE_INLINE
+/* _ALLOW_KEYWORD_MACROS is only relevant for C++ */
+# if (_MSC_VER >= 1700) && !defined(_ALLOW_KEYWORD_MACROS)
+# define _ALLOW_KEYWORD_MACROS
+# endif
+# undef inline
# define inline __forceinline
-#else
+#elif !defined(ZEND_WIN32_KEEP_INLINE)
+# undef inline
# define inline
#endif
diff --git a/Zend/zend_constants.c b/Zend/zend_constants.c
index 21580d3d5f..574d4b1555 100644
--- a/Zend/zend_constants.c
+++ b/Zend/zend_constants.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_constants.h b/Zend/zend_constants.h
index c7261946c8..2e9af42d2f 100644
--- a/Zend/zend_constants.h
+++ b/Zend/zend_constants.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_default_classes.c b/Zend/zend_default_classes.c
index 46b00eac4e..40b28f7a23 100644
--- a/Zend/zend_default_classes.c
+++ b/Zend/zend_default_classes.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_dynamic_array.c b/Zend/zend_dynamic_array.c
index 543479c43e..db81b00a73 100644
--- a/Zend/zend_dynamic_array.c
+++ b/Zend/zend_dynamic_array.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_dynamic_array.h b/Zend/zend_dynamic_array.h
index 2c96f85437..e69eb18768 100644
--- a/Zend/zend_dynamic_array.h
+++ b/Zend/zend_dynamic_array.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_errors.h b/Zend/zend_errors.h
index a2cdc20a60..941903d16d 100644
--- a/Zend/zend_errors.h
+++ b/Zend/zend_errors.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_exceptions.c b/Zend/zend_exceptions.c
index c7f157c4d5..9b7d3689c6 100644
--- a/Zend/zend_exceptions.c
+++ b/Zend/zend_exceptions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -360,6 +360,11 @@ ZEND_METHOD(error_exception, getSeverity)
} \
}
+
+#define TRACE_ARG_APPEND(vallen) \
+ *str = (char*)erealloc(*str, *len + 1 + vallen); \
+ memcpy((*str) + *len - l_added + 1 + vallen, (*str) + *len - l_added + 1, l_added);
+
/* }}} */
static int _build_trace_args(zval **arg TSRMLS_DC, int num_args, va_list args, zend_hash_key *hash_key) /* {{{ */
@@ -371,7 +376,7 @@ static int _build_trace_args(zval **arg TSRMLS_DC, int num_args, va_list args, z
len = va_arg(args, int*);
/* the trivial way would be to do:
- * conver_to_string_ex(arg);
+ * convert_to_string_ex(arg);
* append it and kill the now tmp arg.
* but that could cause some E_NOTICE and also damn long lines.
*/
@@ -394,8 +399,58 @@ static int _build_trace_args(zval **arg TSRMLS_DC, int num_args, va_list args, z
l_added += 3 + 1;
}
while (--l_added) {
- if ((*str)[*len - l_added] < 32) {
- (*str)[*len - l_added] = '?';
+ unsigned char chr = (*str)[*len - l_added];
+ if (chr < 32 || chr == '\\' || chr > 126) {
+ (*str)[*len - l_added] = '\\';
+
+ switch (chr) {
+ case '\n':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 'n';
+ break;
+ case '\r':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 'r';
+ break;
+ case '\t':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 't';
+ break;
+ case '\f':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 'f';
+ break;
+ case '\v':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 'v';
+ break;
+#ifndef PHP_WIN32
+ case '\e':
+#else
+ case VK_ESCAPE:
+#endif
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = 'e';
+ break;
+ case '\\':
+ TRACE_ARG_APPEND(1);
+ (*str)[++(*len) - l_added] = '\\';
+ break;
+ default:
+ TRACE_ARG_APPEND(3);
+ (*str)[*len - l_added + 1] = 'x';
+ if ((chr >> 4) < 10) {
+ (*str)[*len - l_added + 2] = (chr >> 4) + '0';
+ } else {
+ (*str)[*len - l_added + 2] = (chr >> 4) + 'A' - 10;
+ }
+ if (chr % 16 < 10) {
+ (*str)[*len - l_added + 3] = chr % 16 + '0';
+ } else {
+ (*str)[*len - l_added + 3] = chr % 16 + 'A' - 10;
+ }
+ *len += 3;
+ }
}
}
break;
diff --git a/Zend/zend_exceptions.h b/Zend/zend_exceptions.h
index 81c8a1f213..2ce9c1295c 100644
--- a/Zend/zend_exceptions.h
+++ b/Zend/zend_exceptions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_execute.c b/Zend/zend_execute.c
index a65f5331de..1df0cb5514 100644
--- a/Zend/zend_execute.c
+++ b/Zend/zend_execute.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1247,9 +1247,8 @@ convert_to_array:
}
}
-static void zend_fetch_dimension_address_read(temp_variable *result, zval **container_ptr, zval *dim, int dim_type, int type TSRMLS_DC)
+static void zend_fetch_dimension_address_read(temp_variable *result, zval *container, zval *dim, int dim_type, int type TSRMLS_DC)
{
- zval *container = *container_ptr;
zval **retval;
switch (Z_TYPE_P(container)) {
diff --git a/Zend/zend_execute.h b/Zend/zend_execute.h
index ff0758772e..ea06328d93 100644
--- a/Zend/zend_execute.h
+++ b/Zend/zend_execute.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_execute_API.c b/Zend/zend_execute_API.c
index 83c2217984..45ad5c38bf 100644
--- a/Zend/zend_execute_API.c
+++ b/Zend/zend_execute_API.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1063,6 +1063,14 @@ ZEND_API int zend_lookup_class_ex(const char *name, int name_length, const zend_
return FAILURE;
}
+ /* Verify class name before passing it to __autoload() */
+ if (strspn(name, "0123456789_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ\177\200\201\202\203\204\205\206\207\210\211\212\213\214\215\216\217\220\221\222\223\224\225\226\227\230\231\232\233\234\235\236\237\240\241\242\243\244\245\246\247\250\251\252\253\254\255\256\257\260\261\262\263\264\265\266\267\270\271\272\273\274\275\276\277\300\301\302\303\304\305\306\307\310\311\312\313\314\315\316\317\320\321\322\323\324\325\326\327\330\331\332\333\334\335\336\337\340\341\342\343\344\345\346\347\350\351\352\353\354\355\356\357\360\361\362\363\364\365\366\367\370\371\372\373\374\375\376\377\\") != name_length) {
+ if (!key) {
+ free_alloca(lc_free, use_heap);
+ }
+ return FAILURE;
+ }
+
if (EG(in_autoload) == NULL) {
ALLOC_HASHTABLE(EG(in_autoload));
zend_hash_init(EG(in_autoload), 0, NULL, NULL, 0);
diff --git a/Zend/zend_extensions.c b/Zend/zend_extensions.c
index 2dd7cd4c59..e1290b78ca 100644
--- a/Zend/zend_extensions.c
+++ b/Zend/zend_extensions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_extensions.h b/Zend/zend_extensions.h
index 83cad7f38d..cae689b670 100644
--- a/Zend/zend_extensions.h
+++ b/Zend/zend_extensions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_float.c b/Zend/zend_float.c
index cd6fcf2a14..ca0130134c 100644
--- a/Zend/zend_float.c
+++ b/Zend/zend_float.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_float.h b/Zend/zend_float.h
index 56bdb151a0..33f8e93fbf 100644
--- a/Zend/zend_float.h
+++ b/Zend/zend_float.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_gc.c b/Zend/zend_gc.c
index 7b83ddb54f..76217e369d 100644
--- a/Zend/zend_gc.c
+++ b/Zend/zend_gc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_gc.h b/Zend/zend_gc.h
index 3483e9dbf0..ac5f6350a2 100644
--- a/Zend/zend_gc.h
+++ b/Zend/zend_gc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_generators.c b/Zend/zend_generators.c
index 0af20f4593..a5313dc1a3 100644
--- a/Zend/zend_generators.c
+++ b/Zend/zend_generators.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -29,6 +29,73 @@ static zend_object_handlers zend_generator_handlers;
static zend_object_value zend_generator_create(zend_class_entry *class_type TSRMLS_DC);
+static void zend_generator_cleanup_unfinished_execution(zend_generator *generator TSRMLS_DC) /* {{{ */
+{
+ zend_execute_data *execute_data = generator->execute_data;
+ zend_op_array *op_array = execute_data->op_array;
+
+ if (generator->send_target) {
+ Z_DELREF_PP(generator->send_target);
+ generator->send_target = NULL;
+ }
+
+ /* Manually free loop variables, as execution couldn't reach their
+ * SWITCH_FREE / FREE opcodes. */
+ {
+ /* -1 required because we want the last run opcode, not the
+ * next to-be-run one. */
+ zend_uint op_num = execute_data->opline - op_array->opcodes - 1;
+
+ int i;
+ for (i = 0; i < op_array->last_brk_cont; ++i) {
+ zend_brk_cont_element *brk_cont = op_array->brk_cont_array + i;
+
+ if (brk_cont->start < 0) {
+ continue;
+ } else if (brk_cont->start > op_num) {
+ break;
+ } else if (brk_cont->brk > op_num) {
+ zend_op *brk_opline = op_array->opcodes + brk_cont->brk;
+
+ switch (brk_opline->opcode) {
+ case ZEND_SWITCH_FREE:
+ {
+ temp_variable *var = EX_TMP_VAR(execute_data, brk_opline->op1.var);
+ zval_ptr_dtor(&var->var.ptr);
+ }
+ break;
+ case ZEND_FREE:
+ {
+ temp_variable *var = EX_TMP_VAR(execute_data, brk_opline->op1.var);
+ zval_dtor(&var->tmp_var);
+ }
+ break;
+ }
+ }
+ }
+ }
+
+ /* Clear any backed up stack arguments */
+ {
+ void **ptr = generator->stack->top - 1;
+ void **end = zend_vm_stack_frame_base(execute_data);
+
+ for (; ptr >= end; --ptr) {
+ zval_ptr_dtor((zval **) ptr);
+ }
+ }
+
+ /* If yield was used as a function argument there may be active
+ * method calls those objects need to be freed */
+ while (execute_data->call >= execute_data->call_slots) {
+ if (execute_data->call->object) {
+ zval_ptr_dtor(&execute_data->call->object);
+ }
+ execute_data->call--;
+ }
+}
+/* }}} */
+
ZEND_API void zend_generator_close(zend_generator *generator, zend_bool finished_execution TSRMLS_DC) /* {{{ */
{
if (generator->value) {
@@ -61,65 +128,6 @@ ZEND_API void zend_generator_close(zend_generator *generator, zend_bool finished
return;
}
- /* If the generator is closed before it can finish execution (reach
- * a return statement) we have to free loop variables manually, as
- * we don't know whether the SWITCH_FREE / FREE opcodes have run */
- if (!finished_execution) {
- /* -1 required because we want the last run opcode, not the
- * next to-be-run one. */
- zend_uint op_num = execute_data->opline - op_array->opcodes - 1;
-
- int i;
- for (i = 0; i < op_array->last_brk_cont; ++i) {
- zend_brk_cont_element *brk_cont = op_array->brk_cont_array + i;
-
- if (brk_cont->start < 0) {
- continue;
- } else if (brk_cont->start > op_num) {
- break;
- } else if (brk_cont->brk > op_num) {
- zend_op *brk_opline = op_array->opcodes + brk_cont->brk;
-
- switch (brk_opline->opcode) {
- case ZEND_SWITCH_FREE:
- {
- temp_variable *var = EX_TMP_VAR(execute_data, brk_opline->op1.var);
- zval_ptr_dtor(&var->var.ptr);
- }
- break;
- case ZEND_FREE:
- {
- temp_variable *var = EX_TMP_VAR(execute_data, brk_opline->op1.var);
- zval_dtor(&var->tmp_var);
- }
- break;
- }
- }
- }
- }
-
- /* Clear any backed up stack arguments */
- if (generator->stack != EG(argument_stack)) {
- void **ptr = generator->stack->top - 1;
- void **end = zend_vm_stack_frame_base(execute_data);
-
- /* If the top stack element is the argument count, skip it */
- if (execute_data->function_state.arguments) {
- ptr--;
- }
-
- for (; ptr >= end; --ptr) {
- zval_ptr_dtor((zval**) ptr);
- }
- }
-
- while (execute_data->call >= execute_data->call_slots) {
- if (execute_data->call->object) {
- zval_ptr_dtor(&execute_data->call->object);
- }
- execute_data->call--;
- }
-
/* We have added an additional stack frame in prev_execute_data, so we
* have to free it. It also contains the arguments passed to the
* generator (for func_get_args) so those have to be freed too. */
@@ -138,6 +146,12 @@ ZEND_API void zend_generator_close(zend_generator *generator, zend_bool finished
}
}
+ /* Some cleanups are only necessary if the generator was closued
+ * before it could finish execution (reach a return statement). */
+ if (!finished_execution) {
+ zend_generator_cleanup_unfinished_execution(generator TSRMLS_CC);
+ }
+
/* Free a clone of closure */
if (op_array->fn_flags & ZEND_ACC_CLOSURE) {
destroy_op_array(op_array TSRMLS_CC);
@@ -145,10 +159,6 @@ ZEND_API void zend_generator_close(zend_generator *generator, zend_bool finished
}
efree(generator->stack);
- if (generator->stack == EG(argument_stack)) {
- /* abnormal exit for running generator */
- EG(argument_stack) = NULL;
- }
generator->execute_data = NULL;
}
}
@@ -519,8 +529,12 @@ ZEND_METHOD(Generator, send)
return;
}
- /* Put sent value into the TMP_VAR slot */
- MAKE_COPY_ZVAL(&value, &generator->send_target->tmp_var);
+ /* Put sent value in the target VAR slot, if it is used */
+ if (generator->send_target) {
+ Z_DELREF_PP(generator->send_target);
+ Z_ADDREF_P(value);
+ *generator->send_target = value;
+ }
zend_generator_resume(generator TSRMLS_CC);
@@ -546,6 +560,8 @@ ZEND_METHOD(Generator, throw)
generator = (zend_generator *) zend_object_store_get_object(getThis() TSRMLS_CC);
+ zend_generator_ensure_initialized(generator TSRMLS_CC);
+
if (generator->execute_data) {
/* Throw the exception in the context of the generator */
zend_execute_data *current_execute_data = EG(current_execute_data);
diff --git a/Zend/zend_generators.h b/Zend/zend_generators.h
index bc125658ee..2373a1a7c8 100644
--- a/Zend/zend_generators.h
+++ b/Zend/zend_generators.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -49,7 +49,7 @@ typedef struct _zend_generator {
/* Current key */
zval *key;
/* Variable to put sent value into */
- temp_variable *send_target;
+ zval **send_target;
/* Largest used integer key for auto-incrementing keys */
long largest_used_integer_key;
diff --git a/Zend/zend_globals.h b/Zend/zend_globals.h
index b9a5b39914..6dc022dac8 100644
--- a/Zend/zend_globals.h
+++ b/Zend/zend_globals.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_globals_macros.h b/Zend/zend_globals_macros.h
index 9bb1b8026d..ac9b793775 100644
--- a/Zend/zend_globals_macros.h
+++ b/Zend/zend_globals_macros.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_hash.c b/Zend/zend_hash.c
index 96c3f3d7b5..d7188ea564 100644
--- a/Zend/zend_hash.c
+++ b/Zend/zend_hash.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_hash.h b/Zend/zend_hash.h
index 69732cd597..cebb898ffd 100644
--- a/Zend/zend_hash.h
+++ b/Zend/zend_hash.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_highlight.c b/Zend/zend_highlight.c
index c789cb719a..e4f8d0237a 100644
--- a/Zend/zend_highlight.c
+++ b/Zend/zend_highlight.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -57,7 +57,7 @@ ZEND_API void zend_html_putc(char c)
ZEND_API void zend_html_puts(const char *s, uint len TSRMLS_DC)
{
const unsigned char *ptr = (const unsigned char*)s, *end = ptr + len;
- unsigned char *filtered;
+ unsigned char *filtered = NULL;
size_t filtered_len;
if (LANG_SCNG(output_filter)) {
diff --git a/Zend/zend_highlight.h b/Zend/zend_highlight.h
index 20adf349ae..1a35505135 100644
--- a/Zend/zend_highlight.h
+++ b/Zend/zend_highlight.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_indent.c b/Zend/zend_indent.c
index fea78d9c57..cacdf8df3b 100644
--- a/Zend/zend_indent.c
+++ b/Zend/zend_indent.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_indent.h b/Zend/zend_indent.h
index bba02a738b..6d0996efa8 100644
--- a/Zend/zend_indent.h
+++ b/Zend/zend_indent.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini.c b/Zend/zend_ini.c
index 2c74f20f6a..f286ccd157 100644
--- a/Zend/zend_ini.c
+++ b/Zend/zend_ini.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini.h b/Zend/zend_ini.h
index b27d3d4add..0fe4c3161f 100644
--- a/Zend/zend_ini.h
+++ b/Zend/zend_ini.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini_parser.y b/Zend/zend_ini_parser.y
index 901babad60..3823efd413 100644
--- a/Zend/zend_ini_parser.y
+++ b/Zend/zend_ini_parser.y
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini_scanner.c b/Zend/zend_ini_scanner.c
index 87ba664312..521e98e257 100644
--- a/Zend/zend_ini_scanner.c
+++ b/Zend/zend_ini_scanner.c
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini_scanner.h b/Zend/zend_ini_scanner.h
index 2655fc8732..aafe7efdde 100644
--- a/Zend/zend_ini_scanner.h
+++ b/Zend/zend_ini_scanner.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ini_scanner.l b/Zend/zend_ini_scanner.l
index 92fb08f02d..6207c76b27 100644
--- a/Zend/zend_ini_scanner.l
+++ b/Zend/zend_ini_scanner.l
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_interfaces.c b/Zend/zend_interfaces.c
index 16751549b4..4b01eb3c4f 100644
--- a/Zend/zend_interfaces.c
+++ b/Zend/zend_interfaces.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_interfaces.h b/Zend/zend_interfaces.h
index ba4bc6ccb6..7b70bc49d4 100644
--- a/Zend/zend_interfaces.h
+++ b/Zend/zend_interfaces.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_istdiostream.h b/Zend/zend_istdiostream.h
index d7edf172f0..40fdb4310f 100644
--- a/Zend/zend_istdiostream.h
+++ b/Zend/zend_istdiostream.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_iterators.c b/Zend/zend_iterators.c
index f2c27fa63d..a2854c4b74 100644
--- a/Zend/zend_iterators.c
+++ b/Zend/zend_iterators.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_iterators.h b/Zend/zend_iterators.h
index f74068a271..873f36efbe 100644
--- a/Zend/zend_iterators.h
+++ b/Zend/zend_iterators.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_language_parser.y b/Zend/zend_language_parser.y
index 6a9a24a87e..a2026609a5 100644
--- a/Zend/zend_language_parser.y
+++ b/Zend/zend_language_parser.y
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_language_scanner.c b/Zend/zend_language_scanner.c
index deb799ab76..7173e91809 100644
--- a/Zend/zend_language_scanner.c
+++ b/Zend/zend_language_scanner.c
@@ -1,10 +1,10 @@
-/* Generated by re2c 0.13.5 */
+/* Generated by re2c 0.13.5 on Sun Dec 22 13:03:33 2013 */
#line 1 "Zend/zend_language_scanner.l"
/*
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_language_scanner.h b/Zend/zend_language_scanner.h
index 2e5914f1b2..05345b2cc3 100644
--- a/Zend/zend_language_scanner.h
+++ b/Zend/zend_language_scanner.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_language_scanner.l b/Zend/zend_language_scanner.l
index d2e7243bb2..a4b5b32d96 100644
--- a/Zend/zend_language_scanner.l
+++ b/Zend/zend_language_scanner.l
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_language_scanner_defs.h b/Zend/zend_language_scanner_defs.h
index 5926e3c61d..70ce8b890c 100644
--- a/Zend/zend_language_scanner_defs.h
+++ b/Zend/zend_language_scanner_defs.h
@@ -1,4 +1,4 @@
-/* Generated by re2c 0.13.5 */
+/* Generated by re2c 0.13.5 on Sun Dec 22 13:03:33 2013 */
#line 3 "Zend/zend_language_scanner_defs.h"
enum YYCONDTYPE {
diff --git a/Zend/zend_list.c b/Zend/zend_list.c
index e60deb1cd1..11c2c33567 100644
--- a/Zend/zend_list.c
+++ b/Zend/zend_list.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_list.h b/Zend/zend_list.h
index 23f51140f5..b7980d56f2 100644
--- a/Zend/zend_list.h
+++ b/Zend/zend_list.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_llist.c b/Zend/zend_llist.c
index 20f847c781..ad74bd56cb 100644
--- a/Zend/zend_llist.c
+++ b/Zend/zend_llist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_llist.h b/Zend/zend_llist.h
index 0a03e6ce59..b05ece8077 100644
--- a/Zend/zend_llist.h
+++ b/Zend/zend_llist.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_modules.h b/Zend/zend_modules.h
index d4adcf5aac..18cf05cf31 100644
--- a/Zend/zend_modules.h
+++ b/Zend/zend_modules.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_multibyte.c b/Zend/zend_multibyte.c
index dafcf18393..356bfc75fa 100644
--- a/Zend/zend_multibyte.c
+++ b/Zend/zend_multibyte.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_multibyte.h b/Zend/zend_multibyte.h
index c537e133f8..db2db1a971 100644
--- a/Zend/zend_multibyte.h
+++ b/Zend/zend_multibyte.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_multiply.h b/Zend/zend_multiply.h
index 0d8977fdea..74dc7d1452 100644
--- a/Zend/zend_multiply.h
+++ b/Zend/zend_multiply.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_object_handlers.c b/Zend/zend_object_handlers.c
index f7be37036f..093951eeca 100644
--- a/Zend/zend_object_handlers.c
+++ b/Zend/zend_object_handlers.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1379,10 +1379,6 @@ static int zend_std_compare_objects(zval *o1, zval *o2 TSRMLS_DC) /* {{{ */
Z_OBJ_UNPROTECT_RECURSION(o1);
Z_OBJ_UNPROTECT_RECURSION(o2);
return 1;
- } else {
- Z_OBJ_UNPROTECT_RECURSION(o1);
- Z_OBJ_UNPROTECT_RECURSION(o2);
- return 0;
}
}
}
diff --git a/Zend/zend_object_handlers.h b/Zend/zend_object_handlers.h
index 3ea6008350..715ba1ea65 100644
--- a/Zend/zend_object_handlers.h
+++ b/Zend/zend_object_handlers.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_objects.c b/Zend/zend_objects.c
index ce6284439c..da3aab551d 100644
--- a/Zend/zend_objects.c
+++ b/Zend/zend_objects.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_objects.h b/Zend/zend_objects.h
index 17d8430fce..d00c65a368 100644
--- a/Zend/zend_objects.h
+++ b/Zend/zend_objects.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_objects_API.c b/Zend/zend_objects_API.c
index b5dd48f798..f7a6b0b4c3 100644
--- a/Zend/zend_objects_API.c
+++ b/Zend/zend_objects_API.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_objects_API.h b/Zend/zend_objects_API.h
index a6ea9b8c02..d8f2c5e384 100644
--- a/Zend/zend_objects_API.h
+++ b/Zend/zend_objects_API.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_opcode.c b/Zend/zend_opcode.c
index 41b4bd2571..025e8faa3c 100644
--- a/Zend/zend_opcode.c
+++ b/Zend/zend_opcode.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -489,17 +489,22 @@ static void zend_check_finally_breakout(zend_op_array *op_array, zend_uint op_nu
zend_uint i;
for (i = 0; i < op_array->last_try_catch; i++) {
- if (op_array->try_catch_array[i].try_op > op_num) {
- break;
- }
- if ((op_num >= op_array->try_catch_array[i].finally_op
+ if ((op_num < op_array->try_catch_array[i].finally_op ||
+ op_num >= op_array->try_catch_array[i].finally_end)
+ && (dst_num >= op_array->try_catch_array[i].finally_op &&
+ dst_num <= op_array->try_catch_array[i].finally_end)) {
+ CG(in_compilation) = 1;
+ CG(active_op_array) = op_array;
+ CG(zend_lineno) = op_array->opcodes[op_num].lineno;
+ zend_error_noreturn(E_COMPILE_ERROR, "jump into a finally block is disallowed");
+ } else if ((op_num >= op_array->try_catch_array[i].finally_op
&& op_num <= op_array->try_catch_array[i].finally_end)
&& (dst_num > op_array->try_catch_array[i].finally_end
|| dst_num < op_array->try_catch_array[i].finally_op)) {
CG(in_compilation) = 1;
CG(active_op_array) = op_array;
CG(zend_lineno) = op_array->opcodes[op_num].lineno;
- zend_error(E_COMPILE_ERROR, "jump out of a finally block is disallowed");
+ zend_error_noreturn(E_COMPILE_ERROR, "jump out of a finally block is disallowed");
}
}
}
diff --git a/Zend/zend_operators.c b/Zend/zend_operators.c
index 5c84deb268..683ab3c5cf 100644
--- a/Zend/zend_operators.c
+++ b/Zend/zend_operators.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_operators.h b/Zend/zend_operators.h
index 6e7c1c01df..976cf33ca0 100644
--- a/Zend/zend_operators.h
+++ b/Zend/zend_operators.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -640,13 +640,18 @@ static zend_always_inline int fast_add_function(zval *result, zval *op1, zval *o
"n"(ZVAL_OFFSETOF_TYPE)
: "rax","cc");
#else
- Z_LVAL_P(result) = Z_LVAL_P(op1) + Z_LVAL_P(op2);
+ /*
+ * 'result' may alias with op1 or op2, so we need to
+ * ensure that 'result' is not updated until after we
+ * have read the values of op1 and op2.
+ */
if (UNEXPECTED((Z_LVAL_P(op1) & LONG_SIGN_MASK) == (Z_LVAL_P(op2) & LONG_SIGN_MASK)
- && (Z_LVAL_P(op1) & LONG_SIGN_MASK) != (Z_LVAL_P(result) & LONG_SIGN_MASK))) {
+ && (Z_LVAL_P(op1) & LONG_SIGN_MASK) != ((Z_LVAL_P(op1) + Z_LVAL_P(op2)) & LONG_SIGN_MASK))) {
Z_DVAL_P(result) = (double) Z_LVAL_P(op1) + (double) Z_LVAL_P(op2);
Z_TYPE_P(result) = IS_DOUBLE;
} else {
+ Z_LVAL_P(result) = Z_LVAL_P(op1) + Z_LVAL_P(op2);
Z_TYPE_P(result) = IS_LONG;
}
#endif
@@ -789,6 +794,7 @@ static zend_always_inline int fast_mul_function(zval *result, zval *op1, zval *o
static zend_always_inline int fast_div_function(zval *result, zval *op1, zval *op2 TSRMLS_DC)
{
+#if 0
if (EXPECTED(Z_TYPE_P(op1) == IS_LONG) && 0) {
if (EXPECTED(Z_TYPE_P(op2) == IS_LONG)) {
if (UNEXPECTED(Z_LVAL_P(op2) == 0)) {
@@ -843,6 +849,7 @@ static zend_always_inline int fast_div_function(zval *result, zval *op1, zval *o
return SUCCESS;
}
}
+#endif
return div_function(result, op1, op2 TSRMLS_CC);
}
diff --git a/Zend/zend_ptr_stack.c b/Zend/zend_ptr_stack.c
index 9dbdb3ddd7..bb85a2cc26 100644
--- a/Zend/zend_ptr_stack.c
+++ b/Zend/zend_ptr_stack.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ptr_stack.h b/Zend/zend_ptr_stack.h
index 1099240796..ecd7b7042a 100644
--- a/Zend/zend_ptr_stack.h
+++ b/Zend/zend_ptr_stack.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_qsort.c b/Zend/zend_qsort.c
index 128c48dfc8..ea577e1c07 100644
--- a/Zend/zend_qsort.c
+++ b/Zend/zend_qsort.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_qsort.h b/Zend/zend_qsort.h
index 0ce32a77c1..c61a85d18e 100644
--- a/Zend/zend_qsort.h
+++ b/Zend/zend_qsort.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_sprintf.c b/Zend/zend_sprintf.c
index 79ee5a9d6f..64c9b727fd 100644
--- a/Zend/zend_sprintf.c
+++ b/Zend/zend_sprintf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_stack.c b/Zend/zend_stack.c
index 3e7401f5ff..cf99499e79 100644
--- a/Zend/zend_stack.c
+++ b/Zend/zend_stack.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_stack.h b/Zend/zend_stack.h
index f18dfeca7c..d484879468 100644
--- a/Zend/zend_stack.h
+++ b/Zend/zend_stack.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_static_allocator.c b/Zend/zend_static_allocator.c
index 1150deb570..71338d211e 100644
--- a/Zend/zend_static_allocator.c
+++ b/Zend/zend_static_allocator.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_static_allocator.h b/Zend/zend_static_allocator.h
index 5556256535..7516065707 100644
--- a/Zend/zend_static_allocator.h
+++ b/Zend/zend_static_allocator.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_stream.c b/Zend/zend_stream.c
index 835fdbbd7e..6d306b337e 100644
--- a/Zend/zend_stream.c
+++ b/Zend/zend_stream.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_stream.h b/Zend/zend_stream.h
index a65d258957..5306b496f9 100644
--- a/Zend/zend_stream.h
+++ b/Zend/zend_stream.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_string.c b/Zend/zend_string.c
index ff7ee3fd81..9b7005df59 100644
--- a/Zend/zend_string.c
+++ b/Zend/zend_string.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_string.h b/Zend/zend_string.h
index ebf8c816c1..5f823775e4 100644
--- a/Zend/zend_string.h
+++ b/Zend/zend_string.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_strtod.c b/Zend/zend_strtod.c
index d6e5ccf960..4546614cfd 100644
--- a/Zend/zend_strtod.c
+++ b/Zend/zend_strtod.c
@@ -267,8 +267,7 @@ BEGIN_EXTERN_C()
#if defined(IEEE_LITTLE_ENDIAN) + defined(IEEE_BIG_ENDIAN) + defined(VAX) + \
defined(IBM) != 1
- Exactly one of IEEE_LITTLE_ENDIAN IEEE_BIG_ENDIAN, VAX, or
- IBM should be defined.
+#error "Exactly one of IEEE_LITTLE_ENDIAN IEEE_BIG_ENDIAN, VAX, or IBM should be defined."
#endif
typedef union {
diff --git a/Zend/zend_strtod.h b/Zend/zend_strtod.h
index aac17cea14..ba312d4f1b 100644
--- a/Zend/zend_strtod.h
+++ b/Zend/zend_strtod.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ts_hash.c b/Zend/zend_ts_hash.c
index f517fe8560..6f2eb8185c 100644
--- a/Zend/zend_ts_hash.c
+++ b/Zend/zend_ts_hash.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_ts_hash.h b/Zend/zend_ts_hash.h
index 9a849e15ae..25117aa784 100644
--- a/Zend/zend_ts_hash.h
+++ b/Zend/zend_ts_hash.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_types.h b/Zend/zend_types.h
index 9cdf31fb34..e5d5bbb500 100644
--- a/Zend/zend_types.h
+++ b/Zend/zend_types.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_variables.c b/Zend/zend_variables.c
index c0e1849eef..b875445120 100644
--- a/Zend/zend_variables.c
+++ b/Zend/zend_variables.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_variables.h b/Zend/zend_variables.h
index e52dbd7853..30f170bfbe 100644
--- a/Zend/zend_variables.h
+++ b/Zend/zend_variables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_vm.h b/Zend/zend_vm.h
index c406c1a891..078be15b74 100644
--- a/Zend/zend_vm.h
+++ b/Zend/zend_vm.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/Zend/zend_vm_def.h b/Zend/zend_vm_def.h
index c2c3ae5219..03cc9c45a0 100644
--- a/Zend/zend_vm_def.h
+++ b/Zend/zend_vm_def.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1166,28 +1166,17 @@ ZEND_VM_HANDLER(81, ZEND_FETCH_DIM_R, CONST|TMP|VAR|CV, CONST|TMP|VAR|CV)
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- OP1_TYPE != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (OP1_TYPE == IS_TMP_VAR || OP1_TYPE == IS_CONST) {
- zval *container = GET_OP1_ZVAL_PTR(BP_VAR_R);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, GET_OP2_ZVAL_PTR(BP_VAR_R), OP2_TYPE, BP_VAR_R TSRMLS_CC);
- FREE_OP2();
- FREE_OP1();
- } else {
- container = GET_OP1_ZVAL_PTR_PTR(BP_VAR_R);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, GET_OP2_ZVAL_PTR(BP_VAR_R), OP2_TYPE, BP_VAR_R TSRMLS_CC);
- FREE_OP2();
- FREE_OP1_VAR_PTR();
+ if (OP1_TYPE == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
+ container = GET_OP1_ZVAL_PTR(BP_VAR_R);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, GET_OP2_ZVAL_PTR(BP_VAR_R), OP2_TYPE, BP_VAR_R TSRMLS_CC);
+ FREE_OP2();
+ FREE_OP1();
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -1252,13 +1241,13 @@ ZEND_VM_HANDLER(90, ZEND_FETCH_DIM_IS, VAR|CV, CONST|TMP|VAR|CV)
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = GET_OP1_ZVAL_PTR_PTR(BP_VAR_IS);
+ container = GET_OP1_ZVAL_PTR(BP_VAR_IS);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, GET_OP2_ZVAL_PTR(BP_VAR_R), OP2_TYPE, BP_VAR_IS TSRMLS_CC);
FREE_OP2();
- FREE_OP1_VAR_PTR();
+ FREE_OP1();
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -1267,12 +1256,12 @@ ZEND_VM_HANDLER(93, ZEND_FETCH_DIM_FUNC_ARG, VAR|CV, CONST|TMP|VAR|UNUSED|CV)
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = GET_OP1_ZVAL_PTR_PTR(BP_VAR_W);
+ zval **container = GET_OP1_ZVAL_PTR_PTR(BP_VAR_W);
+
if (OP1_TYPE == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -1280,15 +1269,19 @@ ZEND_VM_HANDLER(93, ZEND_FETCH_DIM_FUNC_ARG, VAR|CV, CONST|TMP|VAR|UNUSED|CV)
if (OP1_TYPE == IS_VAR && OP1_FREE && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+ FREE_OP2();
+ FREE_OP1_VAR_PTR();
} else {
+ zval *container;
+
if (OP2_TYPE == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = GET_OP1_ZVAL_PTR_PTR(BP_VAR_R);
+ container = GET_OP1_ZVAL_PTR(BP_VAR_R);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, GET_OP2_ZVAL_PTR(BP_VAR_R), OP2_TYPE, BP_VAR_R TSRMLS_CC);
+ FREE_OP2();
+ FREE_OP1();
}
- FREE_OP2();
- FREE_OP1_VAR_PTR();
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -5360,11 +5353,15 @@ ZEND_VM_HANDLER(160, ZEND_YIELD, CONST|TMP|VAR|CV|UNUSED, CONST|TMP|VAR|CV|UNUSE
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
diff --git a/Zend/zend_vm_execute.h b/Zend/zend_vm_execute.h
index b21f6bf895..511a40b37e 100644
--- a/Zend/zend_vm_execute.h
+++ b/Zend/zend_vm_execute.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -3483,27 +3483,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CONST_CONST_HANDLER(ZEND_OPCODE_
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CONST != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
+ if (IS_CONST == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = opline->op1.zv;
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
- if (IS_CONST == IS_TMP_VAR || IS_CONST == IS_CONST) {
- zval *container = opline->op1.zv;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
-
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
-
- }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -4209,11 +4198,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CONST_CONST_HANDLER(ZEND_OPCODE_HANDLE
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -4506,27 +4499,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CONST_TMP_HANDLER(ZEND_OPCODE_HA
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CONST != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_CONST == IS_TMP_VAR || IS_CONST == IS_CONST) {
- zval *container = opline->op1.zv;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
-
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
-
+ if (IS_CONST == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = opline->op1.zv;
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op2.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -4909,11 +4891,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CONST_TMP_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -5370,27 +5356,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CONST_VAR_HANDLER(ZEND_OPCODE_HA
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CONST != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_CONST == IS_TMP_VAR || IS_CONST == IS_CONST) {
- zval *container = opline->op1.zv;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-
+ if (IS_CONST == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = opline->op1.zv;
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -5937,11 +5912,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CONST_VAR_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -6658,11 +6637,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CONST_UNUSED_HANDLER(ZEND_OPCODE_HANDL
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -6955,27 +6938,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CONST_CV_HANDLER(ZEND_OPCODE_HAN
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CONST != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
+ if (IS_CONST == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = opline->op1.zv;
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
- if (IS_CONST == IS_TMP_VAR || IS_CONST == IS_CONST) {
- zval *container = opline->op1.zv;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
-
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
-
- }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -7417,11 +7389,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CONST_CV_HANDLER(ZEND_OPCODE_HANDLER_A
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -8864,28 +8840,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_TMP_CONST_HANDLER(ZEND_OPCODE_HA
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_TMP_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_TMP_VAR == IS_TMP_VAR || IS_TMP_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
- zval_dtor(free_op1.var);
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
-
+ if (IS_TMP_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op1.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -9455,11 +9420,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_TMP_CONST_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -9752,28 +9721,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_TMP_TMP_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_TMP_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_TMP_VAR == IS_TMP_VAR || IS_TMP_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
- zval_dtor(free_op1.var);
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
-
+ if (IS_TMP_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
+ container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op2.var);
+ zval_dtor(free_op1.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -10157,11 +10115,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_TMP_TMP_HANDLER(ZEND_OPCODE_HANDLER_AR
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -10618,28 +10580,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_TMP_VAR_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_TMP_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_TMP_VAR == IS_TMP_VAR || IS_TMP_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
- zval_dtor(free_op1.var);
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-
+ if (IS_TMP_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
+ container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ zval_dtor(free_op1.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -11187,11 +11138,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_TMP_VAR_HANDLER(ZEND_OPCODE_HANDLER_AR
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -11767,11 +11722,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_TMP_UNUSED_HANDLER(ZEND_OPCODE_HANDLER
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -12064,28 +12023,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_TMP_CV_HANDLER(ZEND_OPCODE_HANDL
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_TMP_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_TMP_VAR == IS_TMP_VAR || IS_TMP_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
- zval_dtor(free_op1.var);
- } else {
- container = NULL;
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
-
+ if (IS_TMP_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_tmp(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op1.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -12466,11 +12414,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_TMP_CV_HANDLER(ZEND_OPCODE_HANDLER_ARG
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -14771,28 +14723,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_VAR_CONST_HANDLER(ZEND_OPCODE_HA
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_VAR == IS_TMP_VAR || IS_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
- } else {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (IS_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -14857,10 +14798,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_VAR_CONST_HANDLER(ZEND_OPCODE_H
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_IS TSRMLS_CC);
if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
@@ -14872,12 +14813,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_CONST_HANDLER(ZEND_OP
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+
if (IS_VAR == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -14885,15 +14826,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_CONST_HANDLER(ZEND_OP
if (IS_VAR == IS_VAR && (free_op1.var != NULL) && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
} else {
+ zval *container;
+
if (IS_CONST == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
- }
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -16360,11 +16305,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_VAR_CONST_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -17120,28 +17069,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_VAR_TMP_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_VAR == IS_TMP_VAR || IS_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
- } else {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (IS_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op2.var);
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -17206,10 +17144,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_VAR_TMP_HANDLER(ZEND_OPCODE_HAN
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_IS TSRMLS_CC);
zval_dtor(free_op2.var);
if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
@@ -17221,12 +17159,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_TMP_HANDLER(ZEND_OPCO
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+
if (IS_VAR == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -17234,15 +17172,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_TMP_HANDLER(ZEND_OPCO
if (IS_VAR == IS_VAR && (free_op1.var != NULL) && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+ zval_dtor(free_op2.var);
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
} else {
+ zval *container;
+
if (IS_TMP_VAR == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op2.var);
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
}
- zval_dtor(free_op2.var);
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -18452,11 +18394,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_VAR_TMP_HANDLER(ZEND_OPCODE_HANDLER_AR
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -19376,28 +19322,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_VAR_VAR_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_VAR == IS_TMP_VAR || IS_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
- } else {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (IS_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -19462,10 +19397,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_VAR_VAR_HANDLER(ZEND_OPCODE_HAN
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_IS TSRMLS_CC);
if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
@@ -19477,12 +19412,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_VAR_HANDLER(ZEND_OPCO
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+
if (IS_VAR == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -19490,15 +19425,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_VAR_HANDLER(ZEND_OPCO
if (IS_VAR == IS_VAR && (free_op1.var != NULL) && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
} else {
+ zval *container;
+
if (IS_VAR == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
}
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -20927,11 +20866,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_VAR_VAR_HANDLER(ZEND_OPCODE_HANDLER_AR
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -21424,12 +21367,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_UNUSED_HANDLER(ZEND_O
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+
if (IS_VAR == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -21437,15 +21380,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_UNUSED_HANDLER(ZEND_O
if (IS_VAR == IS_VAR && (free_op1.var != NULL) && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
} else {
+ zval *container;
+
if (IS_UNUSED == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, NULL, IS_UNUSED, BP_VAR_R TSRMLS_CC);
- }
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -22075,11 +22022,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_VAR_UNUSED_HANDLER(ZEND_OPCODE_HANDLER
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -22834,28 +22785,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_VAR_CV_HANDLER(ZEND_OPCODE_HANDL
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_VAR != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_VAR == IS_TMP_VAR || IS_VAR == IS_CONST) {
- zval *container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
- } else {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (IS_VAR == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -22920,10 +22860,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_VAR_CV_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_IS TSRMLS_CC);
if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
@@ -22935,12 +22875,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_CV_HANDLER(ZEND_OPCOD
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+
if (IS_VAR == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -22948,15 +22888,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_VAR_CV_HANDLER(ZEND_OPCOD
if (IS_VAR == IS_VAR && (free_op1.var != NULL) && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
} else {
+ zval *container;
+
if (IS_CV == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
+ container = _get_zval_ptr_var(opline->op1.var, execute_data, &free_op1 TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
- }
- if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ if (free_op1.var) {zval_ptr_dtor(&free_op1.var);};
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -24216,11 +24160,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_VAR_CV_HANDLER(ZEND_OPCODE_HANDLER_ARG
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -25714,11 +25662,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_UNUSED_CONST_HANDLER(ZEND_OPCODE_HANDL
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -27028,11 +26980,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_UNUSED_TMP_HANDLER(ZEND_OPCODE_HANDLER
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -28343,11 +28299,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_UNUSED_VAR_HANDLER(ZEND_OPCODE_HANDLER
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -28765,11 +28725,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_UNUSED_UNUSED_HANDLER(ZEND_OPCODE_HAND
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -30076,11 +30040,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_UNUSED_CV_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -32213,28 +32181,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CV_CONST_HANDLER(ZEND_OPCODE_HAN
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CV != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
+ if (IS_CV == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
- if (IS_CV == IS_TMP_VAR || IS_CV == IS_CONST) {
- zval *container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
-
-
- } else {
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
- }
-
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -32298,10 +32255,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_CV_CONST_HANDLER(ZEND_OPCODE_HA
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_IS TSRMLS_CC);
@@ -32313,12 +32270,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_CONST_HANDLER(ZEND_OPC
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+
if (IS_CV == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -32326,15 +32283,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_CONST_HANDLER(ZEND_OPC
if (IS_CV == IS_VAR && 0 && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+
} else {
+ zval *container;
+
if (IS_CONST == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, opline->op2.zv, IS_CONST, BP_VAR_R TSRMLS_CC);
- }
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -33568,11 +33529,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CV_CONST_HANDLER(ZEND_OPCODE_HANDLER_A
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -34327,27 +34292,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CV_TMP_HANDLER(ZEND_OPCODE_HANDL
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CV != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_CV == IS_TMP_VAR || IS_CV == IS_CONST) {
- zval *container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
-
- } else {
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- zval_dtor(free_op2.var);
-
+ if (IS_CV == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
+ zval_dtor(free_op2.var);
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -34412,10 +34366,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_CV_TMP_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_IS TSRMLS_CC);
zval_dtor(free_op2.var);
@@ -34427,12 +34381,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_TMP_HANDLER(ZEND_OPCOD
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+
if (IS_CV == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -34440,15 +34394,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_TMP_HANDLER(ZEND_OPCOD
if (IS_CV == IS_VAR && 0 && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+ zval_dtor(free_op2.var);
+
} else {
+ zval *container;
+
if (IS_TMP_VAR == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_tmp(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_TMP_VAR, BP_VAR_R TSRMLS_CC);
- }
- zval_dtor(free_op2.var);
+ zval_dtor(free_op2.var);
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -35522,11 +35480,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CV_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARG
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -36445,27 +36407,16 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CV_VAR_HANDLER(ZEND_OPCODE_HANDL
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CV != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
- }
-
- if (IS_CV == IS_TMP_VAR || IS_CV == IS_CONST) {
- zval *container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-
- } else {
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-
+ if (IS_CV == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
@@ -36530,10 +36481,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_CV_VAR_HANDLER(ZEND_OPCODE_HAND
{
USE_OPLINE
zend_free_op free_op2;
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_IS TSRMLS_CC);
if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
@@ -36545,12 +36496,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_VAR_HANDLER(ZEND_OPCOD
{
USE_OPLINE
zend_free_op free_op1, free_op2;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+
if (IS_CV == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -36558,15 +36509,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_VAR_HANDLER(ZEND_OPCOD
if (IS_CV == IS_VAR && 0 && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+
} else {
+ zval *container;
+
if (IS_VAR == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_var(opline->op2.var, execute_data, &free_op2 TSRMLS_CC), IS_VAR, BP_VAR_R TSRMLS_CC);
- }
- if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -37858,11 +37813,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CV_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARG
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -38353,12 +38312,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_UNUSED_HANDLER(ZEND_OP
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+
if (IS_CV == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -38366,15 +38325,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_UNUSED_HANDLER(ZEND_OP
if (IS_CV == IS_VAR && 0 && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+
} else {
+ zval *container;
+
if (IS_UNUSED == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, NULL, IS_UNUSED, BP_VAR_R TSRMLS_CC);
- }
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -38858,11 +38821,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CV_UNUSED_HANDLER(ZEND_OPCODE_HANDLER_
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
@@ -39616,28 +39583,17 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_R_SPEC_CV_CV_HANDLER(ZEND_OPCODE_HANDLE
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- if ((opline->extended_value & ZEND_FETCH_ADD_LOCK) &&
- IS_CV != IS_CV &&
- EX_T(opline->op1.var).var.ptr_ptr) {
- PZVAL_LOCK(*EX_T(opline->op1.var).var.ptr_ptr);
+ if (IS_CV == IS_VAR && (opline->extended_value & ZEND_FETCH_ADD_LOCK)) {
+ PZVAL_LOCK(EX_T(opline->op1.var).var.ptr);
}
-
- if (IS_CV == IS_TMP_VAR || IS_CV == IS_CONST) {
- zval *container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), &container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
-
-
- } else {
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
- zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
- }
-
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -39701,10 +39657,10 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_IS_SPEC_CV_CV_HANDLER(ZEND_OPCODE_HANDL
{
USE_OPLINE
- zval **container;
+ zval *container;
SAVE_OPLINE();
- container = _get_zval_ptr_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_IS(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_IS TSRMLS_CC);
@@ -39716,12 +39672,12 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_CV_HANDLER(ZEND_OPCODE
{
USE_OPLINE
zend_free_op free_op1;
- zval **container;
SAVE_OPLINE();
if (ARG_SHOULD_BE_SENT_BY_REF(EX(call)->fbc, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
- container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+ zval **container = _get_zval_ptr_ptr_cv_BP_VAR_W(execute_data, opline->op1.var TSRMLS_CC);
+
if (IS_CV == IS_VAR && UNEXPECTED(container == NULL)) {
zend_error_noreturn(E_ERROR, "Cannot use string offset as an array");
}
@@ -39729,15 +39685,19 @@ static int ZEND_FASTCALL ZEND_FETCH_DIM_FUNC_ARG_SPEC_CV_CV_HANDLER(ZEND_OPCODE
if (IS_CV == IS_VAR && 0 && READY_TO_DESTROY(free_op1.var)) {
EXTRACT_ZVAL_PTR(&EX_T(opline->result.var));
}
+
+
} else {
+ zval *container;
+
if (IS_CV == IS_UNUSED) {
zend_error_noreturn(E_ERROR, "Cannot use [] for reading");
}
- container = _get_zval_ptr_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
+ container = _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op1.var TSRMLS_CC);
zend_fetch_dimension_address_read(&EX_T(opline->result.var), container, _get_zval_ptr_cv_BP_VAR_R(execute_data, opline->op2.var TSRMLS_CC), IS_CV, BP_VAR_R TSRMLS_CC);
- }
+ }
CHECK_EXCEPTION();
ZEND_VM_NEXT_OPCODE();
}
@@ -40860,11 +40820,15 @@ static int ZEND_FASTCALL ZEND_YIELD_SPEC_CV_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS
ZVAL_LONG(generator->key, generator->largest_used_integer_key);
}
- /* If a value is sent it should go into the result var */
- generator->send_target = &EX_T(opline->result.var);
-
- /* Initialize the sent value to NULL */
- EX_T(opline->result.var).tmp_var = EG(uninitialized_zval);
+ if (RETURN_VALUE_USED(opline)) {
+ /* If the return value of yield is used set the send
+ * target and initialize it to NULL */
+ generator->send_target = &EX_T(opline->result.var).var.ptr;
+ Z_ADDREF(EG(uninitialized_zval));
+ EX_T(opline->result.var).var.ptr = &EG(uninitialized_zval);
+ } else {
+ generator->send_target = NULL;
+ }
/* We increment to the next op, so we are at the correct position when the
* generator is resumed. */
diff --git a/Zend/zend_vm_gen.php b/Zend/zend_vm_gen.php
index 9b2877b996..5da3405dd7 100644
--- a/Zend/zend_vm_gen.php
+++ b/Zend/zend_vm_gen.php
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -24,7 +24,7 @@ $header_text = <<< DATA
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -884,9 +884,15 @@ function gen_executor($f, $skl, $spec, $kind, $executor_name, $initializer_name,
out($f,"#undef CHECK_EXCEPTION\n");
out($f,"#undef HANDLE_EXCEPTION\n");
out($f,"#undef HANDLE_EXCEPTION_LEAVE\n");
- out($f,"#define CHECK_EXCEPTION() if (UNEXPECTED(EG(exception) != NULL)) goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
- out($f,"#define HANDLE_EXCEPTION() goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
- out($f,"#define HANDLE_EXCEPTION_LEAVE() goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
+ if (ZEND_VM_SPEC) {
+ out($f,"#define CHECK_EXCEPTION() if (UNEXPECTED(EG(exception) != NULL)) goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
+ out($f,"#define HANDLE_EXCEPTION() goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
+ out($f,"#define HANDLE_EXCEPTION_LEAVE() goto ZEND_HANDLE_EXCEPTION_SPEC_HANDLER\n");
+ } else {
+ out($f,"#define CHECK_EXCEPTION() if (UNEXPECTED(EG(exception) != NULL)) goto ZEND_HANDLE_EXCEPTION_HANDLER\n");
+ out($f,"#define HANDLE_EXCEPTION() goto ZEND_HANDLE_EXCEPTION_HANDLER\n");
+ out($f,"#define HANDLE_EXCEPTION_LEAVE() goto ZEND_HANDLE_EXCEPTION_HANDLER\n");
+ }
out($f,"#define LOAD_REGS()\n");
out($f,"#define ZEND_VM_CONTINUE() goto *(void**)(OPLINE->handler)\n");
out($f,"#define ZEND_VM_RETURN() EG(in_execution) = original_in_execution; return\n");
@@ -1174,14 +1180,40 @@ function gen_vm($def, $skel) {
// Insert header
out($f, $GLOBALS['header_text']);
+ fputs($f, "#ifndef ZEND_VM_OPCODES_H\n#define ZEND_VM_OPCODES_H\n\n");
+ fputs($f, "ZEND_API const char *zend_get_opcode_name(zend_uchar opcode);\n\n");
+
foreach ($opcodes as $code => $dsc) {
$code = str_pad((string)$code,$code_len," ",STR_PAD_LEFT);
$op = str_pad($dsc["op"],$max_opcode_len);
fputs($f,"#define $op $code\n");
}
+
+ fputs($f, "\n#endif");
fclose($f);
echo "zend_vm_opcodes.h generated successfully.\n";
+ // zend_vm_opcodes.c
+ $f = fopen(__DIR__ . "/zend_vm_opcodes.c", "w+") or die("ERROR: Cannot create zend_vm_opcodes.c\n");
+
+ // Insert header
+ out($f, $GLOBALS['header_text']);
+ fputs($f,"#include <stdio.h>\n");
+ fputs($f,"#include <zend.h>\n\n");
+
+ fputs($f,"const char *zend_vm_opcodes_map[".($max_opcode + 1)."] = {\n");
+ for ($i = 0; $i <= $max_opcode; $i++) {
+ fputs($f,"\t".(isset($opcodes[$i]["op"])?'"'.$opcodes[$i]["op"].'"':"NULL").",\n");
+ }
+ fputs($f, "};\n\n");
+
+ fputs($f, "ZEND_API const char* zend_get_opcode_name(zend_uchar opcode) {\n");
+ fputs($f, "\treturn zend_vm_opcodes_map[opcode];\n");
+ fputs($f, "}\n");
+
+ fclose($f);
+ echo "zend_vm_opcodes.c generated successfully.\n";
+
// Generate zend_vm_execute.h
$f = fopen(__DIR__ . "/zend_vm_execute.h", "w+") or die("ERROR: Cannot create zend_vm_execute.h\n");
$executor_file = realpath(__DIR__ . "/zend_vm_execute.h");
@@ -1205,7 +1237,7 @@ function gen_vm($def, $skel) {
out($f, "# pragma warning(once : 6285)\n");
// Suppress (<non-zero constant> || <expression>) warnings on windows
out($f, "# pragma warning(once : 6286)\n");
- // Suppress constant with constant comparsion warnings on windows
+ // Suppress constant with constant comparison warnings on windows
out($f, "# pragma warning(once : 6326)\n");
}
out($f, "#endif\n");
diff --git a/Zend/zend_vm_opcodes.c b/Zend/zend_vm_opcodes.c
new file mode 100644
index 0000000000..05c9aeb140
--- /dev/null
+++ b/Zend/zend_vm_opcodes.c
@@ -0,0 +1,193 @@
+/*
+ +----------------------------------------------------------------------+
+ | Zend Engine |
+ +----------------------------------------------------------------------+
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+ +----------------------------------------------------------------------+
+ | This source file is subject to version 2.00 of the Zend license, |
+ | that is bundled with this package in the file LICENSE, and is |
+ | available through the world-wide-web at the following url: |
+ | http://www.zend.com/license/2_00.txt. |
+ | If you did not receive a copy of the Zend license and are unable to |
+ | obtain it through the world-wide-web, please send a note to |
+ | license@zend.com so we can mail you a copy immediately. |
+ +----------------------------------------------------------------------+
+ | Authors: Andi Gutmans <andi@zend.com> |
+ | Zeev Suraski <zeev@zend.com> |
+ | Dmitry Stogov <dmitry@zend.com> |
+ +----------------------------------------------------------------------+
+*/
+
+#include <stdio.h>
+#include <zend.h>
+
+const char *zend_vm_opcodes_map[164] = {
+ "ZEND_NOP",
+ "ZEND_ADD",
+ "ZEND_SUB",
+ "ZEND_MUL",
+ "ZEND_DIV",
+ "ZEND_MOD",
+ "ZEND_SL",
+ "ZEND_SR",
+ "ZEND_CONCAT",
+ "ZEND_BW_OR",
+ "ZEND_BW_AND",
+ "ZEND_BW_XOR",
+ "ZEND_BW_NOT",
+ "ZEND_BOOL_NOT",
+ "ZEND_BOOL_XOR",
+ "ZEND_IS_IDENTICAL",
+ "ZEND_IS_NOT_IDENTICAL",
+ "ZEND_IS_EQUAL",
+ "ZEND_IS_NOT_EQUAL",
+ "ZEND_IS_SMALLER",
+ "ZEND_IS_SMALLER_OR_EQUAL",
+ "ZEND_CAST",
+ "ZEND_QM_ASSIGN",
+ "ZEND_ASSIGN_ADD",
+ "ZEND_ASSIGN_SUB",
+ "ZEND_ASSIGN_MUL",
+ "ZEND_ASSIGN_DIV",
+ "ZEND_ASSIGN_MOD",
+ "ZEND_ASSIGN_SL",
+ "ZEND_ASSIGN_SR",
+ "ZEND_ASSIGN_CONCAT",
+ "ZEND_ASSIGN_BW_OR",
+ "ZEND_ASSIGN_BW_AND",
+ "ZEND_ASSIGN_BW_XOR",
+ "ZEND_PRE_INC",
+ "ZEND_PRE_DEC",
+ "ZEND_POST_INC",
+ "ZEND_POST_DEC",
+ "ZEND_ASSIGN",
+ "ZEND_ASSIGN_REF",
+ "ZEND_ECHO",
+ "ZEND_PRINT",
+ "ZEND_JMP",
+ "ZEND_JMPZ",
+ "ZEND_JMPNZ",
+ "ZEND_JMPZNZ",
+ "ZEND_JMPZ_EX",
+ "ZEND_JMPNZ_EX",
+ "ZEND_CASE",
+ "ZEND_SWITCH_FREE",
+ "ZEND_BRK",
+ "ZEND_CONT",
+ "ZEND_BOOL",
+ "ZEND_INIT_STRING",
+ "ZEND_ADD_CHAR",
+ "ZEND_ADD_STRING",
+ "ZEND_ADD_VAR",
+ "ZEND_BEGIN_SILENCE",
+ "ZEND_END_SILENCE",
+ "ZEND_INIT_FCALL_BY_NAME",
+ "ZEND_DO_FCALL",
+ "ZEND_DO_FCALL_BY_NAME",
+ "ZEND_RETURN",
+ "ZEND_RECV",
+ "ZEND_RECV_INIT",
+ "ZEND_SEND_VAL",
+ "ZEND_SEND_VAR",
+ "ZEND_SEND_REF",
+ "ZEND_NEW",
+ "ZEND_INIT_NS_FCALL_BY_NAME",
+ "ZEND_FREE",
+ "ZEND_INIT_ARRAY",
+ "ZEND_ADD_ARRAY_ELEMENT",
+ "ZEND_INCLUDE_OR_EVAL",
+ "ZEND_UNSET_VAR",
+ "ZEND_UNSET_DIM",
+ "ZEND_UNSET_OBJ",
+ "ZEND_FE_RESET",
+ "ZEND_FE_FETCH",
+ "ZEND_EXIT",
+ "ZEND_FETCH_R",
+ "ZEND_FETCH_DIM_R",
+ "ZEND_FETCH_OBJ_R",
+ "ZEND_FETCH_W",
+ "ZEND_FETCH_DIM_W",
+ "ZEND_FETCH_OBJ_W",
+ "ZEND_FETCH_RW",
+ "ZEND_FETCH_DIM_RW",
+ "ZEND_FETCH_OBJ_RW",
+ "ZEND_FETCH_IS",
+ "ZEND_FETCH_DIM_IS",
+ "ZEND_FETCH_OBJ_IS",
+ "ZEND_FETCH_FUNC_ARG",
+ "ZEND_FETCH_DIM_FUNC_ARG",
+ "ZEND_FETCH_OBJ_FUNC_ARG",
+ "ZEND_FETCH_UNSET",
+ "ZEND_FETCH_DIM_UNSET",
+ "ZEND_FETCH_OBJ_UNSET",
+ "ZEND_FETCH_DIM_TMP_VAR",
+ "ZEND_FETCH_CONSTANT",
+ "ZEND_GOTO",
+ "ZEND_EXT_STMT",
+ "ZEND_EXT_FCALL_BEGIN",
+ "ZEND_EXT_FCALL_END",
+ "ZEND_EXT_NOP",
+ "ZEND_TICKS",
+ "ZEND_SEND_VAR_NO_REF",
+ "ZEND_CATCH",
+ "ZEND_THROW",
+ "ZEND_FETCH_CLASS",
+ "ZEND_CLONE",
+ "ZEND_RETURN_BY_REF",
+ "ZEND_INIT_METHOD_CALL",
+ "ZEND_INIT_STATIC_METHOD_CALL",
+ "ZEND_ISSET_ISEMPTY_VAR",
+ "ZEND_ISSET_ISEMPTY_DIM_OBJ",
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ "ZEND_PRE_INC_OBJ",
+ "ZEND_PRE_DEC_OBJ",
+ "ZEND_POST_INC_OBJ",
+ "ZEND_POST_DEC_OBJ",
+ "ZEND_ASSIGN_OBJ",
+ NULL,
+ "ZEND_INSTANCEOF",
+ "ZEND_DECLARE_CLASS",
+ "ZEND_DECLARE_INHERITED_CLASS",
+ "ZEND_DECLARE_FUNCTION",
+ "ZEND_RAISE_ABSTRACT_ERROR",
+ "ZEND_DECLARE_CONST",
+ "ZEND_ADD_INTERFACE",
+ "ZEND_DECLARE_INHERITED_CLASS_DELAYED",
+ "ZEND_VERIFY_ABSTRACT_CLASS",
+ "ZEND_ASSIGN_DIM",
+ "ZEND_ISSET_ISEMPTY_PROP_OBJ",
+ "ZEND_HANDLE_EXCEPTION",
+ "ZEND_USER_OPCODE",
+ NULL,
+ "ZEND_JMP_SET",
+ "ZEND_DECLARE_LAMBDA_FUNCTION",
+ "ZEND_ADD_TRAIT",
+ "ZEND_BIND_TRAITS",
+ "ZEND_SEPARATE",
+ "ZEND_QM_ASSIGN_VAR",
+ "ZEND_JMP_SET_VAR",
+ "ZEND_DISCARD_EXCEPTION",
+ "ZEND_YIELD",
+ "ZEND_GENERATOR_RETURN",
+ "ZEND_FAST_CALL",
+ "ZEND_FAST_RET",
+};
+
+ZEND_API const char* zend_get_opcode_name(zend_uchar opcode) {
+ return zend_vm_opcodes_map[opcode];
+}
diff --git a/Zend/zend_vm_opcodes.h b/Zend/zend_vm_opcodes.h
index 859258a440..911eee4434 100644
--- a/Zend/zend_vm_opcodes.h
+++ b/Zend/zend_vm_opcodes.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend Engine |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 Zend Technologies Ltd. (http://www.zend.com) |
+ | Copyright (c) 1998-2014 Zend Technologies Ltd. (http://www.zend.com) |
+----------------------------------------------------------------------+
| This source file is subject to version 2.00 of the Zend license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -18,6 +18,11 @@
+----------------------------------------------------------------------+
*/
+#ifndef ZEND_VM_OPCODES_H
+#define ZEND_VM_OPCODES_H
+
+ZEND_API const char *zend_get_opcode_name(zend_uchar opcode);
+
#define ZEND_NOP 0
#define ZEND_ADD 1
#define ZEND_SUB 2
@@ -164,3 +169,5 @@
#define ZEND_GENERATOR_RETURN 161
#define ZEND_FAST_CALL 162
#define ZEND_FAST_RET 163
+
+#endif \ No newline at end of file
diff --git a/build/buildcheck.sh b/build/buildcheck.sh
index 8754e3a292..8ff3531825 100755
--- a/build/buildcheck.sh
+++ b/build/buildcheck.sh
@@ -33,14 +33,14 @@ ac_version=`$PHP_AUTOCONF --version 2>/dev/null|head -n 1|sed -e 's/^[^0-9]*//'
if test -z "$ac_version"; then
echo "buildconf: autoconf not found."
echo " You need autoconf version 2.59 or newer installed"
-echo " to build PHP from SVN."
+echo " to build PHP from Git."
exit 1
fi
IFS=.; set $ac_version; IFS=' '
if test "$1" = "2" -a "$2" -lt "59" || test "$1" -lt "2"; then
echo "buildconf: autoconf version $ac_version found."
echo " You need autoconf version 2.59 or newer installed"
-echo " to build PHP from SVN."
+echo " to build PHP from Git."
exit 1
else
echo "buildconf: autoconf version $ac_version (ok)"
diff --git a/configure.in b/configure.in
index 7e444b0ac4..13ff75d66f 100644
--- a/configure.in
+++ b/configure.in
@@ -119,7 +119,7 @@ int zend_sprintf(char *buffer, const char *format, ...);
PHP_MAJOR_VERSION=5
PHP_MINOR_VERSION=5
-PHP_RELEASE_VERSION=6
+PHP_RELEASE_VERSION=11
PHP_EXTRA_VERSION="-dev"
PHP_VERSION="$PHP_MAJOR_VERSION.$PHP_MINOR_VERSION.$PHP_RELEASE_VERSION$PHP_EXTRA_VERSION"
PHP_VERSION_ID=`expr [$]PHP_MAJOR_VERSION \* 10000 + [$]PHP_MINOR_VERSION \* 100 + [$]PHP_RELEASE_VERSION`
@@ -1467,7 +1467,7 @@ PHP_ADD_SOURCES(Zend, \
zend_ini_parser.c zend_ini_scanner.c \
zend_alloc.c zend_compile.c zend_constants.c zend_dynamic_array.c zend_dtrace.c \
zend_execute_API.c zend_highlight.c zend_llist.c \
- zend_opcode.c zend_operators.c zend_ptr_stack.c zend_stack.c \
+ zend_vm_opcodes.c zend_opcode.c zend_operators.c zend_ptr_stack.c zend_stack.c \
zend_variables.c zend.c zend_API.c zend_extensions.c zend_hash.c \
zend_list.c zend_indent.c zend_builtin_functions.c zend_sprintf.c \
zend_ini.c zend_qsort.c zend_multibyte.c zend_ts_hash.c zend_stream.c \
diff --git a/ext/bcmath/bcmath.c b/ext/bcmath/bcmath.c
index c5fbce94dd..9369897c7f 100644
--- a/ext/bcmath/bcmath.c
+++ b/ext/bcmath/bcmath.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/bcmath/php_bcmath.h b/ext/bcmath/php_bcmath.h
index 571993ed7b..a18e5287e6 100644
--- a/ext/bcmath/php_bcmath.h
+++ b/ext/bcmath/php_bcmath.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/bz2/bz2.c b/ext/bz2/bz2.c
index abe84fc316..2692b22586 100644
--- a/ext/bz2/bz2.c
+++ b/ext/bz2/bz2.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/bz2/bz2_filter.c b/ext/bz2/bz2_filter.c
index 1e7837b098..b31ab3c261 100644
--- a/ext/bz2/bz2_filter.c
+++ b/ext/bz2/bz2_filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/bz2/php_bz2.h b/ext/bz2/php_bz2.h
index 8b12eca357..21aa2683c9 100644
--- a/ext/bz2/php_bz2.h
+++ b/ext/bz2/php_bz2.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/calendar/cal_unix.c b/ext/calendar/cal_unix.c
index c65b046fc8..99adfd3563 100644
--- a/ext/calendar/cal_unix.c
+++ b/ext/calendar/cal_unix.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/calendar/calendar.c b/ext/calendar/calendar.c
index d881494cb5..34b34da371 100644
--- a/ext/calendar/calendar.c
+++ b/ext/calendar/calendar.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/calendar/easter.c b/ext/calendar/easter.c
index 1948ff9f0e..a999da044f 100644
--- a/ext/calendar/easter.c
+++ b/ext/calendar/easter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_com.c b/ext/com_dotnet/com_com.c
index fe48ee9e28..f77779d691 100644
--- a/ext/com_dotnet/com_com.c
+++ b/ext/com_dotnet/com_com.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_dotnet.c b/ext/com_dotnet/com_dotnet.c
index 7fbdae15cb..0aa1a2a9c7 100644
--- a/ext/com_dotnet/com_dotnet.c
+++ b/ext/com_dotnet/com_dotnet.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_extension.c b/ext/com_dotnet/com_extension.c
index 1257974697..e3b3abfe28 100644
--- a/ext/com_dotnet/com_extension.c
+++ b/ext/com_dotnet/com_extension.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_handlers.c b/ext/com_dotnet/com_handlers.c
index 4bdbf52f2b..c889c9a06a 100644
--- a/ext/com_dotnet/com_handlers.c
+++ b/ext/com_dotnet/com_handlers.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_iterator.c b/ext/com_dotnet/com_iterator.c
index ecf395b161..d6f22efcdf 100644
--- a/ext/com_dotnet/com_iterator.c
+++ b/ext/com_dotnet/com_iterator.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_misc.c b/ext/com_dotnet/com_misc.c
index 023c5b80ef..b65a6be85d 100644
--- a/ext/com_dotnet/com_misc.c
+++ b/ext/com_dotnet/com_misc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_olechar.c b/ext/com_dotnet/com_olechar.c
index e456df242d..a3e81978bd 100644
--- a/ext/com_dotnet/com_olechar.c
+++ b/ext/com_dotnet/com_olechar.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_persist.c b/ext/com_dotnet/com_persist.c
index 8953a4184c..aaddf9ce9a 100644
--- a/ext/com_dotnet/com_persist.c
+++ b/ext/com_dotnet/com_persist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_saproxy.c b/ext/com_dotnet/com_saproxy.c
index 5450370cd9..0d557e60ee 100644
--- a/ext/com_dotnet/com_saproxy.c
+++ b/ext/com_dotnet/com_saproxy.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_typeinfo.c b/ext/com_dotnet/com_typeinfo.c
index 482b9b84ab..4ec448e2e3 100644
--- a/ext/com_dotnet/com_typeinfo.c
+++ b/ext/com_dotnet/com_typeinfo.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_variant.c b/ext/com_dotnet/com_variant.c
index e153d35804..4e044b20b8 100644
--- a/ext/com_dotnet/com_variant.c
+++ b/ext/com_dotnet/com_variant.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/com_wrapper.c b/ext/com_dotnet/com_wrapper.c
index 355779e4ad..54b6fb9ae7 100644
--- a/ext/com_dotnet/com_wrapper.c
+++ b/ext/com_dotnet/com_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/php_com_dotnet.h b/ext/com_dotnet/php_com_dotnet.h
index 8771e27736..51f621bd5f 100644
--- a/ext/com_dotnet/php_com_dotnet.h
+++ b/ext/com_dotnet/php_com_dotnet.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/com_dotnet/php_com_dotnet_internal.h b/ext/com_dotnet/php_com_dotnet_internal.h
index 015de450cf..5dabdfb213 100644
--- a/ext/com_dotnet/php_com_dotnet_internal.h
+++ b/ext/com_dotnet/php_com_dotnet_internal.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ctype/ctype.c b/ext/ctype/ctype.c
index e2698f5e73..8f116b86d3 100644
--- a/ext/ctype/ctype.c
+++ b/ext/ctype/ctype.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ctype/php_ctype.h b/ext/ctype/php_ctype.h
index e1036b9d03..ab5ec44ec4 100644
--- a/ext/ctype/php_ctype.h
+++ b/ext/ctype/php_ctype.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/curl/curl_file.c b/ext/curl/curl_file.c
index 91dfd275b5..9f371df538 100644
--- a/ext/curl/curl_file.c
+++ b/ext/curl/curl_file.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/curl/interface.c b/ext/curl/interface.c
index 9fdb57cc4e..09e20d3a67 100644
--- a/ext/curl/interface.c
+++ b/ext/curl/interface.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -165,50 +165,62 @@ static void _php_curl_close(zend_rsrc_list_entry *rsrc TSRMLS_DC);
# define php_curl_ret(__ret) RETVAL_FALSE; return;
#endif
-static int php_curl_option_url(php_curl *ch, const char *url, const int len TSRMLS_DC) /* {{{ */
+static int php_curl_option_str(php_curl *ch, long option, const char *str, const int len, zend_bool make_copy TSRMLS_DC)
{
CURLcode error = CURLE_OK;
-#if LIBCURL_VERSION_NUM < 0x071100
- char *copystr = NULL;
+
+#if LIBCURL_VERSION_NUM >= 0x071100
+ if (make_copy) {
+#endif
+ char *copystr;
+
+ /* Strings passed to libcurl as 'char *' arguments, are copied by the library since 7.17.0 */
+ copystr = estrndup(str, len);
+ error = curl_easy_setopt(ch->cp, option, copystr);
+ zend_llist_add_element(&ch->to_free->str, &copystr);
+#if LIBCURL_VERSION_NUM >= 0x071100
+ } else {
+ error = curl_easy_setopt(ch->cp, option, str);
+ }
#endif
+
+ SAVE_CURL_ERROR(ch, error)
+
+ return error == CURLE_OK ? SUCCESS : FAILURE;
+}
+
+static int php_curl_option_url(php_curl *ch, const char *url, const int len TSRMLS_DC) /* {{{ */
+{
/* Disable file:// if open_basedir are used */
if (PG(open_basedir) && *PG(open_basedir)) {
#if LIBCURL_VERSION_NUM >= 0x071304
- error = curl_easy_setopt(ch->cp, CURLOPT_PROTOCOLS, CURLPROTO_ALL & ~CURLPROTO_FILE);
+ curl_easy_setopt(ch->cp, CURLOPT_PROTOCOLS, CURLPROTO_ALL & ~CURLPROTO_FILE);
#else
php_url *uri;
if (!(uri = php_url_parse_ex(url, len))) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid URL '%s'", url);
- return 0;
+ return FAILURE;
}
if (uri->scheme && !strncasecmp("file", uri->scheme, sizeof("file"))) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Protocol 'file' disabled in cURL");
php_url_free(uri);
- return 0;
+ return FAILURE;
}
php_url_free(uri);
#endif
}
- /* Strings passed to libcurl as 'char *' arguments, are copied by the library... NOTE: before 7.17.0 strings were not copied. */
-#if LIBCURL_VERSION_NUM >= 0x071100
- error = curl_easy_setopt(ch->cp, CURLOPT_URL, url);
-#else
- copystr = estrndup(url, len);
- error = curl_easy_setopt(ch->cp, CURLOPT_URL, copystr);
- zend_llist_add_element(&ch->to_free->str, &copystr);
-#endif
- return (error == CURLE_OK ? 1 : 0);
+ return php_curl_option_str(ch, CURLOPT_URL, url, len, 0 TSRMLS_CC);
}
/* }}} */
-int _php_curl_verify_handlers(php_curl *ch, int reporterror TSRMLS_DC) /* {{{ */
+void _php_curl_verify_handlers(php_curl *ch, int reporterror TSRMLS_DC) /* {{{ */
{
php_stream *stream;
if (!ch || !ch->handlers) {
- return 0;
+ return;
}
if (ch->handlers->std_err) {
@@ -265,7 +277,7 @@ int _php_curl_verify_handlers(php_curl *ch, int reporterror TSRMLS_DC) /* {{{ */
curl_easy_setopt(ch->cp, CURLOPT_FILE, (void *) ch);
}
}
- return 1;
+ return ;
}
/* }}} */
@@ -1941,7 +1953,7 @@ PHP_FUNCTION(curl_init)
_php_curl_set_default_options(ch);
if (url) {
- if (!php_curl_option_url(ch, url, url_len TSRMLS_CC)) {
+ if (php_curl_option_url(ch, url, url_len TSRMLS_CC) == FAILURE) {
_php_curl_close_ex(ch TSRMLS_CC);
RETURN_FALSE;
}
@@ -2058,7 +2070,7 @@ PHP_FUNCTION(curl_copy_handle)
}
/* }}} */
-static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *return_value TSRMLS_DC) /* {{{ */
+static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue TSRMLS_DC) /* {{{ */
{
CURLcode error=CURLE_OK;
@@ -2225,7 +2237,6 @@ static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *retu
if ((option == CURLOPT_PROTOCOLS || option == CURLOPT_REDIR_PROTOCOLS) &&
(PG(open_basedir) && *PG(open_basedir)) && (Z_LVAL_PP(zvalue) & CURLPROTO_FILE)) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "CURLPROTO_FILE cannot be activated when an open_basedir is set");
- RETVAL_FALSE;
return 1;
}
#endif
@@ -2240,14 +2251,10 @@ static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *retu
case CURLOPT_CAINFO:
case CURLOPT_CAPATH:
case CURLOPT_COOKIE:
- case CURLOPT_CUSTOMREQUEST:
case CURLOPT_EGDSOCKET:
- case CURLOPT_FTPPORT:
case CURLOPT_INTERFACE:
- case CURLOPT_PRIVATE:
case CURLOPT_PROXY:
case CURLOPT_PROXYUSERPWD:
- case CURLOPT_RANGE:
case CURLOPT_REFERER:
case CURLOPT_SSLCERTTYPE:
case CURLOPT_SSLENGINE:
@@ -2256,23 +2263,14 @@ static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *retu
case CURLOPT_SSLKEYPASSWD:
case CURLOPT_SSLKEYTYPE:
case CURLOPT_SSL_CIPHER_LIST:
- case CURLOPT_URL:
case CURLOPT_USERAGENT:
case CURLOPT_USERPWD:
-#if LIBCURL_VERSION_NUM >= 0x070d00 /* Available since 7.13.0 */
- case CURLOPT_FTP_ACCOUNT:
-#endif
#if LIBCURL_VERSION_NUM >= 0x070e01 /* Available since 7.14.1 */
case CURLOPT_COOKIELIST:
#endif
#if LIBCURL_VERSION_NUM >= 0x070f05 /* Available since 7.15.5 */
case CURLOPT_FTP_ALTERNATIVE_TO_USER:
#endif
-#if LIBCURL_VERSION_NUM >= 0x071004 /* Available since 7.16.4 */
- case CURLOPT_KRBLEVEL:
-#else
- case CURLOPT_KRB4LEVEL:
-#endif
#if LIBCURL_VERSION_NUM >= 0x071101 /* Available since 7.17.1 */
case CURLOPT_SSH_HOST_PUBLIC_KEY_MD5:
#endif
@@ -2287,7 +2285,6 @@ static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *retu
#endif
#if LIBCURL_VERSION_NUM >= 0x071400 /* Available since 7.20.0 */
case CURLOPT_MAIL_FROM:
- case CURLOPT_RTSP_SESSION_ID:
case CURLOPT_RTSP_STREAM_URI:
case CURLOPT_RTSP_TRANSPORT:
#endif
@@ -2309,32 +2306,44 @@ static int _php_curl_setopt(php_curl *ch, long option, zval **zvalue, zval *retu
#endif
{
convert_to_string_ex(zvalue);
- if (option == CURLOPT_URL) {
- if (!php_curl_option_url(ch, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue) TSRMLS_CC)) {
- RETVAL_FALSE;
- return 1;
- }
- } else {
- if (option == CURLOPT_PRIVATE) {
- char *copystr;
-#if LIBCURL_VERSION_NUM < 0x071100
-string_copy:
-#endif
- copystr = estrndup(Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue));
- error = curl_easy_setopt(ch->cp, option, copystr);
- zend_llist_add_element(&ch->to_free->str, &copystr);
- } else {
-#if LIBCURL_VERSION_NUM >= 0x071100
- /* Strings passed to libcurl as ’char *’ arguments, are copied by the library... NOTE: before 7.17.0 strings were not copied. */
- error = curl_easy_setopt(ch->cp, option, Z_STRVAL_PP(zvalue));
+ return php_curl_option_str(ch, option, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue), 0 TSRMLS_CC);
+ }
+
+ /* Curl nullable string options */
+ case CURLOPT_CUSTOMREQUEST:
+ case CURLOPT_FTPPORT:
+ case CURLOPT_RANGE:
+#if LIBCURL_VERSION_NUM >= 0x070d00 /* Available since 7.13.0 */
+ case CURLOPT_FTP_ACCOUNT:
+#endif
+#if LIBCURL_VERSION_NUM >= 0x071400 /* Available since 7.20.0 */
+ case CURLOPT_RTSP_SESSION_ID:
+#endif
+#if LIBCURL_VERSION_NUM >= 0x071004 /* Available since 7.16.4 */
+ case CURLOPT_KRBLEVEL:
#else
- goto string_copy;
+ case CURLOPT_KRB4LEVEL:
#endif
- }
+ {
+ if (Z_TYPE_PP(zvalue) == IS_NULL) {
+ error = curl_easy_setopt(ch->cp, option, NULL);
+ } else {
+ convert_to_string_ex(zvalue);
+ return php_curl_option_str(ch, option, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue), 0 TSRMLS_CC);
}
break;
}
+ /* Curl private option */
+ case CURLOPT_PRIVATE:
+ convert_to_string_ex(zvalue);
+ return php_curl_option_str(ch, option, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue), 1 TSRMLS_CC);
+
+ /* Curl url option */
+ case CURLOPT_URL:
+ convert_to_string_ex(zvalue);
+ return php_curl_option_url(ch, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue) TSRMLS_CC);
+
/* Curl file handle options */
case CURLOPT_FILE:
case CURLOPT_INFILE:
@@ -2346,18 +2355,15 @@ string_copy:
what = zend_fetch_resource(zvalue TSRMLS_CC, -1, "File-Handle", &type, 1, php_file_le_stream(), php_file_le_pstream());
if (!what) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
if (FAILURE == php_stream_cast((php_stream *) what, PHP_STREAM_AS_STDIO, (void *) &fp, REPORT_ERRORS)) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
if (!fp) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
error = CURLE_OK;
@@ -2373,8 +2379,7 @@ string_copy:
ch->handlers->write->stream = *zvalue;
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "the provided file handle is not writable");
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
break;
case CURLOPT_WRITEHEADER:
@@ -2388,8 +2393,7 @@ string_copy:
ch->handlers->write_header->stream = *zvalue;
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "the provided file handle is not writable");
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
break;
case CURLOPT_INFILE:
@@ -2410,8 +2414,7 @@ string_copy:
ch->handlers->std_err = *zvalue;
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "the provided file handle is not writable");
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
/* break omitted intentionally */
default:
@@ -2473,8 +2476,7 @@ string_copy:
#endif
}
php_error_docref(NULL TSRMLS_CC, E_WARNING, "You must pass either an object or an array with the %s argument", name);
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
for (zend_hash_internal_pointer_reset(ph);
@@ -2487,7 +2489,6 @@ string_copy:
slist = curl_slist_append(slist, Z_STRVAL_PP(current));
if (!slist) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not build curl_slist");
- RETVAL_FALSE;
return 1;
}
}
@@ -2507,8 +2508,7 @@ string_copy:
if (PG(open_basedir) && *PG(open_basedir)) {
if (Z_LVAL_PP(zvalue) != 0) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "CURLOPT_FOLLOWLOCATION cannot be activated when an open_basedir is set");
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
}
error = curl_easy_setopt(ch->cp, option, Z_LVAL_PP(zvalue));
@@ -2534,8 +2534,7 @@ string_copy:
postfields = HASH_OF(*zvalue);
if (!postfields) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Couldn't get HashTable in CURLOPT_POSTFIELDS");
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
for (zend_hash_internal_pointer_reset(postfields);
@@ -2571,7 +2570,6 @@ string_copy:
postval = Z_STRVAL_P(prop);
if (php_check_open_basedir(postval TSRMLS_CC)) {
- RETVAL_FALSE;
return 1;
}
@@ -2620,8 +2618,7 @@ string_copy:
}
/* open_basedir check */
if (php_check_open_basedir(postval TSRMLS_CC)) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
error = curl_formadd(&first, &last,
CURLFORM_COPYNAME, string_key,
@@ -2652,8 +2649,7 @@ string_copy:
SAVE_CURL_ERROR(ch, error);
if (error != CURLE_OK) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
if (Z_REFCOUNT_P(ch->clone) <= 1) {
@@ -2675,7 +2671,7 @@ string_copy:
post = estrndup(Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue));
zend_llist_add_element(&ch->to_free->str, &post);
- error = curl_easy_setopt(ch->cp, CURLOPT_POSTFIELDS, post);
+ curl_easy_setopt(ch->cp, CURLOPT_POSTFIELDS, post);
error = curl_easy_setopt(ch->cp, CURLOPT_POSTFIELDSIZE, Z_STRLEN_PP(zvalue));
#endif
}
@@ -2773,26 +2769,13 @@ string_copy:
case CURLOPT_SSH_KNOWNHOSTS:
#endif
{
-#if LIBCURL_VERSION_NUM < 0x071100
- char *copystr = NULL;
-#endif
-
convert_to_string_ex(zvalue);
if (Z_STRLEN_PP(zvalue) && php_check_open_basedir(Z_STRVAL_PP(zvalue) TSRMLS_CC)) {
- RETVAL_FALSE;
- return 1;
+ return FAILURE;
}
-#if LIBCURL_VERSION_NUM >= 0x071100
- error = curl_easy_setopt(ch->cp, option, Z_STRVAL_PP(zvalue));
-#else
- copystr = estrndup(Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue));
-
- error = curl_easy_setopt(ch->cp, option, copystr);
- zend_llist_add_element(&ch->to_free->str, &copystr);
-#endif
- break;
+ return php_curl_option_str(ch, option, Z_STRVAL_PP(zvalue), Z_STRLEN_PP(zvalue), 0 TSRMLS_CC);
}
case CURLINFO_HEADER_OUT:
@@ -2837,9 +2820,9 @@ string_copy:
SAVE_CURL_ERROR(ch, error);
if (error != CURLE_OK) {
- return 1;
+ return FAILURE;
} else {
- return 0;
+ return SUCCESS;
}
}
/* }}} */
@@ -2863,7 +2846,7 @@ PHP_FUNCTION(curl_setopt)
RETURN_FALSE;
}
- if (!_php_curl_setopt(ch, options, zvalue, return_value TSRMLS_CC)) {
+ if (_php_curl_setopt(ch, options, zvalue TSRMLS_CC) == SUCCESS) {
RETURN_TRUE;
} else {
RETURN_FALSE;
@@ -2894,7 +2877,7 @@ PHP_FUNCTION(curl_setopt_array)
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Array keys must be CURLOPT constants or equivalent integer values");
RETURN_FALSE;
}
- if (_php_curl_setopt(ch, (long) option, entry, return_value TSRMLS_CC)) {
+ if (_php_curl_setopt(ch, (long) option, entry TSRMLS_CC) == FAILURE) {
RETURN_FALSE;
}
zend_hash_move_forward_ex(Z_ARRVAL_P(arr), &pos);
diff --git a/ext/curl/multi.c b/ext/curl/multi.c
index af78651ba1..e5c026a513 100644
--- a/ext/curl/multi.c
+++ b/ext/curl/multi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/curl/php_curl.h b/ext/curl/php_curl.h
index c45ed80fc2..96edb9ae03 100644
--- a/ext/curl/php_curl.h
+++ b/ext/curl/php_curl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -198,7 +198,7 @@ typedef struct {
void _php_curl_cleanup_handle(php_curl *);
void _php_curl_multi_cleanup_list(void *data);
-int _php_curl_verify_handlers(php_curl *ch, int reporterror TSRMLS_DC);
+void _php_curl_verify_handlers(php_curl *ch, int reporterror TSRMLS_DC);
void curlfile_register_class(TSRMLS_D);
PHP_CURL_API extern zend_class_entry *curl_CURLFile_class;
diff --git a/ext/curl/share.c b/ext/curl/share.c
index d1aed87940..d46361e0ae 100644
--- a/ext/curl/share.c
+++ b/ext/curl/share.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/curl/tests/bug48203_multi.phpt b/ext/curl/tests/bug48203_multi.phpt
index 7d4ee4769e..501b77843e 100644
--- a/ext/curl/tests/bug48203_multi.phpt
+++ b/ext/curl/tests/bug48203_multi.phpt
@@ -81,8 +81,7 @@ Ok for CURLOPT_WRITEHEADER
Warning: curl_multi_exec(): CURLOPT_FILE resource has gone away, resetting to default in %sbug48203_multi.php on line 36
Warning: curl_multi_exec(): CURLOPT_FILE resource has gone away, resetting to default in %sbug48203_multi.php on line 36
-%A
-Ok for CURLOPT_FILE
+%AOk for CURLOPT_FILE
Warning: curl_multi_exec(): CURLOPT_INFILE resource has gone away, resetting to default in %sbug48203_multi.php on line 36
diff --git a/ext/curl/tests/bug54798.phpt b/ext/curl/tests/bug54798.phpt
index 7ec84addae..f633a8ab2a 100644
--- a/ext/curl/tests/bug54798.phpt
+++ b/ext/curl/tests/bug54798.phpt
@@ -58,15 +58,14 @@ foreach($options_to_check as $option) {
--EXPECTF--
Warning: curl_exec(): CURLOPT_STDERR resource has gone away, resetting to stderr in %sbug54798.php on line %d
* About to connect() %a
-* Closing connection #%d
+* Closing connection %d
Ok for CURLOPT_STDERR
Warning: curl_exec(): CURLOPT_WRITEHEADER resource has gone away, resetting to default in %sbug54798.php on line 24
Ok for CURLOPT_WRITEHEADER
Warning: curl_exec(): CURLOPT_FILE resource has gone away, resetting to default in %sbug54798.php on line 24
-%a
-Ok for CURLOPT_FILE
+%aOk for CURLOPT_FILE
Warning: curl_exec(): CURLOPT_INFILE resource has gone away, resetting to default in %sbug54798.php on line %d
Ok for CURLOPT_INFILE
diff --git a/ext/curl/tests/bug61948-win32.phpt b/ext/curl/tests/bug61948-win32.phpt
index dc86526b7b..00f498f910 100644
--- a/ext/curl/tests/bug61948-win32.phpt
+++ b/ext/curl/tests/bug61948-win32.phpt
@@ -17,9 +17,7 @@ open_basedir="c:/tmp"
?>
--EXPECTF--
%a
-
-Warning: curl_setopt(): open_basedir restriction in effect. File(c:/tmp/foo) is not within the allowed path(s): (c:/tmp) in %sbug61948-win32.php on line %d
-bool(false)
+bool(true)
Warning: curl_setopt(): open_basedir restriction in effect. File(c:/xxx/bar) is not within the allowed path(s): (c:/tmp) in %sbug61948-win32.php on line %d
bool(false)
diff --git a/ext/curl/tests/bug66109.phpt b/ext/curl/tests/bug66109.phpt
new file mode 100644
index 0000000000..aacfba438a
--- /dev/null
+++ b/ext/curl/tests/bug66109.phpt
@@ -0,0 +1,31 @@
+--TEST--
+Bug #66109 (Option CURLOPT_CUSTOMREQUEST can't be reset to default.)
+--SKIPIF--
+<?php
+if (!extension_loaded("curl")) {
+ exit("skip curl extension not loaded");
+}
+if (false === getenv('PHP_CURL_HTTP_REMOTE_SERVER')) {
+ exit("skip PHP_CURL_HTTP_REMOTE_SERVER env variable is not defined");
+}
+?>
+--FILE--
+<?php
+
+$host = getenv('PHP_CURL_HTTP_REMOTE_SERVER');
+$ch = curl_init();
+curl_setopt($ch, CURLOPT_URL, "{$host}/get.php?test=method");
+curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
+
+curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'DELETE');
+var_dump(curl_exec($ch));
+
+curl_setopt($ch, CURLOPT_CUSTOMREQUEST, NULL);
+var_dump(curl_exec($ch));
+
+curl_close($ch);
+
+?>
+--EXPECTF--
+string(6) "DELETE"
+string(3) "GET"
diff --git a/ext/curl/tests/curl_file_deleted_before_curl_close.phpt b/ext/curl/tests/curl_file_deleted_before_curl_close.phpt
index 592f110fbe..3a4d949e75 100644
--- a/ext/curl/tests/curl_file_deleted_before_curl_close.phpt
+++ b/ext/curl/tests/curl_file_deleted_before_curl_close.phpt
@@ -33,6 +33,5 @@ echo "Closed correctly\n";
<?php
unlink(dirname(__FILE__) . '/curl_file_deleted_before_curl_close.tmp');
?>
---EXPECTF--
-* Closing connection #%d
+--EXPECT--
Closed correctly
diff --git a/ext/curl/tests/curl_setopt_basic002.phpt b/ext/curl/tests/curl_setopt_basic002.phpt
index d90ecb7bd2..074158a4b3 100644
--- a/ext/curl/tests/curl_setopt_basic002.phpt
+++ b/ext/curl/tests/curl_setopt_basic002.phpt
@@ -48,5 +48,4 @@ curl_close($ch);
*** Testing curl_setopt with CURLOPT_STDERR
string(%d) "%S"
string(%d) "%S"
-* Closing connection #%d
diff --git a/ext/curl/tests/responder/get.php b/ext/curl/tests/responder/get.php
index 9e13d6a746..60aafc03d4 100644
--- a/ext/curl/tests/responder/get.php
+++ b/ext/curl/tests/responder/get.php
@@ -31,6 +31,9 @@
echo $_FILES['file']['name'] . '|' . $_FILES['file']['type'];
}
break;
+ case 'method':
+ echo $_SERVER['REQUEST_METHOD'];
+ break;
default:
echo "Hello World!\n";
echo "Hello World!";
diff --git a/ext/date/lib/astro.c b/ext/date/lib/astro.c
index d770d1aaed..7f51c71d92 100644
--- a/ext/date/lib/astro.c
+++ b/ext/date/lib/astro.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/date/lib/dow.c b/ext/date/lib/dow.c
index b6c2d69682..a77fdd7182 100644
--- a/ext/date/lib/dow.c
+++ b/ext/date/lib/dow.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -25,10 +25,7 @@ static int m_table_leap[13] = { -1, 6, 2, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5 }; /* 1
static timelib_sll century_value(timelib_sll j)
{
- timelib_sll i = j - 17;
- timelib_sll c = (4 - i * 2 + (i + 1) / 4) % 7;
-
- return c < 0 ? c + 7 : c;
+ return 6 - (j % 4) * 2;
}
static timelib_sll timelib_day_of_week_ex(timelib_sll y, timelib_sll m, timelib_sll d, int iso)
@@ -36,11 +33,8 @@ static timelib_sll timelib_day_of_week_ex(timelib_sll y, timelib_sll m, timelib_
timelib_sll c1, y1, m1, dow;
/* Only valid for Gregorian calendar, commented out as we don't handle
- * julian calendar. We just return the 'wrong' day of week to be
- * consistent.
- if (y < 1753) {
- return -1;
- } */
+ * Julian calendar. We just return the 'wrong' day of week to be
+ * consistent. */
c1 = century_value(y / 100);
y1 = (y % 100);
m1 = timelib_is_leap(y) ? m_table_leap[m] : m_table_common[m];
diff --git a/ext/date/lib/fallbackmap.h b/ext/date/lib/fallbackmap.h
index 4e4c23c96e..af69482c0c 100644
--- a/ext/date/lib/fallbackmap.h
+++ b/ext/date/lib/fallbackmap.h
@@ -1,40 +1,42 @@
- { "sst", 0, -11, "Pacific/Apia" },
- { "hst", 0, -10, "Pacific/Honolulu" },
- { "akst", 0, -9, "America/Anchorage" },
- { "akdt", 1, -8, "America/Anchorage" },
- { "pst", 0, -8, "America/Los_Angeles" },
- { "pdt", 1, -7, "America/Los_Angeles" },
- { "mst", 0, -7, "America/Denver" },
- { "mdt", 1, -6, "America/Denver" },
- { "cst", 0, -6, "America/Chicago" },
- { "cdt", 1, -5, "America/Chicago" },
- { "est", 0, -5, "America/New_York" },
- { "edt", 1, -4, "America/New_York" },
- { "ast", 0, -4, "America/Halifax" },
- { "adt", 1, -3, "America/Halifax" },
- { "brt", 0, -3, "America/Sao_Paulo" },
- { "brst", 1, -2, "America/Sao_Paulo" },
- { "azost", 0, -1, "Atlantic/Azores" },
- { "azodt", 1, 0, "Atlantic/Azores" },
- { "gmt", 0, 0, "Europe/London" },
- { "bst", 1, 1, "Europe/London" },
- { "cet", 0, 1, "Europe/Paris" },
- { "cest", 1, 2, "Europe/Paris" },
- { "eet", 0, 2, "Europe/Helsinki" },
- { "eest", 1, 3, "Europe/Helsinki" },
- { "msk", 0, 3, "Europe/Moscow" },
- { "msd", 1, 4, "Europe/Moscow" },
- { "gst", 0, 4, "Asia/Dubai" },
- { "pkt", 0, 5, "Asia/Karachi" },
- { "ist", 0, 5.5, "Asia/Kolkata" },
- { "npt", 0, 5.75, "Asia/Katmandu" },
- { "yekt", 1, 6, "Asia/Yekaterinburg" },
- { "novst", 1, 7, "Asia/Novosibirsk" },
- { "krat", 0, 7, "Asia/Krasnoyarsk" },
- { "krast", 1, 8, "Asia/Krasnoyarsk" },
- { "jst", 0, 9, "Asia/Tokyo" },
- { "est", 0, 10, "Australia/Melbourne" },
- { "cst", 1, 10.5, "Australia/Adelaide" },
- { "est", 1, 11, "Australia/Melbourne" },
- { "nzst", 0, 12, "Pacific/Auckland" },
- { "nzdt", 1, 13, "Pacific/Auckland" },
+ { "sst", 0, -660, "Pacific/Apia" },
+ { "hst", 0, -600, "Pacific/Honolulu" },
+ { "akst", 0, -540, "America/Anchorage" },
+ { "akdt", 1, -480, "America/Anchorage" },
+ { "pst", 0, -480, "America/Los_Angeles" },
+ { "pdt", 1, -420, "America/Los_Angeles" },
+ { "mst", 0, -420, "America/Denver" },
+ { "mdt", 1, -360, "America/Denver" },
+ { "cst", 0, -360, "America/Chicago" },
+ { "cdt", 1, -300, "America/Chicago" },
+ { "est", 0, -300, "America/New_York" },
+ { "vet", 0, -270, "America/Caracas" },
+ { "edt", 1, -240, "America/New_York" },
+ { "ast", 0, -240, "America/Halifax" },
+ { "adt", 1, -180, "America/Halifax" },
+ { "brt", 0, -180, "America/Sao_Paulo" },
+ { "brst", 1, -120, "America/Sao_Paulo" },
+ { "azost", 0, -60, "Atlantic/Azores" },
+ { "azodt", 1, 0, "Atlantic/Azores" },
+ { "gmt", 0, 0, "Europe/London" },
+ { "bst", 1, 60, "Europe/London" },
+ { "cet", 0, 60, "Europe/Paris" },
+ { "cest", 1, 120, "Europe/Paris" },
+ { "eet", 0, 120, "Europe/Helsinki" },
+ { "eest", 1, 180, "Europe/Helsinki" },
+ { "msk", 0, 180, "Europe/Moscow" },
+ { "msd", 1, 240, "Europe/Moscow" },
+ { "gst", 0, 240, "Asia/Dubai" },
+ { "pkt", 0, 300, "Asia/Karachi" },
+ { "ist", 0, 330, "Asia/Kolkata" },
+ { "npt", 0, 345, "Asia/Katmandu" },
+ { "yekt", 1, 360, "Asia/Yekaterinburg" },
+ { "novst", 1, 420, "Asia/Novosibirsk" },
+ { "krat", 0, 420, "Asia/Krasnoyarsk" },
+ { "cst", 0, 480, "Asia/Shanghai" },
+ { "krast", 1, 480, "Asia/Krasnoyarsk" },
+ { "jst", 0, 540, "Asia/Tokyo" },
+ { "est", 0, 600, "Australia/Melbourne" },
+ { "cst", 1, 630, "Australia/Adelaide" },
+ { "est", 1, 660, "Australia/Melbourne" },
+ { "nzst", 0, 720, "Pacific/Auckland" },
+ { "nzdt", 1, 780, "Pacific/Auckland" },
diff --git a/ext/date/lib/interval.c b/ext/date/lib/interval.c
index 96867ba2b7..86e98ea744 100644
--- a/ext/date/lib/interval.c
+++ b/ext/date/lib/interval.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -25,7 +25,7 @@ timelib_rel_time *timelib_diff(timelib_time *one, timelib_time *two)
{
timelib_rel_time *rt;
timelib_time *swp;
- timelib_sll dst_h_corr = 0, dst_m_corr = 0;
+ timelib_sll dst_corr = 0 ,dst_h_corr = 0, dst_m_corr = 0;
timelib_time one_backup, two_backup;
rt = timelib_rel_time_ctor();
@@ -43,8 +43,9 @@ timelib_rel_time *timelib_diff(timelib_time *one, timelib_time *two)
&& (strcmp(one->tz_info->name, two->tz_info->name) == 0)
&& (one->z != two->z))
{
- dst_h_corr = (two->z - one->z) / 3600;
- dst_m_corr = ((two->z - one->z) % 3600) / 60;
+ dst_corr = two->z - one->z;
+ dst_h_corr = dst_corr / 3600;
+ dst_m_corr = (dst_corr % 3600) / 60;
}
/* Save old TZ info */
@@ -57,16 +58,108 @@ timelib_rel_time *timelib_diff(timelib_time *one, timelib_time *two)
rt->y = two->y - one->y;
rt->m = two->m - one->m;
rt->d = two->d - one->d;
- rt->h = two->h - one->h + dst_h_corr;
- rt->i = two->i - one->i + dst_m_corr;
+ rt->h = two->h - one->h;
+ rt->i = two->i - one->i;
rt->s = two->s - one->s;
+ if (one_backup.dst == 0 && two_backup.dst == 1 && two->sse >= one->sse + 86400 - dst_corr) {
+ rt->h += dst_h_corr;
+ rt->i += dst_m_corr;
+ }
+
rt->days = abs(floor((one->sse - two->sse - (dst_h_corr * 3600) - (dst_m_corr * 60)) / 86400));
timelib_do_rel_normalize(rt->invert ? one : two, rt);
+ /* We need to do this after normalisation otherwise we can't get "24H" */
+ if (one_backup.dst == 1 && two_backup.dst == 0 && two->sse >= one->sse + 86400) {
+ if (two->sse < one->sse + 86400 - dst_corr) {
+ rt->d--;
+ rt->h = 24;
+ } else {
+ rt->h += dst_h_corr;
+ rt->i += dst_m_corr;
+ }
+ }
+
/* Restore old TZ info */
memcpy(one, &one_backup, sizeof(one_backup));
memcpy(two, &two_backup, sizeof(two_backup));
return rt;
}
+
+timelib_time *timelib_add(timelib_time *old_time, timelib_rel_time *interval)
+{
+ int bias = 1;
+ timelib_time *t = timelib_time_clone(old_time);
+
+ if (interval->have_weekday_relative || interval->have_special_relative) {
+ memcpy(&t->relative, interval, sizeof(struct timelib_rel_time));
+ } else {
+ if (interval->invert) {
+ bias = -1;
+ }
+ memset(&t->relative, 0, sizeof(struct timelib_rel_time));
+ t->relative.y = interval->y * bias;
+ t->relative.m = interval->m * bias;
+ t->relative.d = interval->d * bias;
+ t->relative.h = interval->h * bias;
+ t->relative.i = interval->i * bias;
+ t->relative.s = interval->s * bias;
+ }
+ t->have_relative = 1;
+ t->sse_uptodate = 0;
+
+ timelib_update_ts(t, NULL);
+
+// printf("%lld %lld %d\n", old_time->dst, t->dst, (t->sse - old_time->sse));
+ /* Adjust for backwards DST changeover */
+ if (old_time->dst == 1 && t->dst == 0 && !interval->y && !interval->m && !interval->d) {
+ t->sse -= old_time->z;
+ t->sse += t->z;
+ }
+
+ timelib_update_from_sse(t);
+ t->have_relative = 0;
+
+ return t;
+}
+
+timelib_time *timelib_sub(timelib_time *old_time, timelib_rel_time *interval)
+{
+ int bias = 1;
+ timelib_time *t = timelib_time_clone(old_time);
+
+ if (interval->invert) {
+ bias = -1;
+ }
+
+ memset(&t->relative, 0, sizeof(struct timelib_rel_time));
+ t->relative.y = 0 - (interval->y * bias);
+ t->relative.m = 0 - (interval->m * bias);
+ t->relative.d = 0 - (interval->d * bias);
+ t->relative.h = 0 - (interval->h * bias);
+ t->relative.i = 0 - (interval->i * bias);
+ t->relative.s = 0 - (interval->s * bias);
+ t->have_relative = 1;
+ t->sse_uptodate = 0;
+
+ timelib_update_ts(t, NULL);
+
+ /* Adjust for backwards DST changeover */
+ if (old_time->dst == 1 && t->dst == 0 && !interval->y && !interval->m && !interval->d) {
+ t->sse -= old_time->z;
+ t->sse += t->z;
+ }
+ /* Adjust for forwards DST changeover */
+ if (old_time->dst == 0 && t->dst == 1 && !interval->y && !interval->m && !interval->d ) {
+ t->sse -= old_time->z;
+ t->sse += t->z;
+ }
+
+ timelib_update_from_sse(t);
+
+ t->have_relative = 0;
+
+ return t;
+}
diff --git a/ext/date/lib/parse_date.c b/ext/date/lib/parse_date.c
index 0e99e231d6..fd67d8bf52 100644
--- a/ext/date/lib/parse_date.c
+++ b/ext/date/lib/parse_date.c
@@ -1,4 +1,4 @@
-/* Generated by re2c 0.13.5 on Sun Aug 25 15:12:48 2013 */
+/* Generated by re2c 0.13.5 on Thu Feb 6 07:35:53 2014 */
#line 1 "ext/date/lib/parse_date.re"
/*
+----------------------------------------------------------------------+
@@ -717,7 +717,7 @@ const static timelib_tz_lookup_table* zone_search(const char *word, long gmtoffs
/* Still didn't find anything, let's find the zone solely based on
* offset/isdst then */
for (fmp = timelib_timezone_fallbackmap; fmp->name; fmp++) {
- if ((fmp->gmtoffset * 3600) == gmtoffset && fmp->type == isdst) {
+ if ((fmp->gmtoffset * 60) == gmtoffset && fmp->type == isdst) {
return fmp;
}
}
@@ -751,7 +751,7 @@ static long timelib_lookup_zone(char **ptr, int *dst, char **tz_abbr, int *found
return value;
}
-static long timelib_get_zone(char **ptr, int *dst, timelib_time *t, int *tz_not_found, const timelib_tzdb *tzdb, timelib_tz_get_wrapper tz_wrapper)
+long timelib_parse_zone(char **ptr, int *dst, timelib_time *t, int *tz_not_found, const timelib_tzdb *tzdb, timelib_tz_get_wrapper tz_wrapper)
{
timelib_tzinfo *res;
long retval = 0;
@@ -1006,7 +1006,7 @@ yy4:
DEBUG_OUTPUT("tzcorrection | tz");
TIMELIB_INIT;
TIMELIB_HAVE_TZ();
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -4468,7 +4468,7 @@ yy223:
}
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -9798,7 +9798,7 @@ yy491:
}
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -12073,7 +12073,7 @@ yy701:
s->time->h = timelib_get_nr((char **) &ptr, 2);
s->time->i = timelib_get_nr((char **) &ptr, 2);
s->time->s = timelib_get_nr((char **) &ptr, 2);
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -13464,7 +13464,7 @@ yy843:
if (*ptr == '.') {
s->time->f = timelib_get_frac_nr((char **) &ptr, 9);
if (*ptr) { /* timezone is optional */
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -15813,7 +15813,7 @@ yy1076:
s->time->s = timelib_get_nr((char **) &ptr, 2);
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -25047,7 +25047,7 @@ timelib_time *timelib_parse_from_format(char *format, char *string, int len, tim
case 'O': /* timezone */
{
int tz_not_found;
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_pbf_error(s, "The timezone could not be found in the database", string, begin);
}
diff --git a/ext/date/lib/parse_date.re b/ext/date/lib/parse_date.re
index 6d91d9ada9..e01e292e10 100644
--- a/ext/date/lib/parse_date.re
+++ b/ext/date/lib/parse_date.re
@@ -715,7 +715,7 @@ const static timelib_tz_lookup_table* zone_search(const char *word, long gmtoffs
/* Still didn't find anything, let's find the zone solely based on
* offset/isdst then */
for (fmp = timelib_timezone_fallbackmap; fmp->name; fmp++) {
- if ((fmp->gmtoffset * 3600) == gmtoffset && fmp->type == isdst) {
+ if ((fmp->gmtoffset * 60) == gmtoffset && fmp->type == isdst) {
return fmp;
}
}
@@ -749,7 +749,7 @@ static long timelib_lookup_zone(char **ptr, int *dst, char **tz_abbr, int *found
return value;
}
-static long timelib_get_zone(char **ptr, int *dst, timelib_time *t, int *tz_not_found, const timelib_tzdb *tzdb, timelib_tz_get_wrapper tz_wrapper)
+long timelib_parse_zone(char **ptr, int *dst, timelib_time *t, int *tz_not_found, const timelib_tzdb *tzdb, timelib_tz_get_wrapper tz_wrapper)
{
timelib_tzinfo *res;
long retval = 0;
@@ -1161,7 +1161,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
}
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -1202,7 +1202,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
s->time->h = timelib_get_nr((char **) &ptr, 2);
s->time->i = timelib_get_nr((char **) &ptr, 2);
s->time->s = 0;
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, s->tzdb, tz_get_wrapper);
break;
case 1:
s->time->y = timelib_get_nr((char **) &ptr, 4);
@@ -1227,7 +1227,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
s->time->s = timelib_get_nr((char **) &ptr, 2);
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -1429,7 +1429,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
if (*ptr == '.') {
s->time->f = timelib_get_frac_nr((char **) &ptr, 9);
if (*ptr) { /* timezone is optional */
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -1532,7 +1532,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
s->time->h = timelib_get_nr((char **) &ptr, 2);
s->time->i = timelib_get_nr((char **) &ptr, 2);
s->time->s = timelib_get_nr((char **) &ptr, 2);
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -1645,7 +1645,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
DEBUG_OUTPUT("tzcorrection | tz");
TIMELIB_INIT;
TIMELIB_HAVE_TZ();
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -1698,7 +1698,7 @@ weekdayof = (reltextnumber|reltexttext) space (dayfull|dayabbr) space 'of
}
if (*ptr != '\0') {
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_error(s, "The timezone could not be found in the database");
}
@@ -2054,7 +2054,7 @@ timelib_time *timelib_parse_from_format(char *format, char *string, int len, tim
case 'O': /* timezone */
{
int tz_not_found;
- s->time->z = timelib_get_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
+ s->time->z = timelib_parse_zone((char **) &ptr, &s->time->dst, s->time, &tz_not_found, s->tzdb, tz_get_wrapper);
if (tz_not_found) {
add_pbf_error(s, "The timezone could not be found in the database", string, begin);
}
diff --git a/ext/date/lib/parse_iso_intervals.c b/ext/date/lib/parse_iso_intervals.c
index fedad043c4..c14a07465a 100644
--- a/ext/date/lib/parse_iso_intervals.c
+++ b/ext/date/lib/parse_iso_intervals.c
@@ -1,10 +1,10 @@
-/* Generated by re2c 0.13.5 on Sun Mar 31 10:48:17 2013 */
+/* Generated by re2c 0.13.5 on Wed Nov 27 11:14:23 2013 */
#line 1 "ext/date/lib/parse_iso_intervals.re"
/*
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -380,7 +380,7 @@ yy6:
break;
}
ptr++;
- } while (*ptr);
+ } while (!s->errors->error_count && *ptr);
s->have_period = 1;
TIMELIB_DEINIT;
return TIMELIB_PERIOD;
diff --git a/ext/date/lib/parse_iso_intervals.re b/ext/date/lib/parse_iso_intervals.re
index e50ab37d3b..cbbf8781bf 100644
--- a/ext/date/lib/parse_iso_intervals.re
+++ b/ext/date/lib/parse_iso_intervals.re
@@ -348,7 +348,7 @@ isoweek = year4 "-"? "W" weekofyear;
break;
}
ptr++;
- } while (*ptr);
+ } while (!s->errors->error_count && *ptr);
s->have_period = 1;
TIMELIB_DEINIT;
return TIMELIB_PERIOD;
diff --git a/ext/date/lib/parse_tz.c b/ext/date/lib/parse_tz.c
index d3abf84c81..5d2aec9c93 100644
--- a/ext/date/lib/parse_tz.c
+++ b/ext/date/lib/parse_tz.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/date/lib/timelib.c b/ext/date/lib/timelib.c
index 84354e300f..bf7c55a735 100644
--- a/ext/date/lib/timelib.c
+++ b/ext/date/lib/timelib.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/date/lib/timelib.h b/ext/date/lib/timelib.h
index dfb7dc0300..08484fbec1 100644
--- a/ext/date/lib/timelib.h
+++ b/ext/date/lib/timelib.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -92,6 +92,8 @@ int timelib_apply_localtime(timelib_time *t, unsigned int localtime);
void timelib_unixtime2gmt(timelib_time* tm, timelib_sll ts);
void timelib_unixtime2local(timelib_time *tm, timelib_sll ts);
void timelib_update_from_sse(timelib_time *tm);
+void timelib_set_timezone_from_offset(timelib_time *t, timelib_sll utc_offset);
+void timelib_set_timezone_from_abbr(timelib_time *t, timelib_abbr_info abbr_info);
void timelib_set_timezone(timelib_time *t, timelib_tzinfo *tz);
/* From parse_tz.c */
@@ -103,6 +105,7 @@ timelib_sll timelib_get_current_offset(timelib_time *t);
void timelib_dump_tzinfo(timelib_tzinfo *tz);
const timelib_tzdb *timelib_builtin_db(void);
const timelib_tzdb_index_entry *timelib_timezone_builtin_identifiers_list(int *count);
+long timelib_parse_zone(char **ptr, int *dst, timelib_time *t, int *tz_not_found, const timelib_tzdb *tzdb, timelib_tz_get_wrapper tz_wrapper);
/* From timelib.c */
timelib_tzinfo* timelib_tzinfo_ctor(char *name);
@@ -138,5 +141,7 @@ int timelib_astro_rise_set_altitude(timelib_time *time, double lon, double lat,
/* from interval.c */
timelib_rel_time *timelib_diff(timelib_time *one, timelib_time *two);
+timelib_time *timelib_add(timelib_time *t, timelib_rel_time *interval);
+timelib_time *timelib_sub(timelib_time *t, timelib_rel_time *interval);
#endif
diff --git a/ext/date/lib/timelib_structs.h b/ext/date/lib/timelib_structs.h
index a3d7793447..5185e7b40b 100644
--- a/ext/date/lib/timelib_structs.h
+++ b/ext/date/lib/timelib_structs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -172,6 +172,12 @@ typedef struct timelib_time {
* 2 TimeZone abbreviation */
} timelib_time;
+typedef struct timelib_abbr_info {
+ timelib_sll utc_offset;
+ char *abbr;
+ int dst;
+} timelib_abbr_info;
+
typedef struct timelib_error_message {
int position;
char character;
diff --git a/ext/date/lib/timezonedb.h b/ext/date/lib/timezonedb.h
index 91884a935f..4a4b041882 100644
--- a/ext/date/lib/timezonedb.h
+++ b/ext/date/lib/timezonedb.h
@@ -232,355 +232,355 @@ const timelib_tzdb_index_entry timezonedb_idx_builtin[579] = {
{ "Asia/Aden" , 0x018C91 },
{ "Asia/Almaty" , 0x018CE6 },
{ "Asia/Amman" , 0x018E65 },
- { "Asia/Anadyr" , 0x019037 },
- { "Asia/Aqtau" , 0x01921C },
- { "Asia/Aqtobe" , 0x01941B },
- { "Asia/Ashgabat" , 0x0195D3 },
- { "Asia/Ashkhabad" , 0x0196F0 },
- { "Asia/Baghdad" , 0x01980D },
- { "Asia/Bahrain" , 0x019982 },
- { "Asia/Baku" , 0x0199E8 },
- { "Asia/Bangkok" , 0x019CD0 },
- { "Asia/Beirut" , 0x019D25 },
- { "Asia/Bishkek" , 0x01A032 },
- { "Asia/Brunei" , 0x01A1DE },
- { "Asia/Calcutta" , 0x01A240 },
- { "Asia/Choibalsan" , 0x01A2B9 },
- { "Asia/Chongqing" , 0x01A432 },
- { "Asia/Chungking" , 0x01A521 },
- { "Asia/Colombo" , 0x01A5D0 },
- { "Asia/Dacca" , 0x01A66C },
- { "Asia/Damascus" , 0x01A712 },
- { "Asia/Dhaka" , 0x01AA62 },
- { "Asia/Dili" , 0x01AB08 },
- { "Asia/Dubai" , 0x01AB92 },
- { "Asia/Dushanbe" , 0x01ABE7 },
- { "Asia/Gaza" , 0x01ACEA },
- { "Asia/Harbin" , 0x01B03D },
- { "Asia/Hebron" , 0x01B124 },
- { "Asia/Ho_Chi_Minh" , 0x01B480 },
- { "Asia/Hong_Kong" , 0x01B4F8 },
- { "Asia/Hovd" , 0x01B6BA },
- { "Asia/Irkutsk" , 0x01B832 },
- { "Asia/Istanbul" , 0x01BA18 },
- { "Asia/Jakarta" , 0x01BE05 },
- { "Asia/Jayapura" , 0x01BEAF },
- { "Asia/Jerusalem" , 0x01BF4B },
- { "Asia/Kabul" , 0x01C27A },
- { "Asia/Kamchatka" , 0x01C2CB },
- { "Asia/Karachi" , 0x01C4A7 },
- { "Asia/Kashgar" , 0x01C55C },
- { "Asia/Kathmandu" , 0x01C62D },
- { "Asia/Katmandu" , 0x01C693 },
- { "Asia/Khandyga" , 0x01C6F9 },
- { "Asia/Kolkata" , 0x01C91E },
- { "Asia/Krasnoyarsk" , 0x01C997 },
- { "Asia/Kuala_Lumpur" , 0x01CB7F },
- { "Asia/Kuching" , 0x01CC3C },
- { "Asia/Kuwait" , 0x01CD2A },
- { "Asia/Macao" , 0x01CD7F },
- { "Asia/Macau" , 0x01CEBA },
- { "Asia/Magadan" , 0x01CFF5 },
- { "Asia/Makassar" , 0x01D1D7 },
- { "Asia/Manila" , 0x01D29C },
- { "Asia/Muscat" , 0x01D321 },
- { "Asia/Nicosia" , 0x01D376 },
- { "Asia/Novokuznetsk" , 0x01D65E },
- { "Asia/Novosibirsk" , 0x01D860 },
- { "Asia/Omsk" , 0x01DA4B },
- { "Asia/Oral" , 0x01DC32 },
- { "Asia/Phnom_Penh" , 0x01DE02 },
- { "Asia/Pontianak" , 0x01DE7A },
- { "Asia/Pyongyang" , 0x01DF3C },
- { "Asia/Qatar" , 0x01DFA9 },
- { "Asia/Qyzylorda" , 0x01E00F },
- { "Asia/Rangoon" , 0x01E1E5 },
- { "Asia/Riyadh" , 0x01E25D },
- { "Asia/Saigon" , 0x01E2B2 },
- { "Asia/Sakhalin" , 0x01E32A },
- { "Asia/Samarkand" , 0x01E521 },
- { "Asia/Seoul" , 0x01E657 },
- { "Asia/Shanghai" , 0x01E6FB },
- { "Asia/Singapore" , 0x01E7DB },
- { "Asia/Taipei" , 0x01E892 },
- { "Asia/Tashkent" , 0x01E9AA },
- { "Asia/Tbilisi" , 0x01EADB },
- { "Asia/Tehran" , 0x01EC95 },
- { "Asia/Tel_Aviv" , 0x01EF03 },
- { "Asia/Thimbu" , 0x01F232 },
- { "Asia/Thimphu" , 0x01F298 },
- { "Asia/Tokyo" , 0x01F2FE },
- { "Asia/Ujung_Pandang" , 0x01F387 },
- { "Asia/Ulaanbaatar" , 0x01F404 },
- { "Asia/Ulan_Bator" , 0x01F55F },
- { "Asia/Urumqi" , 0x01F6AC },
- { "Asia/Ust-Nera" , 0x01F773 },
- { "Asia/Vientiane" , 0x01F978 },
- { "Asia/Vladivostok" , 0x01F9F0 },
- { "Asia/Yakutsk" , 0x01FBDC },
- { "Asia/Yekaterinburg" , 0x01FDC1 },
- { "Asia/Yerevan" , 0x01FFCC },
- { "Atlantic/Azores" , 0x0201CC },
- { "Atlantic/Bermuda" , 0x0206CF },
- { "Atlantic/Canary" , 0x0209B0 },
- { "Atlantic/Cape_Verde" , 0x020C86 },
- { "Atlantic/Faeroe" , 0x020CFF },
- { "Atlantic/Faroe" , 0x020FA3 },
- { "Atlantic/Jan_Mayen" , 0x021247 },
- { "Atlantic/Madeira" , 0x021579 },
- { "Atlantic/Reykjavik" , 0x021A82 },
- { "Atlantic/South_Georgia" , 0x021C3B },
- { "Atlantic/St_Helena" , 0x021E4D },
- { "Atlantic/Stanley" , 0x021C7F },
- { "Australia/ACT" , 0x021EA2 },
- { "Australia/Adelaide" , 0x0221BF },
- { "Australia/Brisbane" , 0x0224EB },
- { "Australia/Broken_Hill" , 0x0225B2 },
- { "Australia/Canberra" , 0x0228F0 },
- { "Australia/Currie" , 0x022C0D },
- { "Australia/Darwin" , 0x022F40 },
- { "Australia/Eucla" , 0x022FC6 },
- { "Australia/Hobart" , 0x02309B },
- { "Australia/LHI" , 0x0233F9 },
- { "Australia/Lindeman" , 0x023694 },
- { "Australia/Lord_Howe" , 0x023775 },
- { "Australia/Melbourne" , 0x023A20 },
- { "Australia/North" , 0x023D45 },
- { "Australia/NSW" , 0x023DB9 },
- { "Australia/Perth" , 0x0240D6 },
- { "Australia/Queensland" , 0x0241AE },
- { "Australia/South" , 0x02425A },
- { "Australia/Sydney" , 0x024577 },
- { "Australia/Tasmania" , 0x0248B4 },
- { "Australia/Victoria" , 0x024BF9 },
- { "Australia/West" , 0x024F16 },
- { "Australia/Yancowinna" , 0x024FCC },
- { "Brazil/Acre" , 0x0252EE },
- { "Brazil/DeNoronha" , 0x0253F2 },
- { "Brazil/East" , 0x025512 },
- { "Brazil/West" , 0x0257EF },
- { "Canada/Atlantic" , 0x0258E7 },
- { "Canada/Central" , 0x025DCF },
- { "Canada/East-Saskatchewan" , 0x0266D9 },
- { "Canada/Eastern" , 0x0261E9 },
- { "Canada/Mountain" , 0x026862 },
- { "Canada/Newfoundland" , 0x026BD8 },
- { "Canada/Pacific" , 0x027103 },
- { "Canada/Saskatchewan" , 0x02751C },
- { "Canada/Yukon" , 0x0276A5 },
- { "CET" , 0x0279A8 },
- { "Chile/Continental" , 0x027CB1 },
- { "Chile/EasterIsland" , 0x02804C },
- { "CST6CDT" , 0x02838E },
- { "Cuba" , 0x0286DF },
- { "EET" , 0x028A52 },
- { "Egypt" , 0x028D05 },
- { "Eire" , 0x028FC8 },
- { "EST" , 0x0294D9 },
- { "EST5EDT" , 0x02951D },
- { "Etc/GMT" , 0x02986E },
- { "Etc/GMT+0" , 0x02993A },
- { "Etc/GMT+1" , 0x0299C4 },
- { "Etc/GMT+10" , 0x029A51 },
- { "Etc/GMT+11" , 0x029ADF },
- { "Etc/GMT+12" , 0x029B6D },
- { "Etc/GMT+2" , 0x029C88 },
- { "Etc/GMT+3" , 0x029D14 },
- { "Etc/GMT+4" , 0x029DA0 },
- { "Etc/GMT+5" , 0x029E2C },
- { "Etc/GMT+6" , 0x029EB8 },
- { "Etc/GMT+7" , 0x029F44 },
- { "Etc/GMT+8" , 0x029FD0 },
- { "Etc/GMT+9" , 0x02A05C },
- { "Etc/GMT-0" , 0x0298F6 },
- { "Etc/GMT-1" , 0x02997E },
- { "Etc/GMT-10" , 0x029A0A },
- { "Etc/GMT-11" , 0x029A98 },
- { "Etc/GMT-12" , 0x029B26 },
- { "Etc/GMT-13" , 0x029BB4 },
- { "Etc/GMT-14" , 0x029BFB },
- { "Etc/GMT-2" , 0x029C42 },
- { "Etc/GMT-3" , 0x029CCE },
- { "Etc/GMT-4" , 0x029D5A },
- { "Etc/GMT-5" , 0x029DE6 },
- { "Etc/GMT-6" , 0x029E72 },
- { "Etc/GMT-7" , 0x029EFE },
- { "Etc/GMT-8" , 0x029F8A },
- { "Etc/GMT-9" , 0x02A016 },
- { "Etc/GMT0" , 0x0298B2 },
- { "Etc/Greenwich" , 0x02A0A2 },
- { "Etc/UCT" , 0x02A0E6 },
- { "Etc/Universal" , 0x02A12A },
- { "Etc/UTC" , 0x02A16E },
- { "Etc/Zulu" , 0x02A1B2 },
- { "Europe/Amsterdam" , 0x02A1F6 },
- { "Europe/Andorra" , 0x02A634 },
- { "Europe/Athens" , 0x02A8B0 },
- { "Europe/Belfast" , 0x02ABF3 },
- { "Europe/Belgrade" , 0x02B12A },
- { "Europe/Berlin" , 0x02B3F3 },
- { "Europe/Bratislava" , 0x02B757 },
- { "Europe/Brussels" , 0x02BA89 },
- { "Europe/Bucharest" , 0x02BEC0 },
- { "Europe/Budapest" , 0x02C1EA },
- { "Europe/Busingen" , 0x02C55D },
- { "Europe/Chisinau" , 0x02C814 },
- { "Europe/Copenhagen" , 0x02CBA2 },
- { "Europe/Dublin" , 0x02CEAC },
- { "Europe/Gibraltar" , 0x02D3BD },
- { "Europe/Guernsey" , 0x02D814 },
- { "Europe/Helsinki" , 0x02DD4B },
- { "Europe/Isle_of_Man" , 0x02E001 },
- { "Europe/Istanbul" , 0x02E538 },
- { "Europe/Jersey" , 0x02E925 },
- { "Europe/Kaliningrad" , 0x02EE5C },
- { "Europe/Kiev" , 0x02F0C2 },
- { "Europe/Lisbon" , 0x02F3D9 },
- { "Europe/Ljubljana" , 0x02F8DD },
- { "Europe/London" , 0x02FBA6 },
- { "Europe/Luxembourg" , 0x0300DD },
- { "Europe/Madrid" , 0x030533 },
- { "Europe/Malta" , 0x0308F9 },
- { "Europe/Mariehamn" , 0x030CB2 },
- { "Europe/Minsk" , 0x030F68 },
- { "Europe/Monaco" , 0x031176 },
- { "Europe/Moscow" , 0x0315B1 },
- { "Europe/Nicosia" , 0x031802 },
- { "Europe/Oslo" , 0x031AEA },
- { "Europe/Paris" , 0x031E1C },
- { "Europe/Podgorica" , 0x032262 },
- { "Europe/Prague" , 0x03252B },
- { "Europe/Riga" , 0x03285D },
- { "Europe/Rome" , 0x032BA2 },
- { "Europe/Samara" , 0x032F65 },
- { "Europe/San_Marino" , 0x033198 },
- { "Europe/Sarajevo" , 0x03355B },
- { "Europe/Simferopol" , 0x033824 },
- { "Europe/Skopje" , 0x033B4F },
- { "Europe/Sofia" , 0x033E18 },
- { "Europe/Stockholm" , 0x034120 },
- { "Europe/Tallinn" , 0x0343CF },
- { "Europe/Tirane" , 0x034709 },
- { "Europe/Tiraspol" , 0x034A0F },
- { "Europe/Uzhgorod" , 0x034D9D },
- { "Europe/Vaduz" , 0x0350B4 },
- { "Europe/Vatican" , 0x035363 },
- { "Europe/Vienna" , 0x035726 },
- { "Europe/Vilnius" , 0x035A53 },
- { "Europe/Volgograd" , 0x035D92 },
- { "Europe/Warsaw" , 0x035F92 },
- { "Europe/Zagreb" , 0x036373 },
- { "Europe/Zaporozhye" , 0x03663C },
- { "Europe/Zurich" , 0x03697D },
- { "Factory" , 0x036C2C },
- { "GB" , 0x036C9D },
- { "GB-Eire" , 0x0371D4 },
- { "GMT" , 0x03770B },
- { "GMT+0" , 0x0377D7 },
- { "GMT-0" , 0x037793 },
- { "GMT0" , 0x03774F },
- { "Greenwich" , 0x03781B },
- { "Hongkong" , 0x03785F },
- { "HST" , 0x037A21 },
- { "Iceland" , 0x037A65 },
- { "Indian/Antananarivo" , 0x037C1E },
- { "Indian/Chagos" , 0x037C92 },
- { "Indian/Christmas" , 0x037CF4 },
- { "Indian/Cocos" , 0x037D38 },
- { "Indian/Comoro" , 0x037D7C },
- { "Indian/Kerguelen" , 0x037DD1 },
- { "Indian/Mahe" , 0x037E26 },
- { "Indian/Maldives" , 0x037E7B },
- { "Indian/Mauritius" , 0x037ED0 },
- { "Indian/Mayotte" , 0x037F46 },
- { "Indian/Reunion" , 0x037F9B },
- { "Iran" , 0x037FF0 },
- { "Israel" , 0x03825E },
- { "Jamaica" , 0x03858D },
- { "Japan" , 0x038652 },
- { "Kwajalein" , 0x0386DB },
- { "Libya" , 0x03873E },
- { "MET" , 0x038847 },
- { "Mexico/BajaNorte" , 0x038B50 },
- { "Mexico/BajaSur" , 0x038EB9 },
- { "Mexico/General" , 0x0390FE },
- { "MST" , 0x03935C },
- { "MST7MDT" , 0x0393A0 },
- { "Navajo" , 0x0396F1 },
- { "NZ" , 0x039A6A },
- { "NZ-CHAT" , 0x039DE8 },
- { "Pacific/Apia" , 0x03A0D0 },
- { "Pacific/Auckland" , 0x03A26C },
- { "Pacific/Chatham" , 0x03A5F8 },
- { "Pacific/Chuuk" , 0x03A8EF },
- { "Pacific/Easter" , 0x03A948 },
- { "Pacific/Efate" , 0x03ACA6 },
- { "Pacific/Enderbury" , 0x03AD6C },
- { "Pacific/Fakaofo" , 0x03ADDA },
- { "Pacific/Fiji" , 0x03AE2B },
- { "Pacific/Funafuti" , 0x03AFBE },
- { "Pacific/Galapagos" , 0x03B002 },
- { "Pacific/Gambier" , 0x03B07A },
- { "Pacific/Guadalcanal" , 0x03B0DF },
- { "Pacific/Guam" , 0x03B134 },
- { "Pacific/Honolulu" , 0x03B18A },
- { "Pacific/Johnston" , 0x03B201 },
- { "Pacific/Kiritimati" , 0x03B280 },
- { "Pacific/Kosrae" , 0x03B2EB },
- { "Pacific/Kwajalein" , 0x03B348 },
- { "Pacific/Majuro" , 0x03B3B4 },
- { "Pacific/Marquesas" , 0x03B413 },
- { "Pacific/Midway" , 0x03B47A },
- { "Pacific/Nauru" , 0x03B504 },
- { "Pacific/Niue" , 0x03B57C },
- { "Pacific/Norfolk" , 0x03B5DA },
- { "Pacific/Noumea" , 0x03B62F },
- { "Pacific/Pago_Pago" , 0x03B6BF },
- { "Pacific/Palau" , 0x03B748 },
- { "Pacific/Pitcairn" , 0x03B78C },
- { "Pacific/Pohnpei" , 0x03B7E1 },
- { "Pacific/Ponape" , 0x03B836 },
- { "Pacific/Port_Moresby" , 0x03B87B },
- { "Pacific/Rarotonga" , 0x03B8BF },
- { "Pacific/Saipan" , 0x03B99B },
- { "Pacific/Samoa" , 0x03B9FE },
- { "Pacific/Tahiti" , 0x03BA87 },
- { "Pacific/Tarawa" , 0x03BAEC },
- { "Pacific/Tongatapu" , 0x03BB40 },
- { "Pacific/Truk" , 0x03BBCC },
- { "Pacific/Wake" , 0x03BC11 },
- { "Pacific/Wallis" , 0x03BC61 },
- { "Pacific/Yap" , 0x03BCA5 },
- { "Poland" , 0x03BCEA },
- { "Portugal" , 0x03C0CB },
- { "PRC" , 0x03C5C7 },
- { "PST8PDT" , 0x03C678 },
- { "ROC" , 0x03C9C9 },
- { "ROK" , 0x03CAE1 },
- { "Singapore" , 0x03CB85 },
- { "Turkey" , 0x03CC3C },
- { "UCT" , 0x03D029 },
- { "Universal" , 0x03D06D },
- { "US/Alaska" , 0x03D0B1 },
- { "US/Aleutian" , 0x03D41A },
- { "US/Arizona" , 0x03D780 },
- { "US/Central" , 0x03D80E },
- { "US/East-Indiana" , 0x03E218 },
- { "US/Eastern" , 0x03DD19 },
- { "US/Hawaii" , 0x03E482 },
- { "US/Indiana-Starke" , 0x03E4F3 },
- { "US/Michigan" , 0x03E864 },
- { "US/Mountain" , 0x03EB9B },
- { "US/Pacific" , 0x03EF14 },
- { "US/Pacific-New" , 0x03F319 },
- { "US/Samoa" , 0x03F71E },
- { "UTC" , 0x03F7A7 },
- { "W-SU" , 0x03FA9E },
- { "WET" , 0x03F7EB },
- { "Zulu" , 0x03FCD8 },
+ { "Asia/Anadyr" , 0x01911B },
+ { "Asia/Aqtau" , 0x019300 },
+ { "Asia/Aqtobe" , 0x0194FF },
+ { "Asia/Ashgabat" , 0x0196B7 },
+ { "Asia/Ashkhabad" , 0x0197D4 },
+ { "Asia/Baghdad" , 0x0198F1 },
+ { "Asia/Bahrain" , 0x019A66 },
+ { "Asia/Baku" , 0x019ACC },
+ { "Asia/Bangkok" , 0x019DB4 },
+ { "Asia/Beirut" , 0x019E09 },
+ { "Asia/Bishkek" , 0x01A116 },
+ { "Asia/Brunei" , 0x01A2C2 },
+ { "Asia/Calcutta" , 0x01A324 },
+ { "Asia/Choibalsan" , 0x01A39D },
+ { "Asia/Chongqing" , 0x01A516 },
+ { "Asia/Chungking" , 0x01A605 },
+ { "Asia/Colombo" , 0x01A6B4 },
+ { "Asia/Dacca" , 0x01A750 },
+ { "Asia/Damascus" , 0x01A7F6 },
+ { "Asia/Dhaka" , 0x01AB46 },
+ { "Asia/Dili" , 0x01ABEC },
+ { "Asia/Dubai" , 0x01AC76 },
+ { "Asia/Dushanbe" , 0x01ACCB },
+ { "Asia/Gaza" , 0x01ADCE },
+ { "Asia/Harbin" , 0x01B121 },
+ { "Asia/Hebron" , 0x01B208 },
+ { "Asia/Ho_Chi_Minh" , 0x01B564 },
+ { "Asia/Hong_Kong" , 0x01B5DC },
+ { "Asia/Hovd" , 0x01B79E },
+ { "Asia/Irkutsk" , 0x01B916 },
+ { "Asia/Istanbul" , 0x01BAFC },
+ { "Asia/Jakarta" , 0x01BEE9 },
+ { "Asia/Jayapura" , 0x01BF93 },
+ { "Asia/Jerusalem" , 0x01C02F },
+ { "Asia/Kabul" , 0x01C35E },
+ { "Asia/Kamchatka" , 0x01C3AF },
+ { "Asia/Karachi" , 0x01C58B },
+ { "Asia/Kashgar" , 0x01C640 },
+ { "Asia/Kathmandu" , 0x01C711 },
+ { "Asia/Katmandu" , 0x01C777 },
+ { "Asia/Khandyga" , 0x01C7DD },
+ { "Asia/Kolkata" , 0x01CA02 },
+ { "Asia/Krasnoyarsk" , 0x01CA7B },
+ { "Asia/Kuala_Lumpur" , 0x01CC63 },
+ { "Asia/Kuching" , 0x01CD20 },
+ { "Asia/Kuwait" , 0x01CE0E },
+ { "Asia/Macao" , 0x01CE63 },
+ { "Asia/Macau" , 0x01CF9E },
+ { "Asia/Magadan" , 0x01D0D9 },
+ { "Asia/Makassar" , 0x01D2BB },
+ { "Asia/Manila" , 0x01D380 },
+ { "Asia/Muscat" , 0x01D405 },
+ { "Asia/Nicosia" , 0x01D45A },
+ { "Asia/Novokuznetsk" , 0x01D742 },
+ { "Asia/Novosibirsk" , 0x01D944 },
+ { "Asia/Omsk" , 0x01DB2F },
+ { "Asia/Oral" , 0x01DD16 },
+ { "Asia/Phnom_Penh" , 0x01DEE6 },
+ { "Asia/Pontianak" , 0x01DF5E },
+ { "Asia/Pyongyang" , 0x01E020 },
+ { "Asia/Qatar" , 0x01E08D },
+ { "Asia/Qyzylorda" , 0x01E0F3 },
+ { "Asia/Rangoon" , 0x01E2C9 },
+ { "Asia/Riyadh" , 0x01E341 },
+ { "Asia/Saigon" , 0x01E396 },
+ { "Asia/Sakhalin" , 0x01E40E },
+ { "Asia/Samarkand" , 0x01E605 },
+ { "Asia/Seoul" , 0x01E73B },
+ { "Asia/Shanghai" , 0x01E7DF },
+ { "Asia/Singapore" , 0x01E8BF },
+ { "Asia/Taipei" , 0x01E976 },
+ { "Asia/Tashkent" , 0x01EA8E },
+ { "Asia/Tbilisi" , 0x01EBBF },
+ { "Asia/Tehran" , 0x01ED79 },
+ { "Asia/Tel_Aviv" , 0x01EFE7 },
+ { "Asia/Thimbu" , 0x01F316 },
+ { "Asia/Thimphu" , 0x01F37C },
+ { "Asia/Tokyo" , 0x01F3E2 },
+ { "Asia/Ujung_Pandang" , 0x01F46B },
+ { "Asia/Ulaanbaatar" , 0x01F4E8 },
+ { "Asia/Ulan_Bator" , 0x01F643 },
+ { "Asia/Urumqi" , 0x01F790 },
+ { "Asia/Ust-Nera" , 0x01F857 },
+ { "Asia/Vientiane" , 0x01FA5C },
+ { "Asia/Vladivostok" , 0x01FAD4 },
+ { "Asia/Yakutsk" , 0x01FCC0 },
+ { "Asia/Yekaterinburg" , 0x01FEA5 },
+ { "Asia/Yerevan" , 0x0200B0 },
+ { "Atlantic/Azores" , 0x0202B0 },
+ { "Atlantic/Bermuda" , 0x0207B3 },
+ { "Atlantic/Canary" , 0x020A94 },
+ { "Atlantic/Cape_Verde" , 0x020D6A },
+ { "Atlantic/Faeroe" , 0x020DE3 },
+ { "Atlantic/Faroe" , 0x021087 },
+ { "Atlantic/Jan_Mayen" , 0x02132B },
+ { "Atlantic/Madeira" , 0x02165D },
+ { "Atlantic/Reykjavik" , 0x021B66 },
+ { "Atlantic/South_Georgia" , 0x021D1F },
+ { "Atlantic/St_Helena" , 0x021F31 },
+ { "Atlantic/Stanley" , 0x021D63 },
+ { "Australia/ACT" , 0x021F86 },
+ { "Australia/Adelaide" , 0x0222A3 },
+ { "Australia/Brisbane" , 0x0225CF },
+ { "Australia/Broken_Hill" , 0x022696 },
+ { "Australia/Canberra" , 0x0229D4 },
+ { "Australia/Currie" , 0x022CF1 },
+ { "Australia/Darwin" , 0x023024 },
+ { "Australia/Eucla" , 0x0230AA },
+ { "Australia/Hobart" , 0x02317F },
+ { "Australia/LHI" , 0x0234DD },
+ { "Australia/Lindeman" , 0x023778 },
+ { "Australia/Lord_Howe" , 0x023859 },
+ { "Australia/Melbourne" , 0x023B04 },
+ { "Australia/North" , 0x023E29 },
+ { "Australia/NSW" , 0x023E9D },
+ { "Australia/Perth" , 0x0241BA },
+ { "Australia/Queensland" , 0x024292 },
+ { "Australia/South" , 0x02433E },
+ { "Australia/Sydney" , 0x02465B },
+ { "Australia/Tasmania" , 0x024998 },
+ { "Australia/Victoria" , 0x024CDD },
+ { "Australia/West" , 0x024FFA },
+ { "Australia/Yancowinna" , 0x0250B0 },
+ { "Brazil/Acre" , 0x0253D2 },
+ { "Brazil/DeNoronha" , 0x0254D6 },
+ { "Brazil/East" , 0x0255F6 },
+ { "Brazil/West" , 0x0258D3 },
+ { "Canada/Atlantic" , 0x0259CB },
+ { "Canada/Central" , 0x025EB3 },
+ { "Canada/East-Saskatchewan" , 0x0267BD },
+ { "Canada/Eastern" , 0x0262CD },
+ { "Canada/Mountain" , 0x026946 },
+ { "Canada/Newfoundland" , 0x026CBC },
+ { "Canada/Pacific" , 0x0271E7 },
+ { "Canada/Saskatchewan" , 0x027600 },
+ { "Canada/Yukon" , 0x027789 },
+ { "CET" , 0x027A8C },
+ { "Chile/Continental" , 0x027D95 },
+ { "Chile/EasterIsland" , 0x028130 },
+ { "CST6CDT" , 0x028472 },
+ { "Cuba" , 0x0287C3 },
+ { "EET" , 0x028B36 },
+ { "Egypt" , 0x028DE9 },
+ { "Eire" , 0x0290AC },
+ { "EST" , 0x0295BD },
+ { "EST5EDT" , 0x029601 },
+ { "Etc/GMT" , 0x029952 },
+ { "Etc/GMT+0" , 0x029A1E },
+ { "Etc/GMT+1" , 0x029AA8 },
+ { "Etc/GMT+10" , 0x029B35 },
+ { "Etc/GMT+11" , 0x029BC3 },
+ { "Etc/GMT+12" , 0x029C51 },
+ { "Etc/GMT+2" , 0x029D6C },
+ { "Etc/GMT+3" , 0x029DF8 },
+ { "Etc/GMT+4" , 0x029E84 },
+ { "Etc/GMT+5" , 0x029F10 },
+ { "Etc/GMT+6" , 0x029F9C },
+ { "Etc/GMT+7" , 0x02A028 },
+ { "Etc/GMT+8" , 0x02A0B4 },
+ { "Etc/GMT+9" , 0x02A140 },
+ { "Etc/GMT-0" , 0x0299DA },
+ { "Etc/GMT-1" , 0x029A62 },
+ { "Etc/GMT-10" , 0x029AEE },
+ { "Etc/GMT-11" , 0x029B7C },
+ { "Etc/GMT-12" , 0x029C0A },
+ { "Etc/GMT-13" , 0x029C98 },
+ { "Etc/GMT-14" , 0x029CDF },
+ { "Etc/GMT-2" , 0x029D26 },
+ { "Etc/GMT-3" , 0x029DB2 },
+ { "Etc/GMT-4" , 0x029E3E },
+ { "Etc/GMT-5" , 0x029ECA },
+ { "Etc/GMT-6" , 0x029F56 },
+ { "Etc/GMT-7" , 0x029FE2 },
+ { "Etc/GMT-8" , 0x02A06E },
+ { "Etc/GMT-9" , 0x02A0FA },
+ { "Etc/GMT0" , 0x029996 },
+ { "Etc/Greenwich" , 0x02A186 },
+ { "Etc/UCT" , 0x02A1CA },
+ { "Etc/Universal" , 0x02A20E },
+ { "Etc/UTC" , 0x02A252 },
+ { "Etc/Zulu" , 0x02A296 },
+ { "Europe/Amsterdam" , 0x02A2DA },
+ { "Europe/Andorra" , 0x02A718 },
+ { "Europe/Athens" , 0x02A994 },
+ { "Europe/Belfast" , 0x02ACD7 },
+ { "Europe/Belgrade" , 0x02B20E },
+ { "Europe/Berlin" , 0x02B4D7 },
+ { "Europe/Bratislava" , 0x02B83B },
+ { "Europe/Brussels" , 0x02BB6D },
+ { "Europe/Bucharest" , 0x02BFA4 },
+ { "Europe/Budapest" , 0x02C2CE },
+ { "Europe/Busingen" , 0x02C641 },
+ { "Europe/Chisinau" , 0x02C8F8 },
+ { "Europe/Copenhagen" , 0x02CC86 },
+ { "Europe/Dublin" , 0x02CF90 },
+ { "Europe/Gibraltar" , 0x02D4A1 },
+ { "Europe/Guernsey" , 0x02D8F8 },
+ { "Europe/Helsinki" , 0x02DE2F },
+ { "Europe/Isle_of_Man" , 0x02E0E5 },
+ { "Europe/Istanbul" , 0x02E61C },
+ { "Europe/Jersey" , 0x02EA09 },
+ { "Europe/Kaliningrad" , 0x02EF40 },
+ { "Europe/Kiev" , 0x02F1A6 },
+ { "Europe/Lisbon" , 0x02F4BD },
+ { "Europe/Ljubljana" , 0x02F9C1 },
+ { "Europe/London" , 0x02FC8A },
+ { "Europe/Luxembourg" , 0x0301C1 },
+ { "Europe/Madrid" , 0x030617 },
+ { "Europe/Malta" , 0x0309DD },
+ { "Europe/Mariehamn" , 0x030D96 },
+ { "Europe/Minsk" , 0x03104C },
+ { "Europe/Monaco" , 0x03125A },
+ { "Europe/Moscow" , 0x031695 },
+ { "Europe/Nicosia" , 0x0318E6 },
+ { "Europe/Oslo" , 0x031BCE },
+ { "Europe/Paris" , 0x031F00 },
+ { "Europe/Podgorica" , 0x032346 },
+ { "Europe/Prague" , 0x03260F },
+ { "Europe/Riga" , 0x032941 },
+ { "Europe/Rome" , 0x032C86 },
+ { "Europe/Samara" , 0x033049 },
+ { "Europe/San_Marino" , 0x03327C },
+ { "Europe/Sarajevo" , 0x03363F },
+ { "Europe/Simferopol" , 0x033908 },
+ { "Europe/Skopje" , 0x033C33 },
+ { "Europe/Sofia" , 0x033EFC },
+ { "Europe/Stockholm" , 0x034204 },
+ { "Europe/Tallinn" , 0x0344B3 },
+ { "Europe/Tirane" , 0x0347ED },
+ { "Europe/Tiraspol" , 0x034AF3 },
+ { "Europe/Uzhgorod" , 0x034E81 },
+ { "Europe/Vaduz" , 0x035198 },
+ { "Europe/Vatican" , 0x035447 },
+ { "Europe/Vienna" , 0x03580A },
+ { "Europe/Vilnius" , 0x035B37 },
+ { "Europe/Volgograd" , 0x035E76 },
+ { "Europe/Warsaw" , 0x036076 },
+ { "Europe/Zagreb" , 0x036457 },
+ { "Europe/Zaporozhye" , 0x036720 },
+ { "Europe/Zurich" , 0x036A61 },
+ { "Factory" , 0x036D10 },
+ { "GB" , 0x036D81 },
+ { "GB-Eire" , 0x0372B8 },
+ { "GMT" , 0x0377EF },
+ { "GMT+0" , 0x0378BB },
+ { "GMT-0" , 0x037877 },
+ { "GMT0" , 0x037833 },
+ { "Greenwich" , 0x0378FF },
+ { "Hongkong" , 0x037943 },
+ { "HST" , 0x037B05 },
+ { "Iceland" , 0x037B49 },
+ { "Indian/Antananarivo" , 0x037D02 },
+ { "Indian/Chagos" , 0x037D76 },
+ { "Indian/Christmas" , 0x037DD8 },
+ { "Indian/Cocos" , 0x037E1C },
+ { "Indian/Comoro" , 0x037E60 },
+ { "Indian/Kerguelen" , 0x037EB5 },
+ { "Indian/Mahe" , 0x037F0A },
+ { "Indian/Maldives" , 0x037F5F },
+ { "Indian/Mauritius" , 0x037FB4 },
+ { "Indian/Mayotte" , 0x03802A },
+ { "Indian/Reunion" , 0x03807F },
+ { "Iran" , 0x0380D4 },
+ { "Israel" , 0x038342 },
+ { "Jamaica" , 0x038671 },
+ { "Japan" , 0x038736 },
+ { "Kwajalein" , 0x0387BF },
+ { "Libya" , 0x038822 },
+ { "MET" , 0x03892B },
+ { "Mexico/BajaNorte" , 0x038C34 },
+ { "Mexico/BajaSur" , 0x038F9D },
+ { "Mexico/General" , 0x0391E2 },
+ { "MST" , 0x039440 },
+ { "MST7MDT" , 0x039484 },
+ { "Navajo" , 0x0397D5 },
+ { "NZ" , 0x039B4E },
+ { "NZ-CHAT" , 0x039ECC },
+ { "Pacific/Apia" , 0x03A1B4 },
+ { "Pacific/Auckland" , 0x03A350 },
+ { "Pacific/Chatham" , 0x03A6DC },
+ { "Pacific/Chuuk" , 0x03A9D3 },
+ { "Pacific/Easter" , 0x03AA2C },
+ { "Pacific/Efate" , 0x03AD8A },
+ { "Pacific/Enderbury" , 0x03AE50 },
+ { "Pacific/Fakaofo" , 0x03AEBE },
+ { "Pacific/Fiji" , 0x03AF0F },
+ { "Pacific/Funafuti" , 0x03B0A2 },
+ { "Pacific/Galapagos" , 0x03B0E6 },
+ { "Pacific/Gambier" , 0x03B15E },
+ { "Pacific/Guadalcanal" , 0x03B1C3 },
+ { "Pacific/Guam" , 0x03B218 },
+ { "Pacific/Honolulu" , 0x03B26E },
+ { "Pacific/Johnston" , 0x03B2E5 },
+ { "Pacific/Kiritimati" , 0x03B364 },
+ { "Pacific/Kosrae" , 0x03B3CF },
+ { "Pacific/Kwajalein" , 0x03B42C },
+ { "Pacific/Majuro" , 0x03B498 },
+ { "Pacific/Marquesas" , 0x03B4F7 },
+ { "Pacific/Midway" , 0x03B55E },
+ { "Pacific/Nauru" , 0x03B5E8 },
+ { "Pacific/Niue" , 0x03B660 },
+ { "Pacific/Norfolk" , 0x03B6BE },
+ { "Pacific/Noumea" , 0x03B713 },
+ { "Pacific/Pago_Pago" , 0x03B7A3 },
+ { "Pacific/Palau" , 0x03B82C },
+ { "Pacific/Pitcairn" , 0x03B870 },
+ { "Pacific/Pohnpei" , 0x03B8C5 },
+ { "Pacific/Ponape" , 0x03B91A },
+ { "Pacific/Port_Moresby" , 0x03B95F },
+ { "Pacific/Rarotonga" , 0x03B9A3 },
+ { "Pacific/Saipan" , 0x03BA7F },
+ { "Pacific/Samoa" , 0x03BAE2 },
+ { "Pacific/Tahiti" , 0x03BB6B },
+ { "Pacific/Tarawa" , 0x03BBD0 },
+ { "Pacific/Tongatapu" , 0x03BC24 },
+ { "Pacific/Truk" , 0x03BCB0 },
+ { "Pacific/Wake" , 0x03BCF5 },
+ { "Pacific/Wallis" , 0x03BD45 },
+ { "Pacific/Yap" , 0x03BD89 },
+ { "Poland" , 0x03BDCE },
+ { "Portugal" , 0x03C1AF },
+ { "PRC" , 0x03C6AB },
+ { "PST8PDT" , 0x03C75C },
+ { "ROC" , 0x03CAAD },
+ { "ROK" , 0x03CBC5 },
+ { "Singapore" , 0x03CC69 },
+ { "Turkey" , 0x03CD20 },
+ { "UCT" , 0x03D10D },
+ { "Universal" , 0x03D151 },
+ { "US/Alaska" , 0x03D195 },
+ { "US/Aleutian" , 0x03D4FE },
+ { "US/Arizona" , 0x03D864 },
+ { "US/Central" , 0x03D8F2 },
+ { "US/East-Indiana" , 0x03E2FC },
+ { "US/Eastern" , 0x03DDFD },
+ { "US/Hawaii" , 0x03E566 },
+ { "US/Indiana-Starke" , 0x03E5D7 },
+ { "US/Michigan" , 0x03E948 },
+ { "US/Mountain" , 0x03EC7F },
+ { "US/Pacific" , 0x03EFF8 },
+ { "US/Pacific-New" , 0x03F3FD },
+ { "US/Samoa" , 0x03F802 },
+ { "UTC" , 0x03F88B },
+ { "W-SU" , 0x03FB82 },
+ { "WET" , 0x03F8CF },
+ { "Zulu" , 0x03FDBC },
};
/* This is a generated file, do not modify */
-const unsigned char timelib_timezone_db_data_builtin[261404] = {
+const unsigned char timelib_timezone_db_data_builtin[261632] = {
/* Africa/Abidjan */
@@ -3490,7 +3490,7 @@ const unsigned char timelib_timezone_db_data_builtin[261404] = {
0x33, 0x47, 0x2D, 0xD0, 0x34, 0x40, 0x59, 0x50, 0x35, 0x1D, 0xD5, 0x50, 0x36, 0x32, 0xB0, 0x50,
0x36, 0xFD, 0xB7, 0x50, 0x38, 0x1B, 0xCC, 0xD0, 0x38, 0xE6, 0xD3, 0xD0, 0x39, 0xFB, 0xAE, 0xD0,
0x3A, 0xC6, 0xB5, 0xD0, 0x3B, 0xDB, 0x90, 0xD0, 0x3C, 0xAF, 0xD2, 0x50, 0x3D, 0xBB, 0x72, 0xD0,
-0x3E, 0x8F, 0xB4, 0x50, 0x3F, 0x9B, 0x54, 0xD0, 0x40, 0x6F, 0x96, 0x50, 0x45, 0x44, 0x35, 0x50,
+0x3E, 0x8F, 0xB4, 0x50, 0x3F, 0x9B, 0x54, 0xD0, 0x40, 0x66, 0x5B, 0xD0, 0x45, 0x44, 0x35, 0x50,
0x45, 0xF3, 0x8C, 0xD0, 0x47, 0x24, 0x17, 0x50, 0x47, 0xDC, 0xA9, 0x50, 0x49, 0x03, 0xF9, 0x50,
0x49, 0xB3, 0x50, 0xD0, 0x4A, 0xE3, 0xDB, 0x50, 0x4B, 0x9C, 0x6D, 0x50, 0x4C, 0xCC, 0xF7, 0xD0,
0x4D, 0x85, 0x89, 0xD0, 0x4E, 0xBF, 0x4E, 0xD0, 0x4F, 0x77, 0xE0, 0xD0, 0x50, 0x95, 0xF6, 0x50,
@@ -7552,8 +7552,8 @@ const unsigned char timelib_timezone_db_data_builtin[261404] = {
/* Asia/Amman */
0x50, 0x48, 0x50, 0x31, 0x01, 0x4A, 0x4F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
-0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00,
-0x00, 0x00, 0x00, 0x45, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x11, 0xB6, 0xA3, 0xD6, 0xD0,
+0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x00,
+0x00, 0x00, 0x00, 0x75, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x0D, 0xB6, 0xA3, 0xD6, 0xD0,
0x06, 0x72, 0x79, 0xE0, 0x07, 0x0C, 0xAB, 0x50, 0x08, 0x24, 0x37, 0x60, 0x08, 0xED, 0xDE, 0xD0,
0x0A, 0x05, 0x6A, 0xE0, 0x0A, 0xCF, 0x12, 0x50, 0x0B, 0xE7, 0xEF, 0xE0, 0x0C, 0xDA, 0x75, 0xD0,
0x0D, 0xC9, 0x23, 0x60, 0x0E, 0x92, 0xCA, 0xD0, 0x0F, 0xA9, 0x05, 0x60, 0x10, 0x72, 0xAC, 0xD0,
@@ -7570,17 +7570,31 @@ const unsigned char timelib_timezone_db_data_builtin[261404] = {
0x42, 0x4C, 0x72, 0xE0, 0x43, 0x3C, 0x63, 0xE0, 0x44, 0x2C, 0x54, 0xE0, 0x45, 0x41, 0x2F, 0xE0,
0x46, 0x0C, 0x36, 0xE0, 0x47, 0x21, 0x11, 0xE0, 0x47, 0xEC, 0x18, 0xE0, 0x49, 0x0A, 0x2E, 0x60,
0x49, 0xCB, 0xFA, 0xE0, 0x4A, 0xEA, 0x10, 0x60, 0x4B, 0xAB, 0xDC, 0xE0, 0x4C, 0xC9, 0xF2, 0x60,
-0x4D, 0x94, 0xF9, 0x60, 0x4E, 0xA9, 0xD4, 0x60, 0x4F, 0x74, 0xDB, 0x60, 0x50, 0x89, 0xB6, 0x60,
+0x4D, 0x94, 0xF9, 0x60, 0x4E, 0xA9, 0xD4, 0x60, 0x4F, 0x74, 0xDB, 0x60, 0x52, 0xB3, 0x5E, 0x50,
+0x53, 0x34, 0x9F, 0x60, 0x54, 0x52, 0xB4, 0xE0, 0x55, 0x14, 0x81, 0x60, 0x56, 0x32, 0x96, 0xE0,
+0x56, 0xFD, 0x9D, 0xE0, 0x58, 0x12, 0x78, 0xE0, 0x58, 0xDD, 0x7F, 0xE0, 0x59, 0xF2, 0x5A, 0xE0,
+0x5A, 0xBD, 0x61, 0xE0, 0x5B, 0xD2, 0x3C, 0xE0, 0x5C, 0x9D, 0x43, 0xE0, 0x5D, 0xB2, 0x1E, 0xE0,
+0x5E, 0x7D, 0x25, 0xE0, 0x5F, 0x9B, 0x3B, 0x60, 0x60, 0x5D, 0x07, 0xE0, 0x61, 0x7B, 0x1D, 0x60,
+0x62, 0x46, 0x24, 0x60, 0x63, 0x5A, 0xFF, 0x60, 0x64, 0x26, 0x06, 0x60, 0x65, 0x3A, 0xE1, 0x60,
+0x66, 0x05, 0xE8, 0x60, 0x67, 0x1A, 0xC3, 0x60, 0x67, 0xE5, 0xCA, 0x60, 0x69, 0x03, 0xDF, 0xE0,
+0x69, 0xC5, 0xAC, 0x60, 0x6A, 0xE3, 0xC1, 0xE0, 0x6B, 0xA5, 0x8E, 0x60, 0x6C, 0xC3, 0xA3, 0xE0,
+0x6D, 0x8E, 0xAA, 0xE0, 0x6E, 0xA3, 0x85, 0xE0, 0x6F, 0x6E, 0x8C, 0xE0, 0x70, 0x83, 0x67, 0xE0,
+0x71, 0x4E, 0x6E, 0xE0, 0x72, 0x63, 0x49, 0xE0, 0x73, 0x2E, 0x50, 0xE0, 0x74, 0x4C, 0x66, 0x60,
+0x75, 0x0E, 0x32, 0xE0, 0x76, 0x2C, 0x48, 0x60, 0x76, 0xF7, 0x4F, 0x60, 0x78, 0x0C, 0x2A, 0x60,
+0x78, 0xD7, 0x31, 0x60, 0x79, 0xEC, 0x0C, 0x60, 0x7A, 0xB7, 0x13, 0x60, 0x7B, 0xCB, 0xEE, 0x60,
+0x7C, 0x96, 0xF5, 0x60, 0x7D, 0xB5, 0x0A, 0xE0, 0x7E, 0x76, 0xD7, 0x60, 0x7F, 0x94, 0xEC, 0xE0,
0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01,
0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01, 0x02, 0x01,
0x02, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x04, 0x03, 0x04, 0x03, 0x04, 0x03, 0x01,
0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01,
-0x03, 0x01, 0x03, 0x01, 0x05, 0x00, 0x00, 0x21, 0xB0, 0x00, 0x00, 0x00, 0x00, 0x2A, 0x30, 0x01,
+0x03, 0x01, 0x03, 0x01, 0x02, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01,
+0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01,
+0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01, 0x03, 0x01,
+0x03, 0x01, 0x03, 0x01, 0x03, 0x00, 0x00, 0x21, 0xB0, 0x00, 0x00, 0x00, 0x00, 0x2A, 0x30, 0x01,
0x04, 0x00, 0x00, 0x1C, 0x20, 0x00, 0x09, 0x00, 0x00, 0x1C, 0x20, 0x00, 0x09, 0x00, 0x00, 0x2A,
-0x30, 0x01, 0x04, 0x00, 0x00, 0x2A, 0x30, 0x00, 0x0D, 0x4C, 0x4D, 0x54, 0x00, 0x45, 0x45, 0x53,
-0x54, 0x00, 0x45, 0x45, 0x54, 0x00, 0x41, 0x53, 0x54, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x01,
-0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xBA, 0x14, 0xB8, 0x01, 0x49, 0x7C, 0xF5, 0x00, 0x00,
-0x00, 0x00,
+0x30, 0x01, 0x04, 0x4C, 0x4D, 0x54, 0x00, 0x45, 0x45, 0x53, 0x54, 0x00, 0x45, 0x45, 0x54, 0x00,
+0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xBA, 0x14, 0xB8, 0x01, 0x49,
+0x7C, 0xF5, 0x00, 0x00, 0x00, 0x00,
/* Asia/Anadyr */
0x50, 0x48, 0x50, 0x31, 0x01, 0x52, 0x55, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
@@ -11908,7 +11922,7 @@ const unsigned char timelib_timezone_db_data_builtin[261404] = {
0x33, 0x47, 0x2D, 0xD0, 0x34, 0x40, 0x59, 0x50, 0x35, 0x1D, 0xD5, 0x50, 0x36, 0x32, 0xB0, 0x50,
0x36, 0xFD, 0xB7, 0x50, 0x38, 0x1B, 0xCC, 0xD0, 0x38, 0xE6, 0xD3, 0xD0, 0x39, 0xFB, 0xAE, 0xD0,
0x3A, 0xC6, 0xB5, 0xD0, 0x3B, 0xDB, 0x90, 0xD0, 0x3C, 0xAF, 0xD2, 0x50, 0x3D, 0xBB, 0x72, 0xD0,
-0x3E, 0x8F, 0xB4, 0x50, 0x3F, 0x9B, 0x54, 0xD0, 0x40, 0x6F, 0x96, 0x50, 0x45, 0x44, 0x35, 0x50,
+0x3E, 0x8F, 0xB4, 0x50, 0x3F, 0x9B, 0x54, 0xD0, 0x40, 0x66, 0x5B, 0xD0, 0x45, 0x44, 0x35, 0x50,
0x45, 0xF3, 0x8C, 0xD0, 0x47, 0x24, 0x17, 0x50, 0x47, 0xDC, 0xA9, 0x50, 0x49, 0x03, 0xF9, 0x50,
0x49, 0xB3, 0x50, 0xD0, 0x4A, 0xE3, 0xDB, 0x50, 0x4B, 0x9C, 0x6D, 0x50, 0x4C, 0xCC, 0xF7, 0xD0,
0x4D, 0x85, 0x89, 0xD0, 0x4E, 0xBF, 0x4E, 0xD0, 0x4F, 0x77, 0xE0, 0xD0, 0x50, 0x95, 0xF6, 0x50,
@@ -18402,4 +18416,4 @@ const unsigned char timelib_timezone_db_data_builtin[261404] = {
0x00, 0x00, 0x55, 0x54, 0x43, 0x00, 0x00, 0x00, 0x00, 0x89, 0x54, 0x40, 0x01, 0x12, 0xA8, 0x80,
0x00, 0x00, 0x00, 0x00, };
-const timelib_tzdb timezonedb_builtin = { "2013.8", 579, timezonedb_idx_builtin, timelib_timezone_db_data_builtin };
+const timelib_tzdb timezonedb_builtin = { "2013.9", 579, timezonedb_idx_builtin, timelib_timezone_db_data_builtin };
diff --git a/ext/date/lib/tm2unixtime.c b/ext/date/lib/tm2unixtime.c
index 23fe202ba9..5fc84a5ff7 100644
--- a/ext/date/lib/tm2unixtime.c
+++ b/ext/date/lib/tm2unixtime.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/date/lib/unixtime2tm.c b/ext/date/lib/unixtime2tm.c
index c177feebb1..9870313fbc 100644
--- a/ext/date/lib/unixtime2tm.c
+++ b/ext/date/lib/unixtime2tm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -137,19 +137,16 @@ void timelib_unixtime2gmt(timelib_time* tm, timelib_sll ts)
void timelib_update_from_sse(timelib_time *tm)
{
timelib_sll sse;
+ int z = tm->z;
+ signed int dst = tm->dst;
sse = tm->sse;
switch (tm->zone_type) {
case TIMELIB_ZONETYPE_ABBR:
case TIMELIB_ZONETYPE_OFFSET: {
- int z = tm->z;
- signed int dst = tm->dst;
-
timelib_unixtime2gmt(tm, tm->sse - (tm->z * 60) + (tm->dst * 3600));
- tm->z = z;
- tm->dst = dst;
goto cleanup;
}
@@ -171,6 +168,8 @@ cleanup:
tm->sse = sse;
tm->is_localtime = 1;
tm->have_zone = 1;
+ tm->z = z;
+ tm->dst = dst;
}
void timelib_unixtime2local(timelib_time *tm, timelib_sll ts)
@@ -215,6 +214,34 @@ void timelib_unixtime2local(timelib_time *tm, timelib_sll ts)
tm->have_zone = 1;
}
+void timelib_set_timezone_from_offset(timelib_time *t, timelib_sll utc_offset)
+{
+ if (t->tz_abbr) {
+ free(t->tz_abbr);
+ }
+ t->tz_abbr = NULL;
+
+ t->z = utc_offset;
+ t->have_zone = 1;
+ t->zone_type = TIMELIB_ZONETYPE_OFFSET;
+ t->dst = 0;
+ t->tz_info = NULL;
+}
+
+void timelib_set_timezone_from_abbr(timelib_time *t, timelib_abbr_info abbr_info)
+{
+ if (t->tz_abbr) {
+ free(t->tz_abbr);
+ }
+ t->tz_abbr = strdup(abbr_info.abbr);
+
+ t->z = abbr_info.utc_offset;
+ t->have_zone = 1;
+ t->zone_type = TIMELIB_ZONETYPE_ABBR;
+ t->dst = abbr_info.dst;
+ t->tz_info = NULL;
+}
+
void timelib_set_timezone(timelib_time *t, timelib_tzinfo *tz)
{
timelib_time_offset *gmt_offset;
diff --git a/ext/date/php_date.c b/ext/date/php_date.c
index 13a645117c..f6b12bc42e 100644
--- a/ext/date/php_date.c
+++ b/ext/date/php_date.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -797,6 +797,14 @@ PHP_RSHUTDOWN_FUNCTION(date)
#define DATE_FORMAT_ISO8601 "Y-m-d\\TH:i:sO"
+/*
+ * This comes from various sources that like to contradict. I'm going with the
+ * format here because of:
+ * http://msdn.microsoft.com/en-us/library/windows/desktop/aa384321%28v=vs.85%29.aspx
+ * and http://curl.haxx.se/rfc/cookie_spec.html
+ */
+#define DATE_FORMAT_COOKIE "l, d-M-Y H:i:s T"
+
#define DATE_TZ_ERRMSG \
"It is not safe to rely on the system's timezone settings. You are " \
"*required* to use the date.timezone setting or the " \
@@ -827,7 +835,7 @@ PHP_MINIT_FUNCTION(date)
* with the variations that the only legal time zone is GMT
* and the separators between the elements of the date must be dashes."
*/
- REGISTER_STRING_CONSTANT("DATE_COOKIE", DATE_FORMAT_RFC850, CONST_CS | CONST_PERSISTENT);
+ REGISTER_STRING_CONSTANT("DATE_COOKIE", DATE_FORMAT_COOKIE, CONST_CS | CONST_PERSISTENT);
REGISTER_STRING_CONSTANT("DATE_ISO8601", DATE_FORMAT_ISO8601, CONST_CS | CONST_PERSISTENT);
REGISTER_STRING_CONSTANT("DATE_RFC822", DATE_FORMAT_RFC822, CONST_CS | CONST_PERSISTENT);
REGISTER_STRING_CONSTANT("DATE_RFC850", DATE_FORMAT_RFC850, CONST_CS | CONST_PERSISTENT);
@@ -1981,12 +1989,25 @@ zend_object_iterator *date_object_period_get_iterator(zend_class_entry *ce, zval
return (zend_object_iterator*)iterator;
}
+static int implement_date_interface_handler(zend_class_entry *interface, zend_class_entry *implementor TSRMLS_DC)
+{
+ if (implementor->type == ZEND_USER_CLASS &&
+ !instanceof_function(implementor, date_ce_date TSRMLS_CC) &&
+ !instanceof_function(implementor, date_ce_immutable TSRMLS_CC)
+ ) {
+ zend_error(E_ERROR, "DateTimeInterface can't be implemented by user classes");
+ }
+
+ return SUCCESS;
+}
+
static void date_register_classes(TSRMLS_D)
{
zend_class_entry ce_date, ce_immutable, ce_timezone, ce_interval, ce_period, ce_interface;
INIT_CLASS_ENTRY(ce_interface, "DateTimeInterface", date_funcs_interface);
date_ce_interface = zend_register_internal_interface(&ce_interface TSRMLS_CC);
+ date_ce_interface->interface_gets_implemented = implement_date_interface_handler;
INIT_CLASS_ENTRY(ce_date, "DateTime", date_funcs_date);
ce_date.create_object = date_object_new_date;
@@ -2002,7 +2023,7 @@ static void date_register_classes(TSRMLS_D)
zend_declare_class_constant_stringl(date_ce_date, const_name, sizeof(const_name)-1, value, sizeof(value)-1 TSRMLS_CC);
REGISTER_DATE_CLASS_CONST_STRING("ATOM", DATE_FORMAT_RFC3339);
- REGISTER_DATE_CLASS_CONST_STRING("COOKIE", DATE_FORMAT_RFC850);
+ REGISTER_DATE_CLASS_CONST_STRING("COOKIE", DATE_FORMAT_COOKIE);
REGISTER_DATE_CLASS_CONST_STRING("ISO8601", DATE_FORMAT_ISO8601);
REGISTER_DATE_CLASS_CONST_STRING("RFC822", DATE_FORMAT_RFC822);
REGISTER_DATE_CLASS_CONST_STRING("RFC850", DATE_FORMAT_RFC850);
@@ -2276,7 +2297,7 @@ static zend_object_value date_object_clone_timezone(zval *this_ptr TSRMLS_DC)
case TIMELIB_ZONETYPE_ABBR:
new_obj->tzi.z.utc_offset = old_obj->tzi.z.utc_offset;
new_obj->tzi.z.dst = old_obj->tzi.z.dst;
- new_obj->tzi.z.abbr = old_obj->tzi.z.abbr;
+ new_obj->tzi.z.abbr = strdup(old_obj->tzi.z.abbr);
break;
}
@@ -2602,6 +2623,7 @@ PHPAPI int php_date_initialize(php_date_obj *dateobj, /*const*/ char *time_str,
timelib_fill_holes(dateobj->time, now, TIMELIB_NO_CLONE);
timelib_update_ts(dateobj->time, tzi);
+ timelib_update_from_sse(dateobj->time);
dateobj->time->have_relative = 0;
@@ -3115,33 +3137,16 @@ static void php_date_add(zval *object, zval *interval, zval *return_value TSRMLS
{
php_date_obj *dateobj;
php_interval_obj *intobj;
- int bias = 1;
+ timelib_time *new_time;
dateobj = (php_date_obj *) zend_object_store_get_object(object TSRMLS_CC);
DATE_CHECK_INITIALIZED(dateobj->time, DateTime);
intobj = (php_interval_obj *) zend_object_store_get_object(interval TSRMLS_CC);
DATE_CHECK_INITIALIZED(intobj->initialized, DateInterval);
- if (intobj->diff->have_weekday_relative || intobj->diff->have_special_relative) {
- memcpy(&dateobj->time->relative, intobj->diff, sizeof(struct timelib_rel_time));
- } else {
- if (intobj->diff->invert) {
- bias = -1;
- }
- memset(&dateobj->time->relative, 0, sizeof(struct timelib_rel_time));
- dateobj->time->relative.y = intobj->diff->y * bias;
- dateobj->time->relative.m = intobj->diff->m * bias;
- dateobj->time->relative.d = intobj->diff->d * bias;
- dateobj->time->relative.h = intobj->diff->h * bias;
- dateobj->time->relative.i = intobj->diff->i * bias;
- dateobj->time->relative.s = intobj->diff->s * bias;
- }
- dateobj->time->have_relative = 1;
- dateobj->time->sse_uptodate = 0;
-
- timelib_update_ts(dateobj->time, NULL);
- timelib_update_from_sse(dateobj->time);
- dateobj->time->have_relative = 0;
+ new_time = timelib_add(dateobj->time, intobj->diff);
+ timelib_time_dtor(dateobj->time);
+ dateobj->time = new_time;
}
/* {{{ proto DateTime date_add(DateTime object, DateInterval interval)
@@ -3182,7 +3187,7 @@ static void php_date_sub(zval *object, zval *interval, zval *return_value TSRMLS
{
php_date_obj *dateobj;
php_interval_obj *intobj;
- int bias = 1;
+ timelib_time *new_time;
dateobj = (php_date_obj *) zend_object_store_get_object(object TSRMLS_CC);
DATE_CHECK_INITIALIZED(dateobj->time, DateTime);
@@ -3194,24 +3199,9 @@ static void php_date_sub(zval *object, zval *interval, zval *return_value TSRMLS
return;
}
- if (intobj->diff->invert) {
- bias = -1;
- }
-
- memset(&dateobj->time->relative, 0, sizeof(struct timelib_rel_time));
- dateobj->time->relative.y = 0 - (intobj->diff->y * bias);
- dateobj->time->relative.m = 0 - (intobj->diff->m * bias);
- dateobj->time->relative.d = 0 - (intobj->diff->d * bias);
- dateobj->time->relative.h = 0 - (intobj->diff->h * bias);
- dateobj->time->relative.i = 0 - (intobj->diff->i * bias);
- dateobj->time->relative.s = 0 - (intobj->diff->s * bias);
- dateobj->time->have_relative = 1;
- dateobj->time->sse_uptodate = 0;
-
- timelib_update_ts(dateobj->time, NULL);
- timelib_update_from_sse(dateobj->time);
-
- dateobj->time->have_relative = 0;
+ new_time = timelib_sub(dateobj->time, intobj->diff);
+ timelib_time_dtor(dateobj->time);
+ dateobj->time = new_time;
}
/* {{{ proto DateTime date_sub(DateTime object, DateInterval interval)
@@ -3248,6 +3238,26 @@ PHP_METHOD(DateTimeImmutable, sub)
}
/* }}} */
+static void set_timezone_from_timelib_time(php_timezone_obj *tzobj, timelib_time *t)
+{
+ tzobj->initialized = 1;
+ tzobj->type = t->zone_type;
+ switch (t->zone_type) {
+ case TIMELIB_ZONETYPE_ID:
+ tzobj->tzi.tz = t->tz_info;
+ break;
+ case TIMELIB_ZONETYPE_OFFSET:
+ tzobj->tzi.utc_offset = t->z;
+ break;
+ case TIMELIB_ZONETYPE_ABBR:
+ tzobj->tzi.z.utc_offset = t->z;
+ tzobj->tzi.z.dst = t->dst;
+ tzobj->tzi.z.abbr = strdup(t->tz_abbr);
+ break;
+ }
+}
+
+
/* {{{ proto DateTimeZone date_timezone_get(DateTimeInterface object)
Return new DateTimeZone object relative to give DateTime
*/
@@ -3265,21 +3275,7 @@ PHP_FUNCTION(date_timezone_get)
if (dateobj->time->is_localtime/* && dateobj->time->tz_info*/) {
php_date_instantiate(date_ce_timezone, return_value TSRMLS_CC);
tzobj = (php_timezone_obj *) zend_object_store_get_object(return_value TSRMLS_CC);
- tzobj->initialized = 1;
- tzobj->type = dateobj->time->zone_type;
- switch (dateobj->time->zone_type) {
- case TIMELIB_ZONETYPE_ID:
- tzobj->tzi.tz = dateobj->time->tz_info;
- break;
- case TIMELIB_ZONETYPE_OFFSET:
- tzobj->tzi.utc_offset = dateobj->time->z;
- break;
- case TIMELIB_ZONETYPE_ABBR:
- tzobj->tzi.z.utc_offset = dateobj->time->z;
- tzobj->tzi.z.dst = dateobj->time->dst;
- tzobj->tzi.z.abbr = strdup(dateobj->time->tz_abbr);
- break;
- }
+ set_timezone_from_timelib_time(tzobj, dateobj->time);
} else {
RETURN_FALSE;
}
@@ -3294,11 +3290,18 @@ static void php_date_timezone_set(zval *object, zval *timezone_object, zval *ret
dateobj = (php_date_obj *) zend_object_store_get_object(object TSRMLS_CC);
DATE_CHECK_INITIALIZED(dateobj->time, DateTime);
tzobj = (php_timezone_obj *) zend_object_store_get_object(timezone_object TSRMLS_CC);
- if (tzobj->type != TIMELIB_ZONETYPE_ID) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "Can only do this for zones with ID for now");
- return;
+
+ switch (tzobj->type) {
+ case TIMELIB_ZONETYPE_OFFSET:
+ timelib_set_timezone_from_offset(dateobj->time, tzobj->tzi.utc_offset);
+ break;
+ case TIMELIB_ZONETYPE_ABBR:
+ timelib_set_timezone_from_abbr(dateobj->time, tzobj->tzi.z);
+ break;
+ case TIMELIB_ZONETYPE_ID:
+ timelib_set_timezone(dateobj->time, tzobj->tzi.tz);
+ break;
}
- timelib_set_timezone(dateobj->time, tzobj->tzi.tz);
timelib_unixtime2local(dateobj->time, dateobj->time->sse);
}
@@ -3603,13 +3606,13 @@ PHP_FUNCTION(date_diff)
php_interval_obj *interval;
long absolute = 0;
- if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "OO|l", &object1, date_ce_date, &object2, date_ce_date, &absolute) == FAILURE) {
+ if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "OO|l", &object1, date_ce_interface, &object2, date_ce_interface, &absolute) == FAILURE) {
RETURN_FALSE;
}
dateobj1 = (php_date_obj *) zend_object_store_get_object(object1 TSRMLS_CC);
dateobj2 = (php_date_obj *) zend_object_store_get_object(object2 TSRMLS_CC);
- DATE_CHECK_INITIALIZED(dateobj1->time, DateTime);
- DATE_CHECK_INITIALIZED(dateobj2->time, DateTime);
+ DATE_CHECK_INITIALIZED(dateobj1->time, DateTimeInterface);
+ DATE_CHECK_INITIALIZED(dateobj2->time, DateTimeInterface);
timelib_update_ts(dateobj1->time, NULL);
timelib_update_ts(dateobj2->time, NULL);
@@ -3623,23 +3626,21 @@ PHP_FUNCTION(date_diff)
}
/* }}} */
-static int timezone_initialize(timelib_tzinfo **tzi, /*const*/ char *tz TSRMLS_DC)
+static int timezone_initialize(php_timezone_obj *tzobj, /*const*/ char *tz TSRMLS_DC)
{
- char *tzid;
-
- *tzi = NULL;
-
- if ((tzid = timelib_timezone_id_from_abbr(tz, -1, 0))) {
- *tzi = php_date_parse_tzfile(tzid, DATE_TIMEZONEDB TSRMLS_CC);
+ timelib_time *dummy_t = ecalloc(1, sizeof(timelib_time));
+ int dst, not_found;
+ char *orig_tz = tz;
+
+ dummy_t->z = timelib_parse_zone(&tz, &dst, dummy_t, &not_found, DATE_TIMEZONEDB, php_date_parse_tzfile_wrapper);
+ if (not_found) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown or bad timezone (%s)", orig_tz);
+ efree(dummy_t);
+ return FAILURE;
} else {
- *tzi = php_date_parse_tzfile(tz, DATE_TIMEZONEDB TSRMLS_CC);
- }
-
- if (*tzi) {
+ set_timezone_from_timelib_time(tzobj, dummy_t);
+ efree(dummy_t);
return SUCCESS;
- } else {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unknown or bad timezone (%s)", tz);
- return FAILURE;
}
}
@@ -3650,19 +3651,15 @@ PHP_FUNCTION(timezone_open)
{
char *tz;
int tz_len;
- timelib_tzinfo *tzi = NULL;
php_timezone_obj *tzobj;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &tz, &tz_len) == FAILURE) {
RETURN_FALSE;
}
- if (SUCCESS != timezone_initialize(&tzi, tz TSRMLS_CC)) {
+ tzobj = zend_object_store_get_object(php_date_instantiate(date_ce_timezone, return_value TSRMLS_CC) TSRMLS_CC);
+ if (SUCCESS != timezone_initialize(tzobj, tz TSRMLS_CC)) {
RETURN_FALSE;
}
- tzobj = zend_object_store_get_object(php_date_instantiate(date_ce_timezone, return_value TSRMLS_CC) TSRMLS_CC);
- tzobj->type = TIMELIB_ZONETYPE_ID;
- tzobj->tzi.tz = tzi;
- tzobj->initialized = 1;
}
/* }}} */
@@ -3673,18 +3670,13 @@ PHP_METHOD(DateTimeZone, __construct)
{
char *tz;
int tz_len;
- timelib_tzinfo *tzi = NULL;
php_timezone_obj *tzobj;
zend_error_handling error_handling;
zend_replace_error_handling(EH_THROW, NULL, &error_handling TSRMLS_CC);
if (SUCCESS == zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &tz, &tz_len)) {
- if (SUCCESS == timezone_initialize(&tzi, tz TSRMLS_CC)) {
- tzobj = zend_object_store_get_object(getThis() TSRMLS_CC);
- tzobj->type = TIMELIB_ZONETYPE_ID;
- tzobj->tzi.tz = tzi;
- tzobj->initialized = 1;
- } else {
+ tzobj = zend_object_store_get_object(getThis() TSRMLS_CC);
+ if (FAILURE == timezone_initialize(tzobj, tz TSRMLS_CC)) {
ZVAL_NULL(getThis());
}
}
@@ -3696,39 +3688,12 @@ static int php_date_timezone_initialize_from_hash(zval **return_value, php_timez
{
zval **z_timezone = NULL;
zval **z_timezone_type = NULL;
- timelib_tzinfo *tzi;
if (zend_hash_find(myht, "timezone_type", 14, (void**) &z_timezone_type) == SUCCESS) {
if (zend_hash_find(myht, "timezone", 9, (void**) &z_timezone) == SUCCESS) {
convert_to_long(*z_timezone_type);
- switch (Z_LVAL_PP(z_timezone_type)) {
- case TIMELIB_ZONETYPE_OFFSET: {
- char *offset, *offset_start;
-
- offset = emalloc(sizeof(char) * (Z_STRLEN_PP(z_timezone) + 1));
- memmove(offset, Z_STRVAL_PP(z_timezone), Z_STRLEN_PP(z_timezone)+1);
- offset_start = offset;
-
- ++offset;
- if(*offset_start == '+'){
- (*tzobj)->tzi.utc_offset = -1 * timelib_parse_tz_cor(&offset);
- } else {
- (*tzobj)->tzi.utc_offset = timelib_parse_tz_cor(&offset);
- }
- efree(offset_start);
- (*tzobj)->type = TIMELIB_ZONETYPE_OFFSET;
- (*tzobj)->initialized = 1;
- return SUCCESS;
- break;
- }
- case TIMELIB_ZONETYPE_ABBR:
- case TIMELIB_ZONETYPE_ID:
- if (SUCCESS == timezone_initialize(&tzi, Z_STRVAL_PP(z_timezone) TSRMLS_CC)) {
- (*tzobj)->type = TIMELIB_ZONETYPE_ID;
- (*tzobj)->tzi.tz = tzi;
- (*tzobj)->initialized = 1;
- return SUCCESS;
- }
+ if (SUCCESS == timezone_initialize(*tzobj, Z_STRVAL_PP(z_timezone) TSRMLS_CC)) {
+ return SUCCESS;
}
}
}
@@ -4387,7 +4352,7 @@ PHP_METHOD(DatePeriod, __construct)
zend_replace_error_handling(EH_THROW, NULL, &error_handling TSRMLS_CC);
if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, "OOl|l", &start, date_ce_interface, &interval, date_ce_interval, &recurrences, &options) == FAILURE) {
- if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, "OOO|l", &start, date_ce_interface, &interval, date_ce_interval, &end, date_ce_date, &options) == FAILURE) {
+ if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, "OOO|l", &start, date_ce_interface, &interval, date_ce_interval, &end, date_ce_interface, &options) == FAILURE) {
if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &isostr, &isostr_len, &options) == FAILURE) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "This constructor accepts either (DateTimeInterface, DateInterval, int) OR (DateTimeInterface, DateInterval, DateTime) OR (string) as arguments.");
zend_restore_error_handling(&error_handling TSRMLS_CC);
diff --git a/ext/date/php_date.h b/ext/date/php_date.h
index 536629a25f..d7343e02bc 100644
--- a/ext/date/php_date.h
+++ b/ext/date/php_date.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -137,14 +137,9 @@ struct _php_timezone_obj {
int initialized;
int type;
union {
- timelib_tzinfo *tz; /* TIMELIB_ZONETYPE_ID; */
- timelib_sll utc_offset; /* TIMELIB_ZONETYPE_OFFSET */
- struct /* TIMELIB_ZONETYPE_ABBR */
- {
- timelib_sll utc_offset;
- char *abbr;
- int dst;
- } z;
+ timelib_tzinfo *tz; /* TIMELIB_ZONETYPE_ID */
+ timelib_sll utc_offset; /* TIMELIB_ZONETYPE_OFFSET */
+ timelib_abbr_info z; /* TIMELIB_ZONETYPE_ABBR */
} tzi;
HashTable *props;
};
diff --git a/ext/date/tests/DateTimeZone_clone_basic1.phpt b/ext/date/tests/DateTimeZone_clone_basic1.phpt
index a89005aaec..49c190cf9f 100644
--- a/ext/date/tests/DateTimeZone_clone_basic1.phpt
+++ b/ext/date/tests/DateTimeZone_clone_basic1.phpt
@@ -31,15 +31,15 @@ if ($clone != $orig) {
*** Testing clone on DateTime objects ***
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(3) "UTC"
+ string(3) "GMT"
}
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(3) "UTC"
+ string(3) "GMT"
}
TEST PASSED : Objects equal but not indetical
===DONE===
diff --git a/ext/date/tests/DateTimeZone_construct_basic.phpt b/ext/date/tests/DateTimeZone_construct_basic.phpt
index 2f18f81c03..12b1090661 100644
--- a/ext/date/tests/DateTimeZone_construct_basic.phpt
+++ b/ext/date/tests/DateTimeZone_construct_basic.phpt
@@ -23,9 +23,9 @@ var_dump( new DateTimeZone("America/Los_Angeles") );
*** Testing new DateTimeZone() : basic functionality ***
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(3) "UTC"
+ string(3) "GMT"
}
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
diff --git a/ext/date/tests/DateTimeZone_construct_variation1.phpt b/ext/date/tests/DateTimeZone_construct_variation1.phpt
index 65e575ee44..025c6e2678 100644
--- a/ext/date/tests/DateTimeZone_construct_variation1.phpt
+++ b/ext/date/tests/DateTimeZone_construct_variation1.phpt
@@ -48,11 +48,9 @@ $inputs = array(
'int 0' => 0,
'int 1' => 1,
'int 12345' => 12345,
- 'int -12345' => -12345,
// float data
'float 10.5' => 10.5,
- 'float -10.5' => -10.5,
'float .5' => .5,
// array data
@@ -123,15 +121,9 @@ FAILED: DateTimeZone::__construct(): Unknown or bad timezone (1)
-- int 12345 --
FAILED: DateTimeZone::__construct(): Unknown or bad timezone (12345)
--- int -12345 --
-FAILED: DateTimeZone::__construct(): Unknown or bad timezone (-12345)
-
-- float 10.5 --
FAILED: DateTimeZone::__construct(): Unknown or bad timezone (10.5)
--- float -10.5 --
-FAILED: DateTimeZone::__construct(): Unknown or bad timezone (-10.5)
-
-- float .5 --
FAILED: DateTimeZone::__construct(): Unknown or bad timezone (0.5)
diff --git a/ext/date/tests/DateTimeZone_serialize_type_2.phpt b/ext/date/tests/DateTimeZone_serialize_type_2.phpt
index a264322f3e..4147efe927 100644
--- a/ext/date/tests/DateTimeZone_serialize_type_2.phpt
+++ b/ext/date/tests/DateTimeZone_serialize_type_2.phpt
@@ -20,16 +20,16 @@ var_dump( $tz2->getName() );
--EXPECTF--
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(16) "America/New_York"
+ string(3) "EST"
}
-string(88) "O:12:"DateTimeZone":2:{s:13:"timezone_type";i:3;s:8:"timezone";s:16:"America/New_York";}"
+string(74) "O:12:"DateTimeZone":2:{s:13:"timezone_type";i:2;s:8:"timezone";s:3:"EST";}"
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(16) "America/New_York"
+ string(3) "EST"
}
-string(16) "America/New_York"
+string(3) "EST"
===DONE===
diff --git a/ext/date/tests/DateTimeZone_serialize_type_3.phpt b/ext/date/tests/DateTimeZone_serialize_type_3.phpt
index 49b9349bb8..396bff9196 100644
--- a/ext/date/tests/DateTimeZone_serialize_type_3.phpt
+++ b/ext/date/tests/DateTimeZone_serialize_type_3.phpt
@@ -18,14 +18,14 @@ var_dump( $tz2->getName() );
?>
===DONE===
--EXPECTF--
-object(DateTimeZone)#%d (2) {
+object(DateTimeZone)#1 (2) {
["timezone_type"]=>
int(3)
["timezone"]=>
string(16) "America/New_York"
}
string(88) "O:12:"DateTimeZone":2:{s:13:"timezone_type";i:3;s:8:"timezone";s:16:"America/New_York";}"
-object(DateTimeZone)#%d (2) {
+object(DateTimeZone)#2 (2) {
["timezone_type"]=>
int(3)
["timezone"]=>
diff --git a/ext/date/tests/DateTime_format_basic2.phpt b/ext/date/tests/DateTime_format_basic2.phpt
index d7adaa5df8..016fa7b6b2 100644
--- a/ext/date/tests/DateTime_format_basic2.phpt
+++ b/ext/date/tests/DateTime_format_basic2.phpt
@@ -31,7 +31,7 @@ var_dump( $date->format( DateTime::W3C) ) ;
--EXPECT--
*** Testing date_format() : basic functionality - formatting coinstants ***
string(25) "2005-07-14T22:30:41+01:00"
-string(32) "Thursday, 14-Jul-05 22:30:41 BST"
+string(34) "Thursday, 14-Jul-2005 22:30:41 BST"
string(24) "2005-07-14T22:30:41+0100"
string(29) "Thu, 14 Jul 05 22:30:41 +0100"
string(32) "Thursday, 14-Jul-05 22:30:41 BST"
diff --git a/ext/date/tests/DateTime_verify.phpt b/ext/date/tests/DateTime_verify.phpt
index a03911f5c8..c790974729 100644
--- a/ext/date/tests/DateTime_verify.phpt
+++ b/ext/date/tests/DateTime_verify.phpt
@@ -160,7 +160,7 @@ array(11) {
["ATOM"]=>
string(13) "Y-m-d\TH:i:sP"
["COOKIE"]=>
- string(16) "l, d-M-y H:i:s T"
+ string(16) "l, d-M-Y H:i:s T"
["ISO8601"]=>
string(13) "Y-m-d\TH:i:sO"
["RFC822"]=>
@@ -180,4 +180,4 @@ array(11) {
["W3C"]=>
string(13) "Y-m-d\TH:i:sP"
}
-===DONE=== \ No newline at end of file
+===DONE===
diff --git a/ext/date/tests/bug44780.phpt b/ext/date/tests/bug44780.phpt
new file mode 100644
index 0000000000..5c822d48e6
--- /dev/null
+++ b/ext/date/tests/bug44780.phpt
@@ -0,0 +1,10 @@
+--TEST--
+Bug #44780 (some time zone offsets not recognized by timezone_name_from_abbr)
+--FILE--
+<?php
+var_dump( timezone_name_from_abbr("", 5.5*3600, false) );
+var_dump( timezone_name_from_abbr("", 28800, false) );
+?>
+--EXPECT--
+string(12) "Asia/Kolkata"
+string(13) "Asia/Shanghai"
diff --git a/ext/date/tests/bug45543.phpt b/ext/date/tests/bug45543.phpt
new file mode 100644
index 0000000000..8e36e6287c
--- /dev/null
+++ b/ext/date/tests/bug45543.phpt
@@ -0,0 +1,34 @@
+--TEST--
+Test for bug #45543: DateTime::setTimezone can not set timezones without ID.
+--INI--
+date.timezone=UTC
+--FILE--
+<?php
+$test_dates = array(
+ '2008-01-01 12:00:00 PDT',
+ '2008-01-01 12:00:00 +02:00',
+);
+
+foreach ($test_dates as $test_date)
+{
+ $d1 = new DateTime($test_date);
+ $d2 = new DateTime('2008-01-01 12:00:00 UTC');
+ echo $d1->format(DATE_ISO8601), PHP_EOL;
+ echo $d2->format(DATE_ISO8601), PHP_EOL;
+ $tz = $d1->getTimeZone();
+ $d2->setTimeZone($tz);
+ echo $d1->format(DATE_ISO8601), PHP_EOL;
+ echo $d2->format(DATE_ISO8601), PHP_EOL;
+ echo PHP_EOL;
+}
+--EXPECT--
+2008-01-01T12:00:00-0700
+2008-01-01T12:00:00+0000
+2008-01-01T12:00:00-0700
+2008-01-01T05:00:00-0700
+
+2008-01-01T12:00:00+0200
+2008-01-01T12:00:00+0000
+2008-01-01T12:00:00+0200
+2008-01-01T14:00:00+0200
+
diff --git a/ext/date/tests/bug52063.phpt b/ext/date/tests/bug52063.phpt
index af9da9e429..7364a80612 100644
--- a/ext/date/tests/bug52063.phpt
+++ b/ext/date/tests/bug52063.phpt
@@ -11,5 +11,5 @@ echo $a->format(DateTime::COOKIE);
echo "\n";
?>
--EXPECTF--
-Thursday, 01-Jan-09 00:00:00 WET
-Thursday, 01-Jan-09 00:00:00 WET
+Thursday, 01-Jan-2009 00:00:00 WET
+Thursday, 01-Jan-2009 00:00:00 WET
diff --git a/ext/date/tests/bug53879.phpt b/ext/date/tests/bug53879.phpt
new file mode 100644
index 0000000000..3d16c97209
--- /dev/null
+++ b/ext/date/tests/bug53879.phpt
@@ -0,0 +1,16 @@
+--TEST--
+Bug #53879 (DateTime::createFromFormat() fails to parse cookie expiration date)
+--INI--
+date.timezone=UTC
+--FILE--
+<?php
+$date = DateTime::createFromFormat(DateTime::COOKIE, "Mon, 21-Jan-2041 15:24:52 GMT");
+print_r($date);
+?>
+--EXPECTF--
+DateTime Object
+(
+ [date] => 2041-01-21 15:24:52
+ [timezone_type] => 2
+ [timezone] => GMT
+)
diff --git a/ext/date/tests/bug63391.phpt b/ext/date/tests/bug63391.phpt
new file mode 100644
index 0000000000..a29d25e730
--- /dev/null
+++ b/ext/date/tests/bug63391.phpt
@@ -0,0 +1,20 @@
+--TEST--
+Test for #63391 (Incorrect/inconsistent day of week prior to the year 1600)
+--FILE--
+<?php
+ini_set('date.timezone', 'UTC');
+
+print "Date PHP\n";
+print "---------- ---\n";
+$dates = array('1599-12-30', '1599-12-31', '1600-01-01', '1600-01-02');
+foreach ($dates as $date) {
+ echo date_create($date)->format('Y-m-d D'), "\n";
+}
+?>
+--EXPECT--
+Date PHP
+---------- ---
+1599-12-30 Thu
+1599-12-31 Fri
+1600-01-01 Sat
+1600-01-02 Sun
diff --git a/ext/date/tests/bug65371.phpt b/ext/date/tests/bug65371.phpt
new file mode 100644
index 0000000000..a6e3126514
--- /dev/null
+++ b/ext/date/tests/bug65371.phpt
@@ -0,0 +1,22 @@
+--TEST--
+Testing bug #65371
+--INI--
+date.timezone=Europe/Berlin
+--FILE--
+<?php
+
+function p($str)
+{
+ echo $str, "\n";
+ echo strftime($str), "\n";
+ echo bin2hex($str), "\n";
+ echo bin2hex(strftime($str));
+}
+
+setlocale(LC_ALL, 'C');
+p('ã‚');
+--EXPECT--
+ã‚
+ã‚
+e38182
+e38182
diff --git a/ext/date/tests/date_constants.phpt b/ext/date/tests/date_constants.phpt
index 132e24159b..b9fce8c78b 100644
--- a/ext/date/tests/date_constants.phpt
+++ b/ext/date/tests/date_constants.phpt
@@ -41,8 +41,8 @@ Date constants
--EXPECT--
string(25) "2006-07-01T14:27:30+02:00"
string(25) "2006-05-30T14:32:13+02:00"
-string(33) "Saturday, 01-Jul-06 14:27:30 CEST"
-string(32) "Tuesday, 30-May-06 14:32:13 CEST"
+string(35) "Saturday, 01-Jul-2006 14:27:30 CEST"
+string(34) "Tuesday, 30-May-2006 14:32:13 CEST"
string(24) "2006-07-01T14:27:30+0200"
string(24) "2006-05-30T14:32:13+0200"
string(29) "Sat, 01 Jul 06 14:27:30 +0200"
diff --git a/ext/date/tests/forward-transition-construction.phpt b/ext/date/tests/forward-transition-construction.phpt
new file mode 100644
index 0000000000..8f195a51bd
--- /dev/null
+++ b/ext/date/tests/forward-transition-construction.phpt
@@ -0,0 +1,27 @@
+--TEST--
+Test for Date/Time construction during a forward DST transition
+--FILE--
+<?php
+date_default_timezone_set('America/New_York');
+
+$date = new DateTime('2010-03-14 01:30:00');
+echo $date->format('Y-m-d H:i:s T/e - U') . "\n";
+
+$date = new DateTime('2010-03-14 02:00:00');
+echo $date->format('Y-m-d H:i:s T/e - U') . "\n";
+
+$date = new DateTime('2010-03-14 02:30:00');
+echo $date->format('Y-m-d H:i:s T/e - U') . "\n";
+
+$date = new DateTime('2010-03-14 03:00:00');
+echo $date->format('Y-m-d H:i:s T/e - U') . "\n";
+
+$date = new DateTime('2010-03-14 03:30:00');
+echo $date->format('Y-m-d H:i:s T/e - U') . "\n";
+?>
+--EXPECT--
+2010-03-14 01:30:00 EST/America/New_York - 1268548200
+2010-03-14 03:00:00 EDT/America/New_York - 1268550000
+2010-03-14 03:30:00 EDT/America/New_York - 1268551800
+2010-03-14 03:00:00 EDT/America/New_York - 1268550000
+2010-03-14 03:30:00 EDT/America/New_York - 1268551800
diff --git a/ext/date/tests/gmdate_variation13.phpt b/ext/date/tests/gmdate_variation13.phpt
index 5a19ae268e..1d1f434ece 100644
--- a/ext/date/tests/gmdate_variation13.phpt
+++ b/ext/date/tests/gmdate_variation13.phpt
@@ -45,7 +45,7 @@ string(25) "2008-08-08T08:08:08+00:00"
string(%d) "%s"
--DATE_COOKIE Constant--
-string(30) "Friday, 08-Aug-08 08:08:08 GMT"
+string(32) "Friday, 08-Aug-2008 08:08:08 GMT"
string(%d) "%s"
--DATE_RFC822 Constant--
@@ -79,4 +79,4 @@ string(%d) "%s"
--DATE_W3C Constant--
string(25) "2008-08-08T08:08:08+00:00"
string(%d) "%s"
-===DONE=== \ No newline at end of file
+===DONE===
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-ba.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-ba.phpt
new file mode 100644
index 0000000000..fdbe96d7d0
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-ba.phpt
@@ -0,0 +1,96 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, ba)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Backward Transitions, add().
+ */
+
+$start = new DateTime('2010-11-07 01:59:59');
+$interval_spec = 'PT1S';
+$interval = new DateInterval($interval_spec);
+echo 'ba1 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'ba2 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'PT24H';
+$interval = new DateInterval($interval_spec);
+echo 'ba3 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'PT23H';
+$interval = new DateInterval($interval_spec);
+echo 'ba4 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'PT22H';
+$interval = new DateInterval($interval_spec);
+echo 'ba5 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'PT21H';
+$interval = new DateInterval($interval_spec);
+echo 'ba6 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 01:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'ba7 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 01:30:00');
+$interval_spec = 'P1DT1H';
+$interval = new DateInterval($interval_spec);
+echo 'ba8 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 04:30:00');
+$interval_spec = 'PT25H';
+$interval = new DateInterval($interval_spec);
+echo 'ba9 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 03:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'ba10 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-11-06 02:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'ba11 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+echo "\n";
+
+?>
+--EXPECT--
+ba1 2010-11-07 01:59:59 EDT America/New_York + PT1S = 2010-11-07 01:00:00 EST America/New_York
+ba2 2010-11-06 04:30:00 EDT America/New_York + P1D = 2010-11-07 04:30:00 EST America/New_York
+ba3 2010-11-06 04:30:00 EDT America/New_York + PT24H = 2010-11-07 03:30:00 EST America/New_York
+ba4 2010-11-06 04:30:00 EDT America/New_York + PT23H = 2010-11-07 02:30:00 EST America/New_York
+ba5 2010-11-06 04:30:00 EDT America/New_York + PT22H = 2010-11-07 01:30:00 EST America/New_York
+ba6 2010-11-06 04:30:00 EDT America/New_York + PT21H = 2010-11-07 01:30:00 EDT America/New_York
+ba7 2010-11-06 01:30:00 EDT America/New_York + P1D = 2010-11-07 01:30:00 EDT America/New_York
+ba8 2010-11-06 01:30:00 EDT America/New_York + P1DT1H = 2010-11-07 02:30:00 EST America/New_York
+ba9 2010-11-06 04:30:00 EDT America/New_York + PT25H = 2010-11-07 04:30:00 EST America/New_York
+ba10 2010-11-06 03:30:00 EDT America/New_York + P1D = 2010-11-07 03:30:00 EST America/New_York
+ba11 2010-11-06 02:30:00 EDT America/New_York + P1D = 2010-11-07 02:30:00 EST America/New_York
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd1.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd1.phpt
new file mode 100644
index 0000000000..8249599931
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd1.phpt
@@ -0,0 +1,48 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, bd1)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Backward Transitions, diff().
+ */
+
+$end = new DateTime('2010-11-07 05:30:00');
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd1 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 04:30:00');
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd2 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 03:30:00');
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd3 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 02:30:00');
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd4 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00');
+$start = new DateTime('2010-11-06 01:30:00');
+echo 'bd7 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+echo "\n";
+?>
+--EXPECT--
+bd1 2010-11-07 05:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P1DT1H
+bd2 2010-11-07 04:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P1DT0H
+bd3 2010-11-07 03:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT24H
+bd4 2010-11-07 02:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT23H
+bd7 2010-11-07 01:30:00 EDT America/New_York - 2010-11-06 01:30:00 EDT America/New_York = P1DT0H
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd2.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd2.phpt
new file mode 100644
index 0000000000..fe2e79b3b9
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bd2.phpt
@@ -0,0 +1,56 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, bd2)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--XFAIL--
+Still not quite right
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * For backward transitions, must create objects with zone type 2
+ * where specifying Daylight or Standard time is required
+ * then converting them to zone type 3.
+ */
+
+$tz = new DateTimeZone('America/New_York');
+
+/*
+ * Backward Transitions, diff().
+ */
+
+$end = new DateTime('2010-11-07 05:30:00');
+$end->setTimeZone($tz);
+$start = new DateTime('2010-11-06 04:30:59');
+echo 'bd0 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format('P%dDT%hH%iM%sS') . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EST');
+$end->setTimeZone($tz);
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd5 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EDT');
+$end->setTimeZone($tz);
+$start = new DateTime('2010-11-06 04:30:00');
+echo 'bd6 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EST');
+$end->setTimeZone($tz);
+$start = new DateTime('2010-11-06 01:30:00');
+echo 'bd8 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+echo "\n";
+?>
+--EXPECT--
+bd0 2010-11-07 01:00:00 EST America/New_York - 2010-11-07 01:59:59 EDT America/New_York = PT0H0M1S
+bd5 2010-11-07 01:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT22H
+bd6 2010-11-07 01:30:00 EDT America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT21H
+bd8 2010-11-07 01:30:00 EST America/New_York - 2010-11-06 01:30:00 EDT America/New_York = P1DT1H
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bs.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bs.phpt
new file mode 100644
index 0000000000..138c68f3a9
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-bs.phpt
@@ -0,0 +1,92 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, bs)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$tz = new DateTimeZone('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Backward Transitions, sub().
+ */
+
+$end = new DateTime('2010-11-07 01:00:00 EST');
+$end->setTimeZone($tz);
+$interval_spec = 'PT1S';
+$interval = new DateInterval($interval_spec);
+echo 'bs1 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 04:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'bs2 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 03:30:00');
+$interval_spec = 'PT24H';
+$interval = new DateInterval($interval_spec);
+echo 'bs3 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 02:30:00');
+$interval_spec = 'PT23H';
+$interval = new DateInterval($interval_spec);
+echo 'bs4 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EST');
+$end->setTimeZone($tz);
+$interval_spec = 'PT22H';
+$interval = new DateInterval($interval_spec);
+echo 'bs5 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EDT');
+$end->setTimeZone($tz);
+$interval_spec = 'PT21H';
+$interval = new DateInterval($interval_spec);
+echo 'bs6 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'bs7 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 01:30:00 EST');
+$end->setTimeZone($tz);
+$interval_spec = 'P1DT1H';
+$interval = new DateInterval($interval_spec);
+echo 'bs8 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 03:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'bs9 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-11-07 02:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'bs10 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+?>
+--EXPECT--
+bs1 2010-11-07 01:00:00 EST America/New_York - PT1S = 2010-11-07 01:59:59 EDT America/New_York
+bs2 2010-11-07 04:30:00 EST America/New_York - P1D = 2010-11-06 04:30:00 EDT America/New_York
+bs3 2010-11-07 03:30:00 EST America/New_York - PT24H = 2010-11-06 04:30:00 EDT America/New_York
+bs4 2010-11-07 02:30:00 EST America/New_York - PT23H = 2010-11-06 04:30:00 EDT America/New_York
+bs5 2010-11-07 01:30:00 EST America/New_York - PT22H = 2010-11-06 04:30:00 EDT America/New_York
+bs6 2010-11-07 01:30:00 EDT America/New_York - PT21H = 2010-11-06 04:30:00 EDT America/New_York
+bs7 2010-11-07 01:30:00 EDT America/New_York - P1D = 2010-11-06 01:30:00 EDT America/New_York
+bs8 2010-11-07 01:30:00 EST America/New_York - P1DT1H = 2010-11-06 00:30:00 EDT America/New_York
+bs9 2010-11-07 03:30:00 EST America/New_York - P1D = 2010-11-06 03:30:00 EDT America/New_York
+bs10 2010-11-07 02:30:00 EST America/New_York - P1D = 2010-11-06 02:30:00 EDT America/New_York
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fa.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fa.phpt
new file mode 100644
index 0000000000..9fa493f578
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fa.phpt
@@ -0,0 +1,58 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, fa)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Forward Transitions, add().
+ */
+
+$start = new DateTime('2010-03-14 01:59:59');
+$interval_spec = 'PT1S';
+$interval = new DateInterval($interval_spec);
+echo 'fa1 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-03-13 04:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fa2 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-03-13 04:30:00');
+$interval_spec = 'PT22H';
+$interval = new DateInterval($interval_spec);
+echo 'fa3 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-03-13 04:30:00');
+$interval_spec = 'PT21H';
+$interval = new DateInterval($interval_spec);
+echo 'fa4 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-03-13 01:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fa5 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+
+$start = new DateTime('2010-03-13 02:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fa6 ' . $start->format($date_format) . " + $interval_spec = "
+ . $start->add($interval)->format($date_format) . "\n";
+?>
+--EXPECT--
+fa1 2010-03-14 01:59:59 EST America/New_York + PT1S = 2010-03-14 03:00:00 EDT America/New_York
+fa2 2010-03-13 04:30:00 EST America/New_York + P1D = 2010-03-14 04:30:00 EDT America/New_York
+fa3 2010-03-13 04:30:00 EST America/New_York + PT22H = 2010-03-14 03:30:00 EDT America/New_York
+fa4 2010-03-13 04:30:00 EST America/New_York + PT21H = 2010-03-14 01:30:00 EST America/New_York
+fa5 2010-03-13 01:30:00 EST America/New_York + P1D = 2010-03-14 01:30:00 EST America/New_York
+fa6 2010-03-13 02:30:00 EST America/New_York + P1D = 2010-03-14 03:30:00 EDT America/New_York
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fd.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fd.phpt
new file mode 100644
index 0000000000..ae7060be0b
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fd.phpt
@@ -0,0 +1,58 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, fd)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Forward Transitions, diff().
+ */
+
+$end = new DateTime('2010-03-14 03:00:00');
+$start = new DateTime('2010-03-14 01:59:59');
+echo 'fd1 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format('PT%hH%iM%sS') . "\n";
+
+$end = new DateTime('2010-03-14 04:30:00');
+$start = new DateTime('2010-03-13 04:30:00');
+echo 'fd2 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-03-14 03:30:00');
+$start = new DateTime('2010-03-13 04:30:00');
+echo 'fd3 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-03-14 01:30:00');
+$start = new DateTime('2010-03-13 04:30:00');
+echo 'fd4 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-03-14 01:30:00');
+$start = new DateTime('2010-03-13 01:30:00');
+echo 'fd5 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-03-14 03:30:00');
+$start = new DateTime('2010-03-13 03:30:00');
+echo 'fd6 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+
+$end = new DateTime('2010-03-14 03:30:00');
+$start = new DateTime('2010-03-13 02:30:00');
+echo 'fd7 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
+ . ' = ' . $start->diff($end)->format($interval_format) . "\n";
+?>
+--EXPECT--
+fd1 2010-03-14 03:00:00 EDT America/New_York - 2010-03-14 01:59:59 EST America/New_York = PT0H0M1S
+fd2 2010-03-14 04:30:00 EDT America/New_York - 2010-03-13 04:30:00 EST America/New_York = P1DT0H
+fd3 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 04:30:00 EST America/New_York = P0DT22H
+fd4 2010-03-14 01:30:00 EST America/New_York - 2010-03-13 04:30:00 EST America/New_York = P0DT21H
+fd5 2010-03-14 01:30:00 EST America/New_York - 2010-03-13 01:30:00 EST America/New_York = P1DT0H
+fd6 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 03:30:00 EST America/New_York = P1DT0H
+fd7 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 02:30:00 EST America/New_York = P1DT1H
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fs.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fs.phpt
new file mode 100644
index 0000000000..72351d37e1
--- /dev/null
+++ b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3-fs.phpt
@@ -0,0 +1,67 @@
+--TEST--
+RFC: DateTime and Daylight Saving Time Transitions (zone type 3, fs)
+--CREDITS--
+Daniel Convissor <danielc@php.net>
+--XFAIL--
+Still not quite right
+--FILE--
+<?php
+
+date_default_timezone_set('America/New_York');
+$date_format = 'Y-m-d H:i:s T e';
+$interval_format = 'P%dDT%hH';
+
+/*
+ * Forward Transitions, sub().
+ */
+
+$end = new DateTime('2010-03-14 03:00:00');
+$interval_spec = 'PT1S';
+$interval = new DateInterval($interval_spec);
+echo 'fs1 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-14 04:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fs2 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-14 03:30:00');
+$interval_spec = 'PT22H';
+$interval = new DateInterval($interval_spec);
+echo 'fs3 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-14 01:30:00');
+$interval_spec = 'PT21H';
+$interval = new DateInterval($interval_spec);
+echo 'fs4 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-14 01:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fs5 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-15 03:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fs6 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+
+$end = new DateTime('2010-03-15 02:30:00');
+$interval_spec = 'P1D';
+$interval = new DateInterval($interval_spec);
+echo 'fs7 ' . $end->format($date_format) . " - $interval_spec = "
+ . $end->sub($interval)->format($date_format) . "\n";
+?>
+--EXPECT--
+fs1 2010-03-14 03:00:00 EDT America/New_York - PT1S = 2010-03-14 01:59:59 EST America/New_York
+fs2 2010-03-14 04:30:00 EDT America/New_York - P1D = 2010-03-13 04:30:00 EST America/New_York
+fs3 2010-03-14 03:30:00 EDT America/New_York - PT22H = 2010-03-13 04:30:00 EST America/New_York
+fs4 2010-03-14 01:30:00 EST America/New_York - PT21H = 2010-03-13 04:30:00 EST America/New_York
+fs5 2010-03-14 01:30:00 EST America/New_York - P1D = 2010-03-13 01:30:00 EST America/New_York
+fs6 2010-03-15 03:30:00 EDT America/New_York - P1D = 2010-03-14 03:30:00 EDT America/New_York
+fs7 2010-03-15 02:30:00 EDT America/New_York - P1D = 2010-03-14 03:30:00 EDT America/New_York
diff --git a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3.phpt b/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3.phpt
deleted file mode 100644
index 855fe4ef65..0000000000
--- a/ext/date/tests/rfc-datetime_and_daylight_saving_time-type3.phpt
+++ /dev/null
@@ -1,399 +0,0 @@
---TEST--
-RFC: DateTime and Daylight Saving Time Transitions (zone type 3)
---CREDITS--
-Daniel Convissor <danielc@php.net>
---XFAIL--
-RFC not implemented yet
---FILE--
-<?php
-
-date_default_timezone_set('America/New_York');
-$date_format = 'Y-m-d H:i:s T e';
-$interval_format = 'P%dDT%hH';
-
-/*
- * Forward Transitions, diff().
- */
-
-$end = new DateTime('2010-03-14 03:00:00');
-$start = new DateTime('2010-03-14 01:59:59');
-echo 'fd1 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format('PT%hH%iM%sS') . "\n";
-
-$end = new DateTime('2010-03-14 04:30:00');
-$start = new DateTime('2010-03-13 04:30:00');
-echo 'fd2 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-03-14 03:30:00');
-$start = new DateTime('2010-03-13 04:30:00');
-echo 'fd3 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-03-14 01:30:00');
-$start = new DateTime('2010-03-13 04:30:00');
-echo 'fd4 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-03-14 01:30:00');
-$start = new DateTime('2010-03-13 01:30:00');
-echo 'fd5 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-03-14 03:30:00');
-$start = new DateTime('2010-03-13 03:30:00');
-echo 'fd6 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-03-14 03:30:00');
-$start = new DateTime('2010-03-13 02:30:00');
-echo 'fd7 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-echo "\n";
-
-/*
- * Forward Transitions, add().
- */
-
-$start = new DateTime('2010-03-14 01:59:59');
-$interval_spec = 'PT1S';
-$interval = new DateInterval($interval_spec);
-echo 'fa1 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-03-13 04:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fa2 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-03-13 04:30:00');
-$interval_spec = 'PT22H';
-$interval = new DateInterval($interval_spec);
-echo 'fa3 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-03-13 04:30:00');
-$interval_spec = 'PT21H';
-$interval = new DateInterval($interval_spec);
-echo 'fa4 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-03-13 01:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fa5 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-03-13 02:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fa6 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-echo "\n";
-
-/*
- * Forward Transitions, sub().
- */
-
-$end = new DateTime('2010-03-14 03:00:00');
-$interval_spec = 'PT1S';
-$interval = new DateInterval($interval_spec);
-echo 'fs1 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-14 04:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fs2 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-14 03:30:00');
-$interval_spec = 'PT22H';
-$interval = new DateInterval($interval_spec);
-echo 'fs3 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-14 01:30:00');
-$interval_spec = 'PT21H';
-$interval = new DateInterval($interval_spec);
-echo 'fs4 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-14 01:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fs5 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-15 03:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fs6 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-03-15 02:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'fs7 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-echo "\n";
-
-
-/*
- * For backward transitions, must create objects with zone type 2
- * where specifying Daylight or Standard time is required
- * then converting them to zone type 3.
- */
-
-$tz = new DateTimeZone('America/New_York');
-
-/*
- * Backward Transitions, diff().
- */
-
-$end = new DateTime('2010-11-07 01:00:00 EST');
-$end->setTimeZone($tz);
-$start = new DateTime('2010-11-07 01:59:59');
-echo 'bd1 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format('PT%hH%iM%sS') . "\n";
-
-$end = new DateTime('2010-11-07 04:30:00');
-$start = new DateTime('2010-11-06 04:30:00');
-echo 'bd2 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 03:30:00');
-$start = new DateTime('2010-11-06 04:30:00');
-echo 'bd3 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 02:30:00');
-$start = new DateTime('2010-11-06 04:30:00');
-echo 'bd4 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EST');
-$end->setTimeZone($tz);
-$start = new DateTime('2010-11-06 04:30:00');
-echo 'bd5 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EDT');
-$end->setTimeZone($tz);
-$start = new DateTime('2010-11-06 04:30:00');
-echo 'bd6 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00');
-$start = new DateTime('2010-11-06 01:30:00');
-echo 'bd7 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EST');
-$end->setTimeZone($tz);
-$start = new DateTime('2010-11-06 01:30:00');
-echo 'bd8 ' . $end->format($date_format) . ' - ' . $start->format($date_format)
- . ' = ' . $start->diff($end)->format($interval_format) . "\n";
-
-echo "\n";
-
-/*
- * Backward Transitions, add().
- */
-
-$start = new DateTime('2010-11-07 01:59:59');
-$interval_spec = 'PT1S';
-$interval = new DateInterval($interval_spec);
-echo 'ba1 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'ba2 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'PT24H';
-$interval = new DateInterval($interval_spec);
-echo 'ba3 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'PT23H';
-$interval = new DateInterval($interval_spec);
-echo 'ba4 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'PT22H';
-$interval = new DateInterval($interval_spec);
-echo 'ba5 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'PT21H';
-$interval = new DateInterval($interval_spec);
-echo 'ba6 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 01:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'ba7 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 01:30:00');
-$interval_spec = 'P1DT1H';
-$interval = new DateInterval($interval_spec);
-echo 'ba8 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 04:30:00');
-$interval_spec = 'PT25H';
-$interval = new DateInterval($interval_spec);
-echo 'ba9 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 03:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'ba10 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-$start = new DateTime('2010-11-06 02:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'ba11 ' . $start->format($date_format) . " + $interval_spec = "
- . $start->add($interval)->format($date_format) . "\n";
-
-echo "\n";
-
-/*
- * Backward Transitions, sub().
- */
-
-$end = new DateTime('2010-11-07 01:00:00 EST');
-$end->setTimeZone($tz);
-$interval_spec = 'PT1S';
-$interval = new DateInterval($interval_spec);
-echo 'bs1 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 04:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'bs2 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 03:30:00');
-$interval_spec = 'PT24H';
-$interval = new DateInterval($interval_spec);
-echo 'bs3 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 02:30:00');
-$interval_spec = 'PT23H';
-$interval = new DateInterval($interval_spec);
-echo 'bs4 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EST');
-$end->setTimeZone($tz);
-$interval_spec = 'PT22H';
-$interval = new DateInterval($interval_spec);
-echo 'bs5 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EDT');
-$end->setTimeZone($tz);
-$interval_spec = 'PT21H';
-$interval = new DateInterval($interval_spec);
-echo 'bs6 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'bs7 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 01:30:00 EST');
-$end->setTimeZone($tz);
-$interval_spec = 'P1DT1H';
-$interval = new DateInterval($interval_spec);
-echo 'bs8 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 03:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'bs9 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-$end = new DateTime('2010-11-07 02:30:00');
-$interval_spec = 'P1D';
-$interval = new DateInterval($interval_spec);
-echo 'bs10 ' . $end->format($date_format) . " - $interval_spec = "
- . $end->sub($interval)->format($date_format) . "\n";
-
-?>
---EXPECT--
-fd1 2010-03-14 03:00:00 EDT America/New_York - 2010-03-14 01:59:59 EST America/New_York = PT0H0M1S
-fd2 2010-03-14 04:30:00 EDT America/New_York - 2010-03-13 04:30:00 EST America/New_York = P1DT0H
-fd3 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 04:30:00 EST America/New_York = P0DT22H
-fd4 2010-03-14 01:30:00 EST America/New_York - 2010-03-13 04:30:00 EST America/New_York = P0DT21H
-fd5 2010-03-14 01:30:00 EST America/New_York - 2010-03-13 01:30:00 EST America/New_York = P1DT0H
-fd6 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 03:30:00 EST America/New_York = P1DT0H
-fd7 2010-03-14 03:30:00 EDT America/New_York - 2010-03-13 02:30:00 EST America/New_York = P1DT1H
-
-fa1 2010-03-14 01:59:59 EST America/New_York + PT1S = 2010-03-14 03:00:00 EDT America/New_York
-fa2 2010-03-13 04:30:00 EST America/New_York + P1D = 2010-03-14 04:30:00 EDT America/New_York
-fa3 2010-03-13 04:30:00 EST America/New_York + PT22H = 2010-03-14 03:30:00 EDT America/New_York
-fa4 2010-03-13 04:30:00 EST America/New_York + PT21H = 2010-03-14 01:30:00 EST America/New_York
-fa5 2010-03-13 01:30:00 EST America/New_York + P1D = 2010-03-14 01:30:00 EST America/New_York
-fa6 2010-03-13 02:30:00 EST America/New_York + P1D = 2010-03-14 03:30:00 EDT America/New_York
-
-fs1 2010-03-14 03:00:00 EDT America/New_York - PT1S = 2010-03-14 01:59:59 EST America/New_York
-fs2 2010-03-14 04:30:00 EDT America/New_York - P1D = 2010-03-13 04:30:00 EST America/New_York
-fs3 2010-03-14 03:30:00 EDT America/New_York - PT22H = 2010-03-13 04:30:00 EST America/New_York
-fs4 2010-03-14 01:30:00 EST America/New_York - PT21H = 2010-03-13 04:30:00 EST America/New_York
-fs5 2010-03-14 01:30:00 EST America/New_York - P1D = 2010-03-13 01:30:00 EST America/New_York
-fs6 2010-03-15 03:30:00 EDT America/New_York - P1D = 2010-03-14 03:30:00 EDT America/New_York
-fs7 2010-03-15 03:30:00 EDT America/New_York - P1D = 2010-03-14 03:30:00 EDT America/New_York
-
-bd1 2010-11-07 01:00:00 EST America/New_York - 2010-11-07 01:59:59 EDT America/New_York = PT0H0M1S
-bd2 2010-11-07 04:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P1DT0H
-bd3 2010-11-07 03:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT24H
-bd4 2010-11-07 02:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT23H
-bd5 2010-11-07 01:30:00 EST America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT22H
-bd6 2010-11-07 01:30:00 EDT America/New_York - 2010-11-06 04:30:00 EDT America/New_York = P0DT21H
-bd7 2010-11-07 01:30:00 EDT America/New_York - 2010-11-06 01:30:00 EDT America/New_York = P1DT0H
-bd8 2010-11-07 01:30:00 EST America/New_York - 2010-11-06 01:30:00 EDT America/New_York = P1DT1H
-
-ba1 2010-11-07 01:59:59 EDT America/New_York + PT1S = 2010-11-07 01:00:00 EST America/New_York
-ba2 2010-11-06 04:30:00 EDT America/New_York + P1D = 2010-11-07 04:30:00 EST America/New_York
-ba3 2010-11-06 04:30:00 EDT America/New_York + PT24H = 2010-11-07 03:30:00 EST America/New_York
-ba4 2010-11-06 04:30:00 EDT America/New_York + PT23H = 2010-11-07 02:30:00 EST America/New_York
-ba5 2010-11-06 04:30:00 EDT America/New_York + PT22H = 2010-11-07 01:30:00 EST America/New_York
-ba6 2010-11-06 04:30:00 EDT America/New_York + PT21H = 2010-11-07 01:30:00 EDT America/New_York
-ba7 2010-11-06 01:30:00 EDT America/New_York + P1D = 2010-11-07 01:30:00 EDT America/New_York
-ba8 2010-11-06 01:30:00 EDT America/New_York + P1DT1H = 2010-11-07 01:30:00 EST America/New_York
-ba9 2010-11-06 04:30:00 EDT America/New_York + PT25H = 2010-11-07 04:30:00 EST America/New_York
-ba10 2010-11-06 03:30:00 EDT America/New_York + P1D = 2010-11-07 03:30:00 EST America/New_York
-ba11 2010-11-06 02:30:00 EDT America/New_York + P1D = 2010-11-07 02:30:00 EST America/New_York
-
-bs1 2010-11-07 01:00:00 EST America/New_York - PT1S = 2010-11-07 01:59:59 EDT America/New_York
-bs2 2010-11-07 04:30:00 EST America/New_York - P1D = 2010-11-06 04:30:00 EDT America/New_York
-bs3 2010-11-07 03:30:00 EST America/New_York - PT24H = 2010-11-06 04:30:00 EDT America/New_York
-bs4 2010-11-07 02:30:00 EST America/New_York - PT23H = 2010-11-06 04:30:00 EDT America/New_York
-bs5 2010-11-07 01:30:00 EST America/New_York - PT22H = 2010-11-06 04:30:00 EDT America/New_York
-bs6 2010-11-07 01:30:00 EDT America/New_York - PT21H = 2010-11-06 04:30:00 EDT America/New_York
-bs7 2010-11-07 01:30:00 EDT America/New_York - P1D = 2010-11-06 01:30:00 EDT America/New_York
-bs8 2010-11-07 01:30:00 EST America/New_York - P1DT1H = 2010-11-06 00:30:00 EDT America/New_York
-bs9 2010-11-07 03:30:00 EST America/New_York - P1D = 2010-11-06 03:30:00 EDT America/New_York
-bs10 2010-11-07 02:30:00 EST America/New_York - P1D = 2010-11-06 02:30:00 EDT America/New_York
diff --git a/ext/date/tests/strtotime3-64bit.phpt b/ext/date/tests/strtotime3-64bit.phpt
index 7dc0816359..3a47659f86 100644
--- a/ext/date/tests/strtotime3-64bit.phpt
+++ b/ext/date/tests/strtotime3-64bit.phpt
@@ -53,7 +53,7 @@ bool(false)
string(31) "Fri, 16 Jun 2006 23:49:12 +0100"
bool(false)
string(31) "Fri, 16 Jun 2006 02:22:00 +0100"
-string(31) "Mon, 16 Jun 0222 02:22:00 -0036"
+string(31) "Sun, 16 Jun 0222 02:22:00 -0036"
string(31) "Fri, 16 Jun 2006 02:22:33 +0100"
bool(false)
string(31) "Tue, 02 Mar 2004 00:00:00 +0000"
diff --git a/ext/date/tests/test-parse-from-format.phpt b/ext/date/tests/test-parse-from-format.phpt
index 2bf9c4e1b8..5bb5fe5325 100644
--- a/ext/date/tests/test-parse-from-format.phpt
+++ b/ext/date/tests/test-parse-from-format.phpt
@@ -32,8 +32,8 @@ object(DateTime)#2 (3) {
string(6) "+02:00"
}
-string(16) "l, d-M-y H:i:s T"
-string(36) "Tuesday, 08-Jul-08 22:14:12 GMT+0200"
+string(16) "l, d-M-Y H:i:s T"
+string(38) "Tuesday, 08-Jul-2008 22:14:12 GMT+0200"
object(DateTime)#1 (3) {
["date"]=>
string(19) "2008-07-08 22:14:12"
diff --git a/ext/date/tests/timezone_open_basic1.phpt b/ext/date/tests/timezone_open_basic1.phpt
index 7fcfcb34cb..abd016b35a 100644
--- a/ext/date/tests/timezone_open_basic1.phpt
+++ b/ext/date/tests/timezone_open_basic1.phpt
@@ -20,9 +20,9 @@ var_dump( timezone_open("America/Los_Angeles") );
*** Testing timezone_open() : basic functionality ***
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
- int(3)
+ int(2)
["timezone"]=>
- string(3) "UTC"
+ string(3) "GMT"
}
object(DateTimeZone)#%d (2) {
["timezone_type"]=>
@@ -36,4 +36,4 @@ object(DateTimeZone)#%d (2) {
["timezone"]=>
string(19) "America/Los_Angeles"
}
-===DONE=== \ No newline at end of file
+===DONE===
diff --git a/ext/date/tests/timezone_open_variation1.phpt b/ext/date/tests/timezone_open_variation1.phpt
index 9a069f6472..eb4d4b782e 100644
--- a/ext/date/tests/timezone_open_variation1.phpt
+++ b/ext/date/tests/timezone_open_variation1.phpt
@@ -48,11 +48,9 @@ $inputs = array(
'int 0' => 0,
'int 1' => 1,
'int 12345' => 12345,
- 'int -12345' => -12345,
// float data
'float 10.5' => 10.5,
- 'float -10.5' => -10.5,
'float .5' => .5,
// array data
@@ -124,21 +122,11 @@ bool(false)
Warning: timezone_open(): Unknown or bad timezone (12345) in %s on line %d
bool(false)
--- int -12345 --
-
-Warning: timezone_open(): Unknown or bad timezone (-12345) in %s on line %d
-bool(false)
-
-- float 10.5 --
Warning: timezone_open(): Unknown or bad timezone (10.5) in %s on line %d
bool(false)
--- float -10.5 --
-
-Warning: timezone_open(): Unknown or bad timezone (-10.5) in %s on line %d
-bool(false)
-
-- float .5 --
Warning: timezone_open(): Unknown or bad timezone (0.5) in %s on line %d
diff --git a/ext/dba/dba.c b/ext/dba/dba.c
index ced90f0c62..9df7f34001 100644
--- a/ext/dba/dba.c
+++ b/ext/dba/dba.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_cdb.c b/ext/dba/dba_cdb.c
index a4a7314e8a..075aedb0c1 100644
--- a/ext/dba/dba_cdb.c
+++ b/ext/dba/dba_cdb.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_db1.c b/ext/dba/dba_db1.c
index fbb24d27bb..a8221b9562 100644
--- a/ext/dba/dba_db1.c
+++ b/ext/dba/dba_db1.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_db2.c b/ext/dba/dba_db2.c
index d92613a25b..b6879ca730 100644
--- a/ext/dba/dba_db2.c
+++ b/ext/dba/dba_db2.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_db3.c b/ext/dba/dba_db3.c
index b236865bd0..e248be8e28 100644
--- a/ext/dba/dba_db3.c
+++ b/ext/dba/dba_db3.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_db4.c b/ext/dba/dba_db4.c
index 8987f1a4be..7f9dfed7ab 100644
--- a/ext/dba/dba_db4.c
+++ b/ext/dba/dba_db4.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_dbm.c b/ext/dba/dba_dbm.c
index 2f3b800a31..c18c04f77e 100644
--- a/ext/dba/dba_dbm.c
+++ b/ext/dba/dba_dbm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_flatfile.c b/ext/dba/dba_flatfile.c
index 34aa635a54..ee8eefa652 100644
--- a/ext/dba/dba_flatfile.c
+++ b/ext/dba/dba_flatfile.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_gdbm.c b/ext/dba/dba_gdbm.c
index 47dd576496..345687fcf7 100644
--- a/ext/dba/dba_gdbm.c
+++ b/ext/dba/dba_gdbm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_inifile.c b/ext/dba/dba_inifile.c
index 05ee95c0ec..4d8eae73ac 100644
--- a/ext/dba/dba_inifile.c
+++ b/ext/dba/dba_inifile.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_ndbm.c b/ext/dba/dba_ndbm.c
index 8b5bbda851..bad6385708 100644
--- a/ext/dba/dba_ndbm.c
+++ b/ext/dba/dba_ndbm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_qdbm.c b/ext/dba/dba_qdbm.c
index eeece57011..a32b7e9e97 100644
--- a/ext/dba/dba_qdbm.c
+++ b/ext/dba/dba_qdbm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/dba_tcadb.c b/ext/dba/dba_tcadb.c
index 082a1ae250..341e99fed6 100644
--- a/ext/dba/dba_tcadb.c
+++ b/ext/dba/dba_tcadb.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/cdb.c b/ext/dba/libcdb/cdb.c
index bc4ee08831..d8c58372ba 100644
--- a/ext/dba/libcdb/cdb.c
+++ b/ext/dba/libcdb/cdb.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/cdb.h b/ext/dba/libcdb/cdb.h
index 5be8ec4778..c6ffd17949 100644
--- a/ext/dba/libcdb/cdb.h
+++ b/ext/dba/libcdb/cdb.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/cdb_make.c b/ext/dba/libcdb/cdb_make.c
index 154118c152..2813336b40 100644
--- a/ext/dba/libcdb/cdb_make.c
+++ b/ext/dba/libcdb/cdb_make.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/cdb_make.h b/ext/dba/libcdb/cdb_make.h
index 5bb0ddf5b2..d43fceb6d8 100644
--- a/ext/dba/libcdb/cdb_make.h
+++ b/ext/dba/libcdb/cdb_make.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/uint32.c b/ext/dba/libcdb/uint32.c
index 803a3d5fd7..d8152d5015 100644
--- a/ext/dba/libcdb/uint32.c
+++ b/ext/dba/libcdb/uint32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libcdb/uint32.h b/ext/dba/libcdb/uint32.h
index ac44f05d7d..b0e0b44002 100644
--- a/ext/dba/libcdb/uint32.h
+++ b/ext/dba/libcdb/uint32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libflatfile/flatfile.c b/ext/dba/libflatfile/flatfile.c
index 6ce2f616c8..a1fce218ab 100644
--- a/ext/dba/libflatfile/flatfile.c
+++ b/ext/dba/libflatfile/flatfile.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libflatfile/flatfile.h b/ext/dba/libflatfile/flatfile.h
index b8fbeddc9c..7e9b1796cd 100644
--- a/ext/dba/libflatfile/flatfile.h
+++ b/ext/dba/libflatfile/flatfile.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libinifile/inifile.c b/ext/dba/libinifile/inifile.c
index cc09b3dd80..8c771beba4 100644
--- a/ext/dba/libinifile/inifile.c
+++ b/ext/dba/libinifile/inifile.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/libinifile/inifile.h b/ext/dba/libinifile/inifile.h
index 5a25573892..1177610185 100644
--- a/ext/dba/libinifile/inifile.h
+++ b/ext/dba/libinifile/inifile.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/php_dba.h b/ext/dba/php_dba.h
index 1e931dfe48..6b21b06ee6 100644
--- a/ext/dba/php_dba.h
+++ b/ext/dba/php_dba.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dba/php_tcadb.h b/ext/dba/php_tcadb.h
index 6aa9aa7f8b..b718a172f8 100644
--- a/ext/dba/php_tcadb.h
+++ b/ext/dba/php_tcadb.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/attr.c b/ext/dom/attr.c
index d45ca8820a..ebbc41f6f5 100644
--- a/ext/dom/attr.c
+++ b/ext/dom/attr.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/cdatasection.c b/ext/dom/cdatasection.c
index dc8a3f1492..6ca1ffcf0c 100644
--- a/ext/dom/cdatasection.c
+++ b/ext/dom/cdatasection.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/characterdata.c b/ext/dom/characterdata.c
index 3b1f9b136b..92eb280159 100644
--- a/ext/dom/characterdata.c
+++ b/ext/dom/characterdata.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/comment.c b/ext/dom/comment.c
index 017c2ba78f..eb181ec454 100644
--- a/ext/dom/comment.c
+++ b/ext/dom/comment.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/document.c b/ext/dom/document.c
index efe6d9070f..73bc8c1c62 100644
--- a/ext/dom/document.c
+++ b/ext/dom/document.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -2304,7 +2304,7 @@ PHP_FUNCTION(dom_document_save_html)
xmlBufferPtr buf;
dom_object *intern, *nodeobj;
xmlChar *mem = NULL;
- int size, format;
+ int size = 0, format;
dom_doc_propsptr doc_props;
if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(),
@@ -2332,7 +2332,22 @@ PHP_FUNCTION(dom_document_save_html)
RETURN_FALSE;
}
- size = htmlNodeDump(buf, docp, node);
+ if (node->type == XML_DOCUMENT_FRAG_NODE) {
+ int one_size;
+
+ for (node = node->children; node; node = node->next) {
+ one_size = htmlNodeDump(buf, docp, node);
+
+ if (one_size >= 0) {
+ size += one_size;
+ } else {
+ size = -1;
+ break;
+ }
+ }
+ } else {
+ size = htmlNodeDump(buf, docp, node);
+ }
if (size >= 0) {
mem = (xmlChar*) xmlBufferContent(buf);
if (!mem) {
diff --git a/ext/dom/documentfragment.c b/ext/dom/documentfragment.c
index 4e8d660c9b..e99f57151f 100644
--- a/ext/dom/documentfragment.c
+++ b/ext/dom/documentfragment.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/documenttype.c b/ext/dom/documenttype.c
index 570999a50e..a94cc31d74 100644
--- a/ext/dom/documenttype.c
+++ b/ext/dom/documenttype.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/dom_ce.h b/ext/dom/dom_ce.h
index 8caf0021a1..0e1002536e 100644
--- a/ext/dom/dom_ce.h
+++ b/ext/dom/dom_ce.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/dom_fe.h b/ext/dom/dom_fe.h
index 3778c95208..b05c4aee42 100644
--- a/ext/dom/dom_fe.h
+++ b/ext/dom/dom_fe.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/dom_iterators.c b/ext/dom/dom_iterators.c
index 6c8cf84e9f..987d54de25 100644
--- a/ext/dom/dom_iterators.c
+++ b/ext/dom/dom_iterators.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/dom_properties.h b/ext/dom/dom_properties.h
index 8482502411..a658b1d843 100644
--- a/ext/dom/dom_properties.h
+++ b/ext/dom/dom_properties.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domconfiguration.c b/ext/dom/domconfiguration.c
index 4092d73b37..272fda8f8f 100644
--- a/ext/dom/domconfiguration.c
+++ b/ext/dom/domconfiguration.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domerror.c b/ext/dom/domerror.c
index 92b6622176..cf0eb8da69 100644
--- a/ext/dom/domerror.c
+++ b/ext/dom/domerror.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domerrorhandler.c b/ext/dom/domerrorhandler.c
index 7af3723230..78b75fe615 100644
--- a/ext/dom/domerrorhandler.c
+++ b/ext/dom/domerrorhandler.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domexception.c b/ext/dom/domexception.c
index 9aa878a028..b41b83c6cd 100644
--- a/ext/dom/domexception.c
+++ b/ext/dom/domexception.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domimplementation.c b/ext/dom/domimplementation.c
index 5a32c60dd8..8cdd0fe28b 100644
--- a/ext/dom/domimplementation.c
+++ b/ext/dom/domimplementation.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domimplementationlist.c b/ext/dom/domimplementationlist.c
index d89d2ff143..fde89b7d94 100644
--- a/ext/dom/domimplementationlist.c
+++ b/ext/dom/domimplementationlist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domimplementationsource.c b/ext/dom/domimplementationsource.c
index 2fb5887635..2e8a8d81b2 100644
--- a/ext/dom/domimplementationsource.c
+++ b/ext/dom/domimplementationsource.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domlocator.c b/ext/dom/domlocator.c
index 88c352b3bf..93cd580a01 100644
--- a/ext/dom/domlocator.c
+++ b/ext/dom/domlocator.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/domstringlist.c b/ext/dom/domstringlist.c
index d2ab606d21..f036fbbdd6 100644
--- a/ext/dom/domstringlist.c
+++ b/ext/dom/domstringlist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/element.c b/ext/dom/element.c
index 606a23f9cb..b570471b7d 100644
--- a/ext/dom/element.c
+++ b/ext/dom/element.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/entity.c b/ext/dom/entity.c
index 18e86fceb5..803bb70eec 100644
--- a/ext/dom/entity.c
+++ b/ext/dom/entity.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/entityreference.c b/ext/dom/entityreference.c
index 4ef526c7e1..f2fe3945da 100644
--- a/ext/dom/entityreference.c
+++ b/ext/dom/entityreference.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/namednodemap.c b/ext/dom/namednodemap.c
index 07d7c7002f..d3c8cee558 100644
--- a/ext/dom/namednodemap.c
+++ b/ext/dom/namednodemap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/namelist.c b/ext/dom/namelist.c
index 5831ddeeea..57e6f5d37c 100644
--- a/ext/dom/namelist.c
+++ b/ext/dom/namelist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/node.c b/ext/dom/node.c
index 32795671df..ae74ea04cf 100644
--- a/ext/dom/node.c
+++ b/ext/dom/node.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/nodelist.c b/ext/dom/nodelist.c
index d856f1452a..1a0c811185 100644
--- a/ext/dom/nodelist.c
+++ b/ext/dom/nodelist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/notation.c b/ext/dom/notation.c
index 1fdfe89f76..4c0258cc1f 100644
--- a/ext/dom/notation.c
+++ b/ext/dom/notation.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/php_dom.c b/ext/dom/php_dom.c
index db8ec83a44..0623dbdcde 100644
--- a/ext/dom/php_dom.c
+++ b/ext/dom/php_dom.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/php_dom.h b/ext/dom/php_dom.h
index 3559c4bb5e..f2bccf7b87 100644
--- a/ext/dom/php_dom.h
+++ b/ext/dom/php_dom.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/processinginstruction.c b/ext/dom/processinginstruction.c
index 976b693deb..5a415efc80 100644
--- a/ext/dom/processinginstruction.c
+++ b/ext/dom/processinginstruction.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/string_extend.c b/ext/dom/string_extend.c
index 2c47362fd1..3d65a84bad 100644
--- a/ext/dom/string_extend.c
+++ b/ext/dom/string_extend.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/tests/bug65196.phpt b/ext/dom/tests/bug65196.phpt
new file mode 100644
index 0000000000..c77f97222f
--- /dev/null
+++ b/ext/dom/tests/bug65196.phpt
@@ -0,0 +1,26 @@
+--TEST--
+bug #65196 (Passing DOMDocumentFragment to DOMDocument::saveHTML() Produces invalid Markup)
+--SKIPIF--
+<?php
+extension_loaded("dom") or die("skip need ext/dom");
+?>
+--FILE--
+<?php
+$dom = new DOMDocument();
+
+$frag1 = $dom->createDocumentFragment();
+var_dump($dom->saveHTML($frag1));
+
+$frag2 = $dom->createDocumentFragment();
+$div = $dom->createElement('div');
+$div->appendChild($dom->createElement('span'));
+$frag2->appendChild($div);
+$frag2->appendChild($dom->createElement('div'));
+$frag2->appendChild($dom->createElement('div'));
+var_dump($dom->saveHTML($frag2));
+?>
+===DONE===
+--EXPECT--
+string(0) ""
+string(46) "<div><span></span></div><div></div><div></div>"
+===DONE===
diff --git a/ext/dom/text.c b/ext/dom/text.c
index f608997050..212d040873 100644
--- a/ext/dom/text.c
+++ b/ext/dom/text.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/typeinfo.c b/ext/dom/typeinfo.c
index bc0e60837e..3742780ab7 100644
--- a/ext/dom/typeinfo.c
+++ b/ext/dom/typeinfo.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/userdatahandler.c b/ext/dom/userdatahandler.c
index d368a2957b..6bddff6e73 100644
--- a/ext/dom/userdatahandler.c
+++ b/ext/dom/userdatahandler.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/xml_common.h b/ext/dom/xml_common.h
index 87a41c5305..61d9854e1d 100644
--- a/ext/dom/xml_common.h
+++ b/ext/dom/xml_common.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/dom/xpath.c b/ext/dom/xpath.c
index d12ef30323..a7540ba38d 100644
--- a/ext/dom/xpath.c
+++ b/ext/dom/xpath.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/enchant/enchant.c b/ext/enchant/enchant.c
index 98b5c9fd87..6de2feac80 100644
--- a/ext/enchant/enchant.c
+++ b/ext/enchant/enchant.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/enchant/php_enchant.h b/ext/enchant/php_enchant.h
index 604c47937e..2024effa6a 100644
--- a/ext/enchant/php_enchant.h
+++ b/ext/enchant/php_enchant.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 4 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ereg/ereg.c b/ext/ereg/ereg.c
index 76f5c1b765..20f967feb9 100644
--- a/ext/ereg/ereg.c
+++ b/ext/ereg/ereg.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ereg/php_ereg.h b/ext/ereg/php_ereg.h
index d733d5087d..d34d19855f 100644
--- a/ext/ereg/php_ereg.h
+++ b/ext/ereg/php_ereg.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ereg/php_regex.h b/ext/ereg/php_regex.h
index 53b92da69a..bb83b89fc9 100644
--- a/ext/ereg/php_regex.h
+++ b/ext/ereg/php_regex.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/exif/exif.c b/ext/exif/exif.c
index 2fe54f7b31..38907b4d94 100644
--- a/ext/exif/exif.c
+++ b/ext/exif/exif.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -2852,7 +2852,12 @@ static int exif_process_IFD_TAG(image_info_type *ImageInfo, char *dir_entry, cha
offset_val = php_ifd_get32u(dir_entry+8, ImageInfo->motorola_intel);
/* If its bigger than 4 bytes, the dir entry contains an offset. */
value_ptr = offset_base+offset_val;
- if (byte_count > IFDlength || offset_val > IFDlength-byte_count || value_ptr < dir_entry) {
+ /*
+ dir_entry is ImageInfo->file.list[sn].data+2+i*12
+ offset_base is ImageInfo->file.list[sn].data-dir_offset
+ dir_entry - offset_base is dir_offset+2+i*12
+ */
+ if (byte_count > IFDlength || offset_val > IFDlength-byte_count || value_ptr < dir_entry || offset_val < (size_t)(dir_entry-offset_base)) {
/* It is important to check for IMAGE_FILETYPE_TIFF
* JPEG does not use absolute pointers instead its pointers are
* relative to the start of the TIFF header in APP1 section. */
diff --git a/ext/exif/php_exif.h b/ext/exif/php_exif.h
index 5b624e0e56..e0326752e6 100644
--- a/ext/exif/php_exif.h
+++ b/ext/exif/php_exif.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/fileinfo/fileinfo.c b/ext/fileinfo/fileinfo.c
index 353adb98b9..2d523ab498 100644
--- a/ext/fileinfo/fileinfo.c
+++ b/ext/fileinfo/fileinfo.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/fileinfo/libmagic.patch b/ext/fileinfo/libmagic.patch
index 97e771e920..c5d40e9657 100644
--- a/ext/fileinfo/libmagic.patch
+++ b/ext/fileinfo/libmagic.patch
@@ -1,6 +1,6 @@
diff -u libmagic.orig/apprentice.c libmagic/apprentice.c
---- libmagic.orig/apprentice.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/apprentice.c 2013-04-27 13:53:32.175250261 +0200
+--- libmagic.orig/apprentice.c Thu Mar 21 18:45:14 2013
++++ libmagic/apprentice.c Fri May 3 15:19:35 2013
@@ -29,6 +29,8 @@
* apprentice - make one pass through /etc/magic, learning its secrets.
*/
@@ -830,8 +830,8 @@ diff -u libmagic.orig/apprentice.c libmagic/apprentice.c
m->str_flags = swap4(m->str_flags);
}
diff -u libmagic.orig/ascmagic.c libmagic/ascmagic.c
---- libmagic.orig/ascmagic.c 2012-10-31 18:03:01.000000000 +0100
-+++ libmagic/ascmagic.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/ascmagic.c Wed Oct 31 18:03:01 2012
++++ libmagic/ascmagic.c Tue Feb 18 18:44:17 2014
@@ -139,7 +139,7 @@
/* malloc size is a conservative overestimate; could be
improved, or at least realloced after conversion. */
@@ -841,6 +841,15 @@ diff -u libmagic.orig/ascmagic.c libmagic/ascmagic.c
file_oomem(ms, mlen);
goto done;
}
+@@ -147,7 +147,7 @@
+ == NULL)
+ goto done;
+ if ((rv = file_softmagic(ms, utf8_buf,
+- (size_t)(utf8_end - utf8_buf), TEXTTEST, text)) == 0)
++ (size_t)(utf8_end - utf8_buf), 0, TEXTTEST, text)) == 0)
+ rv = -1;
+ }
+
@@ -211,6 +211,7 @@
case 0:
if (file_printf(ms, ", ") == -1)
@@ -860,8 +869,8 @@ diff -u libmagic.orig/ascmagic.c libmagic/ascmagic.c
return rv;
}
diff -u libmagic.orig/cdf.c libmagic/cdf.c
---- libmagic.orig/cdf.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/cdf.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/cdf.c Thu Mar 21 18:45:14 2013
++++ libmagic/cdf.c Sun Apr 7 22:30:22 2013
@@ -43,7 +43,17 @@
#include <err.h>
#endif
@@ -923,8 +932,8 @@ diff -u libmagic.orig/cdf.c libmagic/cdf.c
(void)fprintf(stderr, "timestamp %s\n", buf);
} else {
diff -u libmagic.orig/cdf.h libmagic/cdf.h
---- libmagic.orig/cdf.h 2012-10-31 18:03:01.000000000 +0100
-+++ libmagic/cdf.h 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/cdf.h Wed Oct 31 18:03:01 2012
++++ libmagic/cdf.h Sun Apr 7 22:30:22 2013
@@ -35,10 +35,12 @@
#ifndef _H_CDF_
#define _H_CDF_
@@ -966,8 +975,8 @@ diff -u libmagic.orig/cdf.h libmagic/cdf.h
void cdf_swap_header(cdf_header_t *);
void cdf_unpack_header(cdf_header_t *, char *);
diff -u libmagic.orig/cdf_time.c libmagic/cdf_time.c
---- libmagic.orig/cdf_time.c 2012-10-31 18:03:01.000000000 +0100
-+++ libmagic/cdf_time.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/cdf_time.c Wed Oct 31 18:03:01 2012
++++ libmagic/cdf_time.c Sun Apr 7 22:30:22 2013
@@ -96,7 +96,7 @@
}
@@ -1026,8 +1035,8 @@ diff -u libmagic.orig/cdf_time.c libmagic/cdf_time.c
static const cdf_timestamp_t tst = 0x01A5E403C2D59C00ULL;
static const char *ref = "Sat Apr 23 01:30:00 1977";
diff -u libmagic.orig/compress.c libmagic/compress.c
---- libmagic.orig/compress.c 2013-01-06 21:35:43.000000000 +0100
-+++ libmagic/compress.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/compress.c Sun Jan 6 21:35:43 2013
++++ libmagic/compress.c Sun Apr 7 22:30:22 2013
@@ -32,6 +32,7 @@
* uncompress(method, old, n, newch) - uncompress old into new,
* using method, return sizeof new
@@ -1189,8 +1198,8 @@ diff -u libmagic.orig/compress.c libmagic/compress.c
-#endif
+#endif /* if PHP_FILEINFO_UNCOMPRESS */
diff -u libmagic.orig/file.h libmagic/file.h
---- libmagic.orig/file.h 2013-02-18 16:40:59.000000000 +0100
-+++ libmagic/file.h 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/file.h Mon Feb 18 16:40:59 2013
++++ libmagic/file.h Tue Feb 18 18:44:17 2014
@@ -33,11 +33,9 @@
#ifndef __file_h__
#define __file_h__
@@ -1303,7 +1312,13 @@ diff -u libmagic.orig/file.h libmagic/file.h
protected int file_zmagic(struct magic_set *, int, const char *,
const unsigned char *, size_t);
#endif
-@@ -443,16 +442,13 @@
+@@ -438,21 +437,18 @@
+ unichar **, size_t *, const char **, const char **, const char **);
+ protected int file_is_tar(struct magic_set *, const unsigned char *, size_t);
+ protected int file_softmagic(struct magic_set *, const unsigned char *, size_t,
+- int, int);
++ size_t, int, int);
+ protected int file_apprentice(struct magic_set *, const char *, int);
protected int file_magicfind(struct magic_set *, const char *, struct mlist *);
protected uint64_t file_signextend(struct magic_set *, struct magic *,
uint64_t);
@@ -1377,22 +1392,24 @@ diff -u libmagic.orig/file.h libmagic/file.h
#if defined(HAVE_MMAP) && defined(HAVE_SYS_MMAN_H) && !defined(QUICK)
#define QUICK
-@@ -533,4 +511,12 @@
- #define FILE_RCSID(id)
+@@ -531,6 +509,14 @@
#endif
-
+ #else
+ #define FILE_RCSID(id)
++#endif
++
+#ifdef PHP_WIN32
+#define FINFO_LSEEK_FUNC _lseek
+#define FINFO_READ_FUNC _read
+#else
+#define FINFO_LSEEK_FUNC lseek
+#define FINFO_READ_FUNC read
-+#endif
-+
+ #endif
+
#endif /* __file_h__ */
diff -u libmagic.orig/fsmagic.c libmagic/fsmagic.c
---- libmagic.orig/fsmagic.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/fsmagic.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/fsmagic.c Thu Mar 21 18:45:14 2013
++++ libmagic/fsmagic.c Sun Apr 7 22:30:22 2013
@@ -59,27 +59,21 @@
# define minor(dev) ((dev) & 0xff)
#endif
@@ -1758,8 +1775,8 @@ diff -u libmagic.orig/fsmagic.c libmagic/fsmagic.c
return ret;
}
diff -u libmagic.orig/funcs.c libmagic/funcs.c
---- libmagic.orig/funcs.c 2012-10-31 18:03:01.000000000 +0100
-+++ libmagic/funcs.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/funcs.c Wed Oct 31 18:03:01 2012
++++ libmagic/funcs.c Tue Feb 18 18:44:17 2014
@@ -41,52 +41,42 @@
#if defined(HAVE_WCTYPE_H)
#include <wctype.h>
@@ -1896,7 +1913,7 @@ diff -u libmagic.orig/funcs.c libmagic/funcs.c
if ((ms->flags & MAGIC_DEBUG) != 0)
(void)fprintf(stderr, "zmagic %d\n", m);
goto done;
-@@ -219,12 +221,17 @@
+@@ -219,16 +221,21 @@
}
/* Check if we have a CDF file */
@@ -1919,6 +1936,11 @@ diff -u libmagic.orig/funcs.c libmagic/funcs.c
/* try soft magic tests */
if ((ms->flags & MAGIC_NO_CHECK_SOFT) == 0)
+- if ((m = file_softmagic(ms, ubuf, nb, BINTEST,
++ if ((m = file_softmagic(ms, ubuf, nb, 0, BINTEST,
+ looks_text)) != 0) {
+ if ((ms->flags & MAGIC_DEBUG) != 0)
+ (void)fprintf(stderr, "softmagic %d\n", m);
@@ -296,7 +303,6 @@
return m;
@@ -2047,8 +2069,8 @@ diff -u libmagic.orig/funcs.c libmagic/funcs.c
}
+
diff -u libmagic.orig/magic.c libmagic/magic.c
---- libmagic.orig/magic.c 2013-01-11 17:43:09.000000000 +0100
-+++ libmagic/magic.c 2013-04-27 13:53:32.175250261 +0200
+--- libmagic.orig/magic.c Fri Jan 11 17:43:09 2013
++++ libmagic/magic.c Fri May 3 15:19:35 2013
@@ -25,11 +25,6 @@
* SUCH DAMAGE.
*/
@@ -2391,8 +2413,8 @@ diff -u libmagic.orig/magic.c libmagic/magic.c
public const char *
magic_error(struct magic_set *ms)
diff -u libmagic.orig/magic.h libmagic/magic.h
---- libmagic.orig/magic.h 2013-03-21 18:52:42.000000000 +0100
-+++ libmagic/magic.h 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/magic.h Thu Mar 21 18:52:42 2013
++++ libmagic/magic.h Sun Apr 7 22:30:22 2013
@@ -87,6 +87,7 @@
const char *magic_getpath(const char *, int);
@@ -2410,15 +2432,15 @@ diff -u libmagic.orig/magic.h libmagic/magic.h
int magic_errno(magic_t);
diff -u libmagic.orig/print.c libmagic/print.c
---- libmagic.orig/print.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/print.c 2013-04-27 13:53:32.175250261 +0200
-@@ -28,13 +28,17 @@
- /*
+--- libmagic.orig/print.c Thu Mar 21 18:45:14 2013
++++ libmagic/print.c Mon Dec 16 23:09:24 2013
+@@ -29,12 +29,17 @@
* print.c - debugging printout routines
*/
+
+#define _GNU_SOURCE
+#include "php.h"
-
++
#include "file.h"
+#include "cdf.h"
@@ -2430,7 +2452,7 @@ diff -u libmagic.orig/print.c libmagic/print.c
#include <string.h>
#include <stdarg.h>
#include <stdlib.h>
-@@ -43,188 +47,28 @@
+@@ -43,188 +48,28 @@
#endif
#include <time.h>
@@ -2631,7 +2653,7 @@ diff -u libmagic.orig/print.c libmagic/print.c
}
protected const char *
-@@ -235,7 +79,7 @@
+@@ -235,7 +80,7 @@
struct tm *tm;
if (flags & FILE_T_WINDOWS) {
@@ -2641,8 +2663,8 @@ diff -u libmagic.orig/print.c libmagic/print.c
t = ts.tv_sec;
}
diff -u libmagic.orig/readcdf.c libmagic/readcdf.c
---- libmagic.orig/readcdf.c 2012-10-31 18:03:01.000000000 +0100
-+++ libmagic/readcdf.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/readcdf.c Wed Oct 31 18:03:01 2012
++++ libmagic/readcdf.c Sun Apr 7 22:30:22 2013
@@ -30,7 +30,11 @@
#endif
@@ -2704,8 +2726,8 @@ diff -u libmagic.orig/readcdf.c libmagic/readcdf.c
if (file_printf(ms, "application/CDFV2-corrupt") == -1)
return -1;
diff -u libmagic.orig/readelf.c libmagic/readelf.c
---- libmagic.orig/readelf.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/readelf.c 2013-04-08 15:42:57.328298809 +0200
+--- libmagic.orig/readelf.c Thu Mar 21 18:45:14 2013
++++ libmagic/readelf.c Sun Apr 7 22:30:22 2013
@@ -48,8 +48,8 @@
private int dophn_exec(struct magic_set *, int, int, int, off_t, int, size_t,
off_t, int *, int);
@@ -2956,8 +2978,8 @@ diff -u libmagic.orig/readelf.c libmagic/readelf.c
if (fstat(fd, &st) == -1) {
diff -u libmagic.orig/readelf.h libmagic/readelf.h
---- libmagic.orig/readelf.h 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/readelf.h 2013-03-31 16:57:18.499744030 +0200
+--- libmagic.orig/readelf.h Thu Mar 21 18:45:14 2013
++++ libmagic/readelf.h Wed Mar 28 15:35:26 2012
@@ -44,9 +44,17 @@
typedef uint32_t Elf32_Word;
typedef uint8_t Elf32_Char;
@@ -2977,8 +2999,8 @@ diff -u libmagic.orig/readelf.h libmagic/readelf.h
typedef uint32_t Elf64_Word;
typedef uint8_t Elf64_Char;
diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
---- libmagic.orig/softmagic.c 2013-03-21 18:45:14.000000000 +0100
-+++ libmagic/softmagic.c 2013-05-14 11:00:07.044745939 +0200
+--- libmagic.orig/softmagic.c Thu Mar 21 18:45:14 2013
++++ libmagic/softmagic.c Thu Feb 20 18:57:46 2014
@@ -41,6 +41,11 @@
#include <stdlib.h>
#include <time.h>
@@ -2991,6 +3013,22 @@ diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
private int match(struct magic_set *, struct magic *, uint32_t,
const unsigned char *, size_t, size_t, int, int, int, int, int *, int *,
+@@ -69,13 +74,13 @@
+ /*ARGSUSED1*/ /* nbytes passed for regularity, maybe need later */
+ protected int
+ file_softmagic(struct magic_set *ms, const unsigned char *buf, size_t nbytes,
+- int mode, int text)
++ size_t level, int mode, int text)
+ {
+ struct mlist *ml;
+ int rv, printed_something = 0, need_separator = 0;
+ for (ml = ms->mlist[0]->next; ml != ms->mlist[0]; ml = ml->next)
+ if ((rv = match(ms, ml->magic, ml->nmagic, buf, nbytes, 0, mode,
+- text, 0, 0, &printed_something, &need_separator,
++ text, 0, level, &printed_something, &need_separator,
+ NULL)) != 0)
+ return rv;
+
@@ -132,7 +137,7 @@
struct magic *m = &magic[magindex];
@@ -3113,7 +3151,7 @@ diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
}
if (m->flag & INDIR) {
-@@ -1644,9 +1624,6 @@
+@@ -1644,16 +1624,13 @@
if ((ms->flags & MAGIC_DEBUG) != 0) {
mdebug(offset, (char *)(void *)p,
sizeof(union VALUETYPE));
@@ -3123,7 +3161,32 @@ diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
}
}
-@@ -1717,12 +1694,12 @@
+ /* Verify we have enough data to match magic type */
+ switch (m->type) {
+ case FILE_BYTE:
+- if (nbytes < (offset + 1)) /* should alway be true */
++ if (nbytes < (offset + 1)) /* should always be true */
+ return 0;
+ break;
+
+@@ -1703,6 +1680,8 @@
+ break;
+
+ case FILE_INDIRECT:
++ if (offset == 0)
++ return 0;
+ if (nbytes < offset)
+ return 0;
+ sbuf = ms->o.buf;
+@@ -1710,19 +1689,21 @@
+ ms->o.buf = NULL;
+ ms->offset = 0;
+ rv = file_softmagic(ms, s + offset, nbytes - offset,
+- BINTEST, text);
++ recursion_level, BINTEST, text);
+ if ((ms->flags & MAGIC_DEBUG) != 0)
+ fprintf(stderr, "indirect @offs=%u[%d]\n", offset, rv);
+ rbuf = ms->o.buf;
ms->o.buf = sbuf;
ms->offset = soffset;
if (rv == 1) {
@@ -3135,11 +3198,13 @@ diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
if (file_printf(ms, "%s", rbuf) == -1)
return -1;
- free(rbuf);
++ }
++ if (rbuf) {
+ efree(rbuf);
}
return rv;
-@@ -1837,6 +1814,42 @@
+@@ -1837,6 +1818,42 @@
return file_strncmp(a, b, len, flags);
}
@@ -3182,7 +3247,7 @@ diff -u libmagic.orig/softmagic.c libmagic/softmagic.c
private int
magiccheck(struct magic_set *ms, struct magic *m)
{
-@@ -1996,69 +2009,157 @@
+@@ -1996,69 +2013,157 @@
break;
}
case FILE_REGEX: {
diff --git a/ext/fileinfo/libmagic/ascmagic.c b/ext/fileinfo/libmagic/ascmagic.c
index 209009764e..c0041df3b4 100644
--- a/ext/fileinfo/libmagic/ascmagic.c
+++ b/ext/fileinfo/libmagic/ascmagic.c
@@ -147,7 +147,7 @@ file_ascmagic_with_encoding(struct magic_set *ms, const unsigned char *buf,
== NULL)
goto done;
if ((rv = file_softmagic(ms, utf8_buf,
- (size_t)(utf8_end - utf8_buf), TEXTTEST, text)) == 0)
+ (size_t)(utf8_end - utf8_buf), 0, TEXTTEST, text)) == 0)
rv = -1;
}
diff --git a/ext/fileinfo/libmagic/file.h b/ext/fileinfo/libmagic/file.h
index 19b6872b49..ab5082d753 100644
--- a/ext/fileinfo/libmagic/file.h
+++ b/ext/fileinfo/libmagic/file.h
@@ -437,7 +437,7 @@ protected int file_encoding(struct magic_set *, const unsigned char *, size_t,
unichar **, size_t *, const char **, const char **, const char **);
protected int file_is_tar(struct magic_set *, const unsigned char *, size_t);
protected int file_softmagic(struct magic_set *, const unsigned char *, size_t,
- int, int);
+ size_t, int, int);
protected int file_apprentice(struct magic_set *, const char *, int);
protected int file_magicfind(struct magic_set *, const char *, struct mlist *);
protected uint64_t file_signextend(struct magic_set *, struct magic *,
diff --git a/ext/fileinfo/libmagic/funcs.c b/ext/fileinfo/libmagic/funcs.c
index 9c0d2bdb7c..011ca42757 100644
--- a/ext/fileinfo/libmagic/funcs.c
+++ b/ext/fileinfo/libmagic/funcs.c
@@ -235,7 +235,7 @@ file_buffer(struct magic_set *ms, php_stream *stream, const char *inname, const
/* try soft magic tests */
if ((ms->flags & MAGIC_NO_CHECK_SOFT) == 0)
- if ((m = file_softmagic(ms, ubuf, nb, BINTEST,
+ if ((m = file_softmagic(ms, ubuf, nb, 0, BINTEST,
looks_text)) != 0) {
if ((ms->flags & MAGIC_DEBUG) != 0)
(void)fprintf(stderr, "softmagic %d\n", m);
diff --git a/ext/fileinfo/libmagic/softmagic.c b/ext/fileinfo/libmagic/softmagic.c
index 0671fa99f9..21fea6b726 100644
--- a/ext/fileinfo/libmagic/softmagic.c
+++ b/ext/fileinfo/libmagic/softmagic.c
@@ -67,6 +67,8 @@ private void cvt_16(union VALUETYPE *, const struct magic *);
private void cvt_32(union VALUETYPE *, const struct magic *);
private void cvt_64(union VALUETYPE *, const struct magic *);
+#define OFFSET_OOB(n, o, i) ((n) < (o) || (i) > ((n) - (o)))
+
/*
* softmagic - lookup one file in parsed, in-memory copy of database
* Passed the name and FILE * of one file to be typed.
@@ -74,13 +76,13 @@ private void cvt_64(union VALUETYPE *, const struct magic *);
/*ARGSUSED1*/ /* nbytes passed for regularity, maybe need later */
protected int
file_softmagic(struct magic_set *ms, const unsigned char *buf, size_t nbytes,
- int mode, int text)
+ size_t level, int mode, int text)
{
struct mlist *ml;
int rv, printed_something = 0, need_separator = 0;
for (ml = ms->mlist[0]->next; ml != ms->mlist[0]; ml = ml->next)
if ((rv = match(ms, ml->magic, ml->nmagic, buf, nbytes, 0, mode,
- text, 0, 0, &printed_something, &need_separator,
+ text, 0, level, &printed_something, &need_separator,
NULL)) != 0)
return rv;
@@ -1171,7 +1173,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
}
switch (cvt_flip(m->in_type, flip)) {
case FILE_BYTE:
- if (nbytes < (offset + 1))
+ if (OFFSET_OOB(nbytes, offset, 1))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1206,7 +1208,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
offset = ~offset;
break;
case FILE_BESHORT:
- if (nbytes < (offset + 2))
+ if (OFFSET_OOB(nbytes, offset, 2))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1258,7 +1260,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
offset = ~offset;
break;
case FILE_LESHORT:
- if (nbytes < (offset + 2))
+ if (OFFSET_OOB(nbytes, offset, 2))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1310,7 +1312,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
offset = ~offset;
break;
case FILE_SHORT:
- if (nbytes < (offset + 2))
+ if (OFFSET_OOB(nbytes, offset, 2))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1347,7 +1349,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
break;
case FILE_BELONG:
case FILE_BEID3:
- if (nbytes < (offset + 4))
+ if (OFFSET_OOB(nbytes, offset, 4))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1418,7 +1420,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
break;
case FILE_LELONG:
case FILE_LEID3:
- if (nbytes < (offset + 4))
+ if (OFFSET_OOB(nbytes, offset, 4))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1488,7 +1490,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
offset = ~offset;
break;
case FILE_MELONG:
- if (nbytes < (offset + 4))
+ if (OFFSET_OOB(nbytes, offset, 4))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1558,7 +1560,7 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
offset = ~offset;
break;
case FILE_LONG:
- if (nbytes < (offset + 4))
+ if (OFFSET_OOB(nbytes, offset, 4))
return 0;
if (off) {
switch (m->in_op & FILE_OPS_MASK) {
@@ -1630,14 +1632,14 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
/* Verify we have enough data to match magic type */
switch (m->type) {
case FILE_BYTE:
- if (nbytes < (offset + 1)) /* should always be true */
+ if (OFFSET_OOB(nbytes, offset, 1))
return 0;
break;
case FILE_SHORT:
case FILE_BESHORT:
case FILE_LESHORT:
- if (nbytes < (offset + 2))
+ if (OFFSET_OOB(nbytes, offset, 2))
return 0;
break;
@@ -1656,55 +1658,67 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
case FILE_FLOAT:
case FILE_BEFLOAT:
case FILE_LEFLOAT:
- if (nbytes < (offset + 4))
+ if (OFFSET_OOB(nbytes, offset, 4))
return 0;
break;
case FILE_DOUBLE:
case FILE_BEDOUBLE:
case FILE_LEDOUBLE:
- if (nbytes < (offset + 8))
+ if (OFFSET_OOB(nbytes, offset, 8))
return 0;
break;
case FILE_STRING:
case FILE_PSTRING:
case FILE_SEARCH:
- if (nbytes < (offset + m->vallen))
+ if (OFFSET_OOB(nbytes, offset, m->vallen))
return 0;
break;
case FILE_REGEX:
- if (nbytes < offset)
+ if (OFFSET_OOB(nbytes, offset, 0))
return 0;
break;
case FILE_INDIRECT:
- if (nbytes < offset)
+ if (offset == 0)
+ return 0;
+ if (OFFSET_OOB(nbytes, offset, 0))
return 0;
sbuf = ms->o.buf;
soffset = ms->offset;
ms->o.buf = NULL;
ms->offset = 0;
rv = file_softmagic(ms, s + offset, nbytes - offset,
- BINTEST, text);
+ recursion_level, BINTEST, text);
if ((ms->flags & MAGIC_DEBUG) != 0)
fprintf(stderr, "indirect @offs=%u[%d]\n", offset, rv);
rbuf = ms->o.buf;
ms->o.buf = sbuf;
ms->offset = soffset;
if (rv == 1) {
- if ((ms->flags & (MAGIC_MIME|MAGIC_APPLE)) == 0 &&
- file_printf(ms, m->desc, offset) == -1)
- return -1;
- if (file_printf(ms, "%s", rbuf) == -1)
+ if ((ms->flags & (MAGIC_MIME|MAGIC_APPLE)) == 0 &&
+ file_printf(ms, m->desc, offset) == -1) {
+ if (rbuf) {
+ efree(rbuf);
+ }
return -1;
+ }
+ if (file_printf(ms, "%s", rbuf) == -1) {
+ if (rbuf) {
+ efree(rbuf);
+ }
+ return -1;
+ }
+ }
+ if (rbuf) {
efree(rbuf);
}
return rv;
case FILE_USE:
- if (nbytes < offset)
+ if (OFFSET_OOB(nbytes, offset, 0))
return 0;
sbuf = m->value.s;
if (*sbuf == '^') {
diff --git a/ext/fileinfo/php_fileinfo.h b/ext/fileinfo/php_fileinfo.h
index 4a34357ccf..354ec7b284 100644
--- a/ext/fileinfo/php_fileinfo.h
+++ b/ext/fileinfo/php_fileinfo.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -24,7 +24,7 @@
extern zend_module_entry fileinfo_module_entry;
#define phpext_fileinfo_ptr &fileinfo_module_entry
-#define PHP_FILEINFO_VERSION "1.0.5-dev"
+#define PHP_FILEINFO_VERSION "1.0.5"
#ifdef PHP_WIN32
#define PHP_FILEINFO_API __declspec(dllexport)
diff --git a/ext/fileinfo/tests/cve-2014-1943.phpt b/ext/fileinfo/tests/cve-2014-1943.phpt
new file mode 100644
index 0000000000..b2e9c17c3f
--- /dev/null
+++ b/ext/fileinfo/tests/cve-2014-1943.phpt
@@ -0,0 +1,39 @@
+--TEST--
+Bug #66731: file: infinite recursion
+--SKIPIF--
+<?php
+if (!class_exists('finfo'))
+ die('skip no fileinfo extension');
+--FILE--
+<?php
+$fd = __DIR__.'/cve-2014-1943.data';
+$fm = __DIR__.'/cve-2014-1943.magic';
+
+$a = "\105\122\000\000\000\000\000";
+$b = str_repeat("\001", 250000);
+$m = "0 byte x\n".
+ ">(1.b) indirect x\n";
+
+file_put_contents($fd, $a);
+$fi = finfo_open(FILEINFO_NONE);
+var_dump(finfo_file($fi, $fd));
+finfo_close($fi);
+
+file_put_contents($fd, $b);
+file_put_contents($fm, $m);
+$fi = finfo_open(FILEINFO_NONE, $fm);
+var_dump(finfo_file($fi, $fd));
+finfo_close($fi);
+?>
+Done
+--CLEAN--
+<?php
+@unlink(__DIR__.'/cve-2014-1943.data');
+@unlink(__DIR__.'/cve-2014-1943.magic');
+?>
+--EXPECTF--
+string(%d) "%s"
+
+Warning: finfo_file(): Failed identify data 0:(null) in %s on line %d
+bool(false)
+Done
diff --git a/ext/fileinfo/tests/magic b/ext/fileinfo/tests/magic
index aa75fb65bc..b554333a6c 100644
--- a/ext/fileinfo/tests/magic
+++ b/ext/fileinfo/tests/magic
@@ -4888,7 +4888,7 @@
>>0 ubyte 0xF5 FoxPro with memo
# http://msdn.microsoft.com/en-US/library/st4a0s68(v=vs.80).aspx
#>>0 ubyte 0xFA FoxPro 2.x, with memo
-# unkown version (should not happen)
+# unknown version (should not happen)
>>0 default x xBase
>>>0 ubyte x (0x%x)
# flags in version byte
@@ -6115,7 +6115,7 @@
>>>>>379 string GRUB\ \0 \b, GRUB version 0.95 or 0.96
>>>>391 string Geom\0Hard\ Disk\0Read\0\ Error\0
>>>>>385 string GRUB\ \0 \b, GRUB version 0.97
-#unkown version
+#unknown version
>>>343 string Geom\0Read\0\ Error\0
>>>>321 string Loading\ stage1.5 \b, GRUB version x.y
>>>380 string Geom\0Hard\ Disk\0Read\0\ Error\0
diff --git a/ext/filter/callback_filter.c b/ext/filter/callback_filter.c
index 3beacb6a8f..644807d0dd 100644
--- a/ext/filter/callback_filter.c
+++ b/ext/filter/callback_filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/filter/filter.c b/ext/filter/filter.c
index 12aebcf366..4d3899e089 100644
--- a/ext/filter/filter.c
+++ b/ext/filter/filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/filter/filter_private.h b/ext/filter/filter_private.h
index 65e61dfea7..fc596f02ca 100644
--- a/ext/filter/filter_private.h
+++ b/ext/filter/filter_private.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/filter/logical_filters.c b/ext/filter/logical_filters.c
index 39433d6ece..923e6f6a39 100644
--- a/ext/filter/logical_filters.c
+++ b/ext/filter/logical_filters.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -715,8 +715,6 @@ void php_filter_validate_ip(PHP_INPUT_FILTER_PARAM_DECL) /* {{{ */
if (
(ip[0] == 0) ||
(ip[0] == 100 && (ip[1] >= 64 && ip[1] <= 127)) ||
- (ip[0] == 128 && ip[1] == 0) ||
- (ip[0] == 191 && ip[1] == 255) ||
(ip[0] == 169 && ip[1] == 254) ||
(ip[0] == 192 && ip[1] == 0 && ip[2] == 2) ||
(ip[0] == 127 && ip[1] == 0 && ip[2] == 0 && ip[3] == 1) ||
diff --git a/ext/filter/php_filter.h b/ext/filter/php_filter.h
index e31f0f0817..37ccdd23bb 100644
--- a/ext/filter/php_filter.h
+++ b/ext/filter/php_filter.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/filter/sanitizing_filters.c b/ext/filter/sanitizing_filters.c
index 30da05a217..7d1e74830e 100644
--- a/ext/filter/sanitizing_filters.c
+++ b/ext/filter/sanitizing_filters.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/filter/tests/bug53150.phpt b/ext/filter/tests/bug53150.phpt
index 4baa4db772..4906888bdf 100644
--- a/ext/filter/tests/bug53150.phpt
+++ b/ext/filter/tests/bug53150.phpt
@@ -23,6 +23,6 @@ string(3) "::1"
bool(false)
bool(false)
string(9) "128.0.0.1"
-bool(false)
+string(9) "128.0.0.1"
+string(11) "191.255.0.0"
string(11) "191.255.0.0"
-bool(false)
diff --git a/ext/ftp/ftp.c b/ext/ftp/ftp.c
index 30b3ba6285..558463b845 100644
--- a/ext/ftp/ftp.c
+++ b/ext/ftp/ftp.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -178,6 +178,10 @@ ftp_close(ftpbuf_t *ftp)
if (ftp->data) {
data_close(ftp, ftp->data);
}
+ if (ftp->stream && ftp->closestream) {
+ TSRMLS_FETCH();
+ php_stream_close(ftp->stream);
+ }
if (ftp->fd != -1) {
#if HAVE_OPENSSL_EXT
if (ftp->ssl_active) {
diff --git a/ext/ftp/ftp.h b/ext/ftp/ftp.h
index 69de7dbb78..2759ce2af5 100644
--- a/ext/ftp/ftp.h
+++ b/ext/ftp/ftp.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ftp/php_ftp.c b/ext/ftp/php_ftp.c
index 21e13ea460..79c871f559 100644
--- a/ext/ftp/php_ftp.c
+++ b/ext/ftp/php_ftp.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -963,6 +963,7 @@ PHP_FUNCTION(ftp_nb_get)
if ((ret = ftp_nb_get(ftp, outstream, remote, xtype, resumepos TSRMLS_CC)) == PHP_FTP_FAILED) {
php_stream_close(outstream);
+ ftp->stream = NULL;
VCWD_UNLINK(local);
php_error_docref(NULL TSRMLS_CC, E_WARNING, "%s", ftp->inbuf);
RETURN_LONG(PHP_FTP_FAILED);
@@ -970,6 +971,7 @@ PHP_FUNCTION(ftp_nb_get)
if (ret == PHP_FTP_FINISHED){
php_stream_close(outstream);
+ ftp->stream = NULL;
}
RETURN_LONG(ret);
@@ -1003,6 +1005,7 @@ PHP_FUNCTION(ftp_nb_continue)
if (ret != PHP_FTP_MOREDATA && ftp->closestream) {
php_stream_close(ftp->stream);
+ ftp->stream = NULL;
}
if (ret == PHP_FTP_FAILED) {
@@ -1214,6 +1217,7 @@ PHP_FUNCTION(ftp_nb_put)
if (ret != PHP_FTP_MOREDATA) {
php_stream_close(instream);
+ ftp->stream = NULL;
}
if (ret == PHP_FTP_FAILED) {
diff --git a/ext/ftp/php_ftp.h b/ext/ftp/php_ftp.h
index 41f65f900a..fffe6bf2f5 100644
--- a/ext/ftp/php_ftp.h
+++ b/ext/ftp/php_ftp.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/ftp/tests/ftp_fget_basic1.phpt b/ext/ftp/tests/ftp_fget_basic1.phpt
index 475f7183d2..5909d35cef 100644
--- a/ext/ftp/tests/ftp_fget_basic1.phpt
+++ b/ext/ftp/tests/ftp_fget_basic1.phpt
@@ -16,7 +16,7 @@ ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
ftp_set_option($ftp, FTP_AUTOSEEK, false);
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic1.txt";
$handle = fopen($local_file, 'w');
var_dump(ftp_fget($ftp, $handle, 'fget.txt', FTP_ASCII, FTP_AUTORESUME));
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic1.txt");
?>
--EXPECT--
bool(true)
diff --git a/ext/ftp/tests/ftp_fget_basic2.phpt b/ext/ftp/tests/ftp_fget_basic2.phpt
index 00a26752d9..622cea3683 100644
--- a/ext/ftp/tests/ftp_fget_basic2.phpt
+++ b/ext/ftp/tests/ftp_fget_basic2.phpt
@@ -15,7 +15,7 @@ $ftp = ftp_connect('127.0.0.1', $port);
ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic2.txt";
file_put_contents($local_file, 'ASCIIFoo');
$handle = fopen($local_file, 'a');
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic2.txt");
?>
--EXPECT--
bool(true)
diff --git a/ext/ftp/tests/ftp_fget_basic3.phpt b/ext/ftp/tests/ftp_fget_basic3.phpt
index b7098701ab..9485473b1c 100644
--- a/ext/ftp/tests/ftp_fget_basic3.phpt
+++ b/ext/ftp/tests/ftp_fget_basic3.phpt
@@ -15,7 +15,7 @@ $ftp = ftp_connect('127.0.0.1', $port);
ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic3.txt";
file_put_contents($local_file, 'ASCIIFoo');
$handle = fopen($local_file, 'a');
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_fget_basic3.txt");
?>
--EXPECT--
bool(true)
diff --git a/ext/ftp/tests/ftp_nb_fget_basic1.phpt b/ext/ftp/tests/ftp_nb_fget_basic1.phpt
index cac4eec56b..5e6389ff13 100644
--- a/ext/ftp/tests/ftp_nb_fget_basic1.phpt
+++ b/ext/ftp/tests/ftp_nb_fget_basic1.phpt
@@ -16,7 +16,7 @@ ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
ftp_set_option($ftp, FTP_AUTOSEEK, false);
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic1.txt";
$handle = fopen($local_file, 'w');
var_dump(ftp_nb_fget($ftp, $handle, 'fget.txt', FTP_ASCII, FTP_AUTORESUME));
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic1.txt");
?>
--EXPECT--
int(2)
diff --git a/ext/ftp/tests/ftp_nb_fget_basic2.phpt b/ext/ftp/tests/ftp_nb_fget_basic2.phpt
index dc92f4e23b..215b79ac4a 100644
--- a/ext/ftp/tests/ftp_nb_fget_basic2.phpt
+++ b/ext/ftp/tests/ftp_nb_fget_basic2.phpt
@@ -15,7 +15,7 @@ $ftp = ftp_connect('127.0.0.1', $port);
ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic2.txt";
file_put_contents($local_file, 'ASCIIFoo');
$handle = fopen($local_file, 'a');
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic2.txt");
?>
--EXPECT--
int(2)
diff --git a/ext/ftp/tests/ftp_nb_fget_basic3.phpt b/ext/ftp/tests/ftp_nb_fget_basic3.phpt
index d1a87c4f3d..66daf2ba0a 100644
--- a/ext/ftp/tests/ftp_nb_fget_basic3.phpt
+++ b/ext/ftp/tests/ftp_nb_fget_basic3.phpt
@@ -15,7 +15,7 @@ $ftp = ftp_connect('127.0.0.1', $port);
ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic3.txt";
file_put_contents($local_file, 'ASCIIFoo');
$handle = fopen($local_file, 'a');
@@ -24,7 +24,7 @@ var_dump(file_get_contents($local_file));
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_fget_basic3.txt");
?>
--EXPECT--
int(2)
diff --git a/ext/ftp/tests/ftp_nb_get_large.phpt b/ext/ftp/tests/ftp_nb_get_large.phpt
index 3fbf2a4831..0c354d7c19 100644
--- a/ext/ftp/tests/ftp_nb_get_large.phpt
+++ b/ext/ftp/tests/ftp_nb_get_large.phpt
@@ -18,7 +18,7 @@ $ftp = ftp_connect('127.0.0.1', $port);
ftp_login($ftp, 'user', 'pass');
if (!$ftp) die("Couldn't connect to the server");
-$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt";
+$local_file = dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_get_large.txt";
touch($local_file);
ftp_nb_get($ftp, $local_file, 'fget_large.txt', FTP_BINARY, 5368709119);
$fp = fopen($local_file, 'r');
@@ -29,7 +29,7 @@ fclose($fp);
?>
--CLEAN--
<?php
-@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "localfile.txt");
+@unlink(dirname(__FILE__) . DIRECTORY_SEPARATOR . "ftp_nb_get_large.txt");
?>
--EXPECT--
string(1) "X"
diff --git a/ext/gd/config.m4 b/ext/gd/config.m4
index c9e080faab..446c2425ae 100644
--- a/ext/gd/config.m4
+++ b/ext/gd/config.m4
@@ -185,30 +185,25 @@ AC_DEFUN([PHP_GD_FREETYPE2],[
if test "$PHP_FREETYPE_DIR" != "no"; then
for i in $PHP_FREETYPE_DIR /usr/local /usr; do
- if test -f "$i/include/freetype2/freetype/freetype.h"; then
+ if test -f "$i/bin/freetype-config"; then
FREETYPE2_DIR=$i
- FREETYPE2_INC_DIR=$i/include/freetype2
+ FREETYPE2_CONFIG="$i/bin/freetype-config"
break
fi
done
if test -z "$FREETYPE2_DIR"; then
- AC_MSG_ERROR([freetype.h not found.])
+ AC_MSG_ERROR([freetype-config not found.])
fi
- PHP_CHECK_LIBRARY(freetype, FT_New_Face,
- [
- PHP_ADD_LIBRARY_WITH_PATH(freetype, $FREETYPE2_DIR/$PHP_LIBDIR, GD_SHARED_LIBADD)
- PHP_ADD_INCLUDE($FREETYPE2_DIR/include)
- PHP_ADD_INCLUDE($FREETYPE2_INC_DIR)
- AC_DEFINE(USE_GD_IMGSTRTTF, 1, [ ])
- AC_DEFINE(HAVE_LIBFREETYPE,1,[ ])
- AC_DEFINE(ENABLE_GD_TTF,1,[ ])
- ],[
- AC_MSG_ERROR([Problem with freetype.(a|so). Please check config.log for more information.])
- ],[
- -L$FREETYPE2_DIR/$PHP_LIBDIR
- ])
+ FREETYPE2_CFLAGS=`$FREETYPE2_CONFIG --cflags`
+ FREETYPE2_LIBS=`$FREETYPE2_CONFIG --libs`
+
+ PHP_EVAL_INCLINE($FREETYPE2_CFLAGS)
+ PHP_EVAL_LIBLINE($FREETYPE2_LIBS, GD_SHARED_LIBADD)
+ AC_DEFINE(USE_GD_IMGSTRTTF, 1, [ ])
+ AC_DEFINE(HAVE_LIBFREETYPE,1,[ ])
+ AC_DEFINE(ENABLE_GD_TTF,1,[ ])
else
AC_MSG_RESULT([If configure fails try --with-freetype-dir=<DIR>])
fi
diff --git a/ext/gd/gd.c b/ext/gd/gd.c
index fb258214a1..0c4a0b36ff 100644
--- a/ext/gd/gd.c
+++ b/ext/gd/gd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1538,9 +1538,15 @@ PHP_FUNCTION(imagesetstyle)
break;
}
- convert_to_long_ex(item);
-
- stylearr[index++] = Z_LVAL_PP(item);
+ if (Z_TYPE_PP(item) != IS_LONG) {
+ zval lval;
+ lval = **item;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ stylearr[index++] = Z_LVAL(lval);
+ } else {
+ stylearr[index++] = Z_LVAL_PP(item);
+ }
}
gdImageSetStyle(im, stylearr, index);
@@ -3346,14 +3352,26 @@ static void php_imagepolygon(INTERNAL_FUNCTION_PARAMETERS, int filled)
for (i = 0; i < npoints; i++) {
if (zend_hash_index_find(Z_ARRVAL_P(POINTS), (i * 2), (void **) &var) == SUCCESS) {
- SEPARATE_ZVAL((var));
- convert_to_long(*var);
- points[i].x = Z_LVAL_PP(var);
+ if (Z_TYPE_PP(var) != IS_LONG) {
+ zval lval;
+ lval = **var;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ points[i].x = Z_LVAL(lval);
+ } else {
+ points[i].x = Z_LVAL_PP(var);
+ }
}
if (zend_hash_index_find(Z_ARRVAL_P(POINTS), (i * 2) + 1, (void **) &var) == SUCCESS) {
- SEPARATE_ZVAL(var);
- convert_to_long(*var);
- points[i].y = Z_LVAL_PP(var);
+ if (Z_TYPE_PP(var) != IS_LONG) {
+ zval lval;
+ lval = **var;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ points[i].y = Z_LVAL(lval);
+ } else {
+ points[i].y = Z_LVAL_PP(var);
+ }
}
}
@@ -4859,9 +4877,15 @@ PHP_FUNCTION(imageconvolution)
for (j=0; j<3; j++) {
if (zend_hash_index_find(Z_ARRVAL_PP(var), (j), (void **) &var2) == SUCCESS) {
- SEPARATE_ZVAL(var2);
- convert_to_double(*var2);
- matrix[i][j] = (float)Z_DVAL_PP(var2);
+ if (Z_TYPE_PP(var2) != IS_DOUBLE) {
+ zval dval;
+ dval = **var2;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ matrix[i][j] = (float)Z_DVAL(dval);
+ } else {
+ matrix[i][j] = (float)Z_DVAL_PP(var2);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "You must have a 3x3 matrix");
RETURN_FALSE;
@@ -4954,28 +4978,60 @@ PHP_FUNCTION(imagecrop)
ZEND_FETCH_RESOURCE(im, gdImagePtr, &IM, -1, "Image", le_gd);
if (zend_hash_find(HASH_OF(z_rect), "x", sizeof("x"), (void **)&tmp) != FAILURE) {
- rect.x = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.x = Z_LVAL(lval);
+ } else {
+ rect.x = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing x position");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "y", sizeof("x"), (void **)&tmp) != FAILURE) {
- rect.y = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.y = Z_LVAL(lval);
+ } else {
+ rect.y = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing y position");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "width", sizeof("width"), (void **)&tmp) != FAILURE) {
- rect.width = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.width = Z_LVAL(lval);
+ } else {
+ rect.width = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing width");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "height", sizeof("height"), (void **)&tmp) != FAILURE) {
- rect.height = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.height = Z_LVAL(lval);
+ } else {
+ rect.height = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing height");
RETURN_FALSE;
@@ -5124,8 +5180,13 @@ PHP_FUNCTION(imageaffine)
affine[i] = Z_DVAL_PP(zval_affine_elem);
break;
case IS_STRING:
- convert_to_double_ex(zval_affine_elem);
- affine[i] = Z_DVAL_PP(zval_affine_elem);
+ {
+ zval dval;
+ dval = **zval_affine_elem;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ affine[i] = Z_DVAL(dval);
+ }
break;
default:
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid type for element %i", i);
@@ -5136,32 +5197,60 @@ PHP_FUNCTION(imageaffine)
if (z_rect != NULL) {
if (zend_hash_find(HASH_OF(z_rect), "x", sizeof("x"), (void **)&tmp) != FAILURE) {
- convert_to_long_ex(tmp);
- rect.x = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.x = Z_LVAL(lval);
+ } else {
+ rect.x = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing x position");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "y", sizeof("x"), (void **)&tmp) != FAILURE) {
- convert_to_long_ex(tmp);
- rect.y = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.y = Z_LVAL(lval);
+ } else {
+ rect.y = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing y position");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "width", sizeof("width"), (void **)&tmp) != FAILURE) {
- convert_to_long_ex(tmp);
- rect.width = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.width = Z_LVAL(lval);
+ } else {
+ rect.width = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing width");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(z_rect), "height", sizeof("height"), (void **)&tmp) != FAILURE) {
- convert_to_long_ex(tmp);
- rect.height = Z_LVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_LONG) {
+ zval lval;
+ lval = **tmp;
+ zval_copy_ctor(&lval);
+ convert_to_long(&lval);
+ rect.height = Z_LVAL(lval);
+ } else {
+ rect.height = Z_LVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing height");
RETURN_FALSE;
@@ -5211,16 +5300,30 @@ PHP_FUNCTION(imageaffinematrixget)
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Array expected as options");
}
if (zend_hash_find(HASH_OF(options), "x", sizeof("x"), (void **)&tmp) != FAILURE) {
- convert_to_double_ex(tmp);
- x = Z_DVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_DOUBLE) {
+ zval dval;
+ dval = **tmp;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ x = Z_DVAL(dval);
+ } else {
+ x = Z_DVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing x position");
RETURN_FALSE;
}
if (zend_hash_find(HASH_OF(options), "y", sizeof("y"), (void **)&tmp) != FAILURE) {
- convert_to_double_ex(tmp);
- y = Z_DVAL_PP(tmp);
+ if (Z_TYPE_PP(tmp) != IS_DOUBLE) {
+ zval dval;
+ dval = **tmp;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ y = Z_DVAL(dval);
+ } else {
+ y = Z_DVAL_PP(tmp);
+ }
} else {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Missing y position");
RETURN_FALSE;
@@ -5300,8 +5403,13 @@ PHP_FUNCTION(imageaffinematrixconcat)
m1[i] = Z_DVAL_PP(tmp);
break;
case IS_STRING:
- convert_to_double_ex(tmp);
- m1[i] = Z_DVAL_PP(tmp);
+ {
+ zval dval;
+ dval = **tmp;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ m1[i] = Z_DVAL(dval);
+ }
break;
default:
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid type for element %i", i);
@@ -5317,8 +5425,13 @@ PHP_FUNCTION(imageaffinematrixconcat)
m2[i] = Z_DVAL_PP(tmp);
break;
case IS_STRING:
- convert_to_double_ex(tmp);
- m2[i] = Z_DVAL_PP(tmp);
+ {
+ zval dval;
+ dval = **tmp;
+ zval_copy_ctor(&dval);
+ convert_to_double(&dval);
+ m2[i] = Z_DVAL(dval);
+ }
break;
default:
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Invalid type for element %i", i);
diff --git a/ext/gd/gd_ctx.c b/ext/gd/gd_ctx.c
index 2a0b500e9e..59eff80443 100644
--- a/ext/gd/gd_ctx.c
+++ b/ext/gd/gd_ctx.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gd/libgd/gd_crop.c b/ext/gd/libgd/gd_crop.c
index f0b888a4f1..bba425d0e3 100644
--- a/ext/gd/libgd/gd_crop.c
+++ b/ext/gd/libgd/gd_crop.c
@@ -43,7 +43,14 @@ static int gdColorMatch(gdImagePtr im, int col1, int col2, float threshold);
gdImagePtr gdImageCrop(gdImagePtr src, const gdRectPtr crop)
{
gdImagePtr dst;
+ int y;
+ /* check size */
+ if (crop->width<=0 || crop->height<=0) {
+ return NULL;
+ }
+
+ /* allocate the requested size (could be only partially filled) */
if (src->trueColor) {
dst = gdImageCreateTrueColor(crop->width, crop->height);
gdImageSaveAlpha(dst, 1);
@@ -51,37 +58,43 @@ gdImagePtr gdImageCrop(gdImagePtr src, const gdRectPtr crop)
dst = gdImageCreate(crop->width, crop->height);
gdImagePaletteCopy(dst, src);
}
+ if (dst == NULL) {
+ return NULL;
+ }
dst->transparent = src->transparent;
- if (src->sx < (crop->x + crop->width -1)) {
- crop->width = src->sx - crop->x + 1;
+ /* check position in the src image */
+ if (crop->x < 0 || crop->x>=src->sx || crop->y<0 || crop->y>=src->sy) {
+ return dst;
+ }
+
+ /* reduce size if needed */
+ if ((src->sx - crop->width) < crop->x) {
+ crop->width = src->sx - crop->x;
}
- if (src->sy < (crop->y + crop->height -1)) {
- crop->height = src->sy - crop->y + 1;
+ if ((src->sy - crop->height) < crop->y) {
+ crop->height = src->sy - crop->y;
}
+
#if 0
printf("rect->x: %i\nrect->y: %i\nrect->width: %i\nrect->height: %i\n", crop->x, crop->y, crop->width, crop->height);
#endif
- if (dst == NULL) {
- return NULL;
+ y = crop->y;
+ if (src->trueColor) {
+ unsigned int dst_y = 0;
+ while (y < (crop->y + (crop->height - 1))) {
+ /* TODO: replace 4 w/byte per channel||pitch once available */
+ memcpy(dst->tpixels[dst_y++], src->tpixels[y++] + crop->x, crop->width * 4);
+ }
} else {
- int y = crop->y;
- if (src->trueColor) {
- unsigned int dst_y = 0;
- while (y < (crop->y + (crop->height - 1))) {
- /* TODO: replace 4 w/byte per channel||pitch once available */
- memcpy(dst->tpixels[dst_y++], src->tpixels[y++] + crop->x, crop->width * 4);
- }
- } else {
- int x;
- for (y = crop->y; y < (crop->y + (crop->height - 1)); y++) {
- for (x = crop->x; x < (crop->x + (crop->width - 1)); x++) {
- dst->pixels[y - crop->y][x - crop->x] = src->pixels[y][x];
- }
+ int x;
+ for (y = crop->y; y < (crop->y + (crop->height - 1)); y++) {
+ for (x = crop->x; x < (crop->x + (crop->width - 1)); x++) {
+ dst->pixels[y - crop->y][x - crop->x] = src->pixels[y][x];
}
}
- return dst;
}
+ return dst;
}
/**
diff --git a/ext/gd/libgd/xbm.c b/ext/gd/libgd/xbm.c
index 9491328d66..d6fdd7d086 100644
--- a/ext/gd/libgd/xbm.c
+++ b/ext/gd/libgd/xbm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gd/php_gd.h b/ext/gd/php_gd.h
index 22fac40dd0..1f32a8f9b1 100644
--- a/ext/gd/php_gd.h
+++ b/ext/gd/php_gd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gd/tests/bug66356.phpt b/ext/gd/tests/bug66356.phpt
new file mode 100644
index 0000000000..2da91d61a9
--- /dev/null
+++ b/ext/gd/tests/bug66356.phpt
@@ -0,0 +1,40 @@
+--TEST--
+Bug #66356 (Heap Overflow Vulnerability in imagecrop())
+--SKIPIF--
+<?php
+ if(!extension_loaded('gd')){ die('skip gd extension not available'); }
+?>
+--FILE--
+<?php
+$img = imagecreatetruecolor(10, 10);
+
+// POC #1
+var_dump(imagecrop($img, array("x" => "a", "y" => 0, "width" => 10, "height" => 10)));
+
+$arr = array("x" => "a", "y" => "12b", "width" => 10, "height" => 10);
+var_dump(imagecrop($img, $arr));
+print_r($arr);
+
+// POC #2
+var_dump(imagecrop($img, array("x" => 0, "y" => 0, "width" => -1, "height" => 10)));
+
+// POC #3
+var_dump(imagecrop($img, array("x" => -20, "y" => -20, "width" => 10, "height" => 10)));
+
+// POC #4
+var_dump(imagecrop($img, array("x" => 0x7fffff00, "y" => 0, "width" => 10, "height" => 10)));
+
+?>
+--EXPECTF--
+resource(%d) of type (gd)
+resource(%d) of type (gd)
+Array
+(
+ [x] => a
+ [y] => 12b
+ [width] => 10
+ [height] => 10
+)
+bool(false)
+resource(%d) of type (gd)
+resource(%d) of type (gd) \ No newline at end of file
diff --git a/ext/gettext/gettext.c b/ext/gettext/gettext.c
index ed86b6cbc4..732ef54998 100644
--- a/ext/gettext/gettext.c
+++ b/ext/gettext/gettext.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gettext/php_gettext.h b/ext/gettext/php_gettext.h
index 0c517d9a51..f990d32af5 100644
--- a/ext/gettext/php_gettext.h
+++ b/ext/gettext/php_gettext.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gmp/gmp.c b/ext/gmp/gmp.c
index e3a3563aac..25e8203030 100644
--- a/ext/gmp/gmp.c
+++ b/ext/gmp/gmp.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/gmp/php_gmp.h b/ext/gmp/php_gmp.h
index e1aaef886d..50feadc2d4 100644
--- a/ext/gmp/php_gmp.h
+++ b/ext/gmp/php_gmp.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash.c b/ext/hash/hash.c
index 117221484e..5222a395e6 100644
--- a/ext/hash/hash.c
+++ b/ext/hash/hash.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_adler32.c b/ext/hash/hash_adler32.c
index 4575c00c4e..af5ff82de0 100644
--- a/ext/hash/hash_adler32.c
+++ b/ext/hash/hash_adler32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_crc32.c b/ext/hash/hash_crc32.c
index 9be5b4bd40..7e748df559 100644
--- a/ext/hash/hash_crc32.c
+++ b/ext/hash/hash_crc32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_fnv.c b/ext/hash/hash_fnv.c
index f96946d824..1c92478259 100644
--- a/ext/hash/hash_fnv.c
+++ b/ext/hash/hash_fnv.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_gost.c b/ext/hash/hash_gost.c
index 3961c4f2d5..d61075c44f 100644
--- a/ext/hash/hash_gost.c
+++ b/ext/hash/hash_gost.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_haval.c b/ext/hash/hash_haval.c
index 7d8b49670f..32437cecdf 100644
--- a/ext/hash/hash_haval.c
+++ b/ext/hash/hash_haval.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_joaat.c b/ext/hash/hash_joaat.c
index d73938dead..cfeab863de 100644
--- a/ext/hash/hash_joaat.c
+++ b/ext/hash/hash_joaat.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_md.c b/ext/hash/hash_md.c
index 25165eef43..f13f594452 100644
--- a/ext/hash/hash_md.c
+++ b/ext/hash/hash_md.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_ripemd.c b/ext/hash/hash_ripemd.c
index c7c53c603c..16fbd12b18 100644
--- a/ext/hash/hash_ripemd.c
+++ b/ext/hash/hash_ripemd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_sha.c b/ext/hash/hash_sha.c
index 80d9f1f265..a784c102d7 100644
--- a/ext/hash/hash_sha.c
+++ b/ext/hash/hash_sha.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_snefru.c b/ext/hash/hash_snefru.c
index 34101de9d2..2cf37998ad 100644
--- a/ext/hash/hash_snefru.c
+++ b/ext/hash/hash_snefru.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_tiger.c b/ext/hash/hash_tiger.c
index e6e2692cc9..78f932a745 100644
--- a/ext/hash/hash_tiger.c
+++ b/ext/hash/hash_tiger.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/hash_whirlpool.c b/ext/hash/hash_whirlpool.c
index 6fde452bc9..ca41e523d0 100644
--- a/ext/hash/hash_whirlpool.c
+++ b/ext/hash/hash_whirlpool.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash.h b/ext/hash/php_hash.h
index 4bfddbacd9..1d35ae8a46 100644
--- a/ext/hash/php_hash.h
+++ b/ext/hash/php_hash.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_adler32.h b/ext/hash/php_hash_adler32.h
index 789cf18ef7..ca78b38a13 100644
--- a/ext/hash/php_hash_adler32.h
+++ b/ext/hash/php_hash_adler32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_crc32.h b/ext/hash/php_hash_crc32.h
index 111a12f193..cc61243c30 100644
--- a/ext/hash/php_hash_crc32.h
+++ b/ext/hash/php_hash_crc32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_crc32_tables.h b/ext/hash/php_hash_crc32_tables.h
index 8424a23d13..30f5602287 100644
--- a/ext/hash/php_hash_crc32_tables.h
+++ b/ext/hash/php_hash_crc32_tables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_fnv.h b/ext/hash/php_hash_fnv.h
index 3eeb046c34..10023fc618 100644
--- a/ext/hash/php_hash_fnv.h
+++ b/ext/hash/php_hash_fnv.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_gost.h b/ext/hash/php_hash_gost.h
index 6a4af310dc..072be98983 100644
--- a/ext/hash/php_hash_gost.h
+++ b/ext/hash/php_hash_gost.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_haval.h b/ext/hash/php_hash_haval.h
index 0e62f230dd..4a37815daf 100644
--- a/ext/hash/php_hash_haval.h
+++ b/ext/hash/php_hash_haval.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_joaat.h b/ext/hash/php_hash_joaat.h
index d4eacd98f0..494e7eb09a 100644
--- a/ext/hash/php_hash_joaat.h
+++ b/ext/hash/php_hash_joaat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_md.h b/ext/hash/php_hash_md.h
index 10b6f121bb..473abee66c 100644
--- a/ext/hash/php_hash_md.h
+++ b/ext/hash/php_hash_md.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_ripemd.h b/ext/hash/php_hash_ripemd.h
index fde5c0f533..b564b3a17c 100644
--- a/ext/hash/php_hash_ripemd.h
+++ b/ext/hash/php_hash_ripemd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_sha.h b/ext/hash/php_hash_sha.h
index bae7cf3c2f..bd24fb0974 100644
--- a/ext/hash/php_hash_sha.h
+++ b/ext/hash/php_hash_sha.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_snefru.h b/ext/hash/php_hash_snefru.h
index 87e3c53019..214edb1982 100644
--- a/ext/hash/php_hash_snefru.h
+++ b/ext/hash/php_hash_snefru.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_snefru_tables.h b/ext/hash/php_hash_snefru_tables.h
index 1956e9e1e3..ef92453031 100644
--- a/ext/hash/php_hash_snefru_tables.h
+++ b/ext/hash/php_hash_snefru_tables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_tiger.h b/ext/hash/php_hash_tiger.h
index c3428bfe81..fd602d6819 100644
--- a/ext/hash/php_hash_tiger.h
+++ b/ext/hash/php_hash_tiger.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_tiger_tables.h b/ext/hash/php_hash_tiger_tables.h
index a826c9ac66..f3e726f80c 100644
--- a/ext/hash/php_hash_tiger_tables.h
+++ b/ext/hash/php_hash_tiger_tables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_types.h b/ext/hash/php_hash_types.h
index 8793da55d6..d662ebf204 100644
--- a/ext/hash/php_hash_types.h
+++ b/ext/hash/php_hash_types.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_whirlpool.h b/ext/hash/php_hash_whirlpool.h
index f742547c50..d28b1d927c 100644
--- a/ext/hash/php_hash_whirlpool.h
+++ b/ext/hash/php_hash_whirlpool.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/hash/php_hash_whirlpool_tables.h b/ext/hash/php_hash_whirlpool_tables.h
index 819a52a19e..4951636003 100644
--- a/ext/hash/php_hash_whirlpool_tables.h
+++ b/ext/hash/php_hash_whirlpool_tables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/iconv/iconv.c b/ext/iconv/iconv.c
index ba893ea9e6..ea6ac1a1f1 100644
--- a/ext/iconv/iconv.c
+++ b/ext/iconv/iconv.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/iconv/php_iconv.h b/ext/iconv/php_iconv.h
index 04fa6ef534..26e3f3b2a6 100644
--- a/ext/iconv/php_iconv.h
+++ b/ext/iconv/php_iconv.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/imap/php_imap.c b/ext/imap/php_imap.c
index d697fa7911..0e8310a367 100644
--- a/ext/imap/php_imap.c
+++ b/ext/imap/php_imap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/imap/php_imap.h b/ext/imap/php_imap.h
index 52128a643b..a823326cca 100644
--- a/ext/imap/php_imap.h
+++ b/ext/imap/php_imap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/ibase_blobs.c b/ext/interbase/ibase_blobs.c
index 9d9d2f807d..7c27ccf325 100644
--- a/ext/interbase/ibase_blobs.c
+++ b/ext/interbase/ibase_blobs.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/ibase_events.c b/ext/interbase/ibase_events.c
index 3380defd4b..09cdbfa404 100644
--- a/ext/interbase/ibase_events.c
+++ b/ext/interbase/ibase_events.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/ibase_query.c b/ext/interbase/ibase_query.c
index b30d741a82..53eb7a885e 100644
--- a/ext/interbase/ibase_query.c
+++ b/ext/interbase/ibase_query.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/ibase_service.c b/ext/interbase/ibase_service.c
index 956ef04474..bd6d4ad1aa 100644
--- a/ext/interbase/ibase_service.c
+++ b/ext/interbase/ibase_service.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/interbase.c b/ext/interbase/interbase.c
index 132ad35fba..c78c522606 100644
--- a/ext/interbase/interbase.c
+++ b/ext/interbase/interbase.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/php_ibase_includes.h b/ext/interbase/php_ibase_includes.h
index 559be77a44..71990a5e4b 100644
--- a/ext/interbase/php_ibase_includes.h
+++ b/ext/interbase/php_ibase_includes.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/php_ibase_udf.c b/ext/interbase/php_ibase_udf.c
index 7faf314bc0..497a862449 100644
--- a/ext/interbase/php_ibase_udf.c
+++ b/ext/interbase/php_ibase_udf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/interbase/php_interbase.h b/ext/interbase/php_interbase.h
index 149319e577..044896ac43 100644
--- a/ext/interbase/php_interbase.h
+++ b/ext/interbase/php_interbase.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/intl/config.w32 b/ext/intl/config.w32
index bb1dca8124..22cde6bd6d 100644
--- a/ext/intl/config.w32
+++ b/ext/intl/config.w32
@@ -118,6 +118,7 @@ if (PHP_INTL != "no") {
"intl");
ADD_FLAG("LIBS_INTL", "icudt.lib icuin.lib icuio.lib icule.lib iculx.lib");
+ ADD_FLAG("CFLAGS_INTL", "/EHsc");
AC_DEFINE("HAVE_INTL", 1, "Internationalization support enabled");
} else {
WARNING("intl not enabled; libraries and/or headers not found");
diff --git a/ext/json/json.c b/ext/json/json.c
index 782375e371..b0191c38f5 100644
--- a/ext/json/json.c
+++ b/ext/json/json.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -39,7 +39,7 @@ static PHP_FUNCTION(json_last_error_msg);
static const char digits[] = "0123456789abcdef";
-zend_class_entry *php_json_serializable_ce;
+PHP_JSON_API zend_class_entry *php_json_serializable_ce;
ZEND_DECLARE_MODULE_GLOBALS(json)
@@ -695,21 +695,35 @@ PHP_JSON_API void php_json_decode_ex(zval *return_value, char *str, int str_len,
double d;
int type, overflow_info;
long p;
+ char *trim = str;
+ int trim_len = str_len;
+
+ /* Increment trimmed string pointer to strip leading whitespace */
+ /* JSON RFC says to consider as whitespace: space, tab, LF or CR */
+ while (trim_len && (*trim == ' ' || *trim == '\t' || *trim == '\n' || *trim == '\r')) {
+ trim++;
+ trim_len--;
+ }
+
+ /* Decrement trimmed string length to strip trailing whitespace */
+ while (trim_len && (trim[trim_len - 1] == ' ' || trim[trim_len - 1] == '\t' || trim[trim_len - 1] == '\n' || trim[trim_len - 1] == '\r')) {
+ trim_len--;
+ }
RETVAL_NULL();
- if (str_len == 4) {
- if (!strcasecmp(str, "null")) {
+ if (trim_len == 4) {
+ if (!strncasecmp(trim, "null", trim_len)) {
/* We need to explicitly clear the error because its an actual NULL and not an error */
jp->error_code = PHP_JSON_ERROR_NONE;
RETVAL_NULL();
- } else if (!strcasecmp(str, "true")) {
+ } else if (!strncasecmp(trim, "true", trim_len)) {
RETVAL_BOOL(1);
}
- } else if (str_len == 5 && !strcasecmp(str, "false")) {
+ } else if (trim_len == 5 && !strncasecmp(trim, "false", trim_len)) {
RETVAL_BOOL(0);
}
- if ((type = is_numeric_string_ex(str, str_len, &p, &d, 0, &overflow_info)) != 0) {
+ if ((type = is_numeric_string_ex(trim, trim_len, &p, &d, 0, &overflow_info)) != 0) {
if (type == IS_LONG) {
RETVAL_LONG(p);
} else if (type == IS_DOUBLE) {
@@ -722,10 +736,10 @@ PHP_JSON_API void php_json_decode_ex(zval *return_value, char *str, int str_len,
int i;
zend_bool is_float = 0;
- for (i = (str[0] == '-' ? 1 : 0); i < str_len; i++) {
+ for (i = (trim[0] == '-' ? 1 : 0); i < trim_len; i++) {
/* Not using isdigit() because it's locale specific,
* but we expect JSON input to always be UTF-8. */
- if (str[i] < '0' || str[i] > '9') {
+ if (trim[i] < '0' || trim[i] > '9') {
is_float = 1;
break;
}
@@ -734,7 +748,7 @@ PHP_JSON_API void php_json_decode_ex(zval *return_value, char *str, int str_len,
if (is_float) {
RETVAL_DOUBLE(d);
} else {
- RETVAL_STRINGL(str, str_len, 1);
+ RETVAL_STRINGL(trim, trim_len, 1);
}
} else {
RETVAL_DOUBLE(d);
diff --git a/ext/json/php_json.h b/ext/json/php_json.h
index ec707ce346..e00de6a27b 100644
--- a/ext/json/php_json.h
+++ b/ext/json/php_json.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -51,7 +51,7 @@ ZEND_END_MODULE_GLOBALS(json)
PHP_JSON_API void php_json_encode(smart_str *buf, zval *val, int options TSRMLS_DC);
PHP_JSON_API void php_json_decode_ex(zval *return_value, char *str, int str_len, int options, long depth TSRMLS_DC);
-extern zend_class_entry *php_json_serializable_ce;
+extern PHP_JSON_API zend_class_entry *php_json_serializable_ce;
/* json_encode() options */
diff --git a/ext/json/tests/bug64874_part1.phpt b/ext/json/tests/bug64874_part1.phpt
new file mode 100644
index 0000000000..6b79b8dc04
--- /dev/null
+++ b/ext/json/tests/bug64874_part1.phpt
@@ -0,0 +1,117 @@
+--TEST--
+Whitespace part of bug #64874 ("json_decode handles whitespace and case-sensitivity incorrectly")
+--SKIPIF--
+<?php if (!extension_loaded("json")) print "skip"; ?>
+--FILE--
+<?php
+function decode($json) {
+ var_dump(json_decode($json));
+ var_dump(json_last_error() !== 0);
+ echo "\n";
+}
+
+// Leading whitespace should be ignored
+decode(" true");
+decode("\ttrue");
+decode("\ntrue");
+decode("\rtrue");
+
+// So should trailing whitespace
+decode("true ");
+decode("true\t");
+decode("true\n");
+decode("true\r");
+
+// And so should the combination of both
+decode(" true ");
+decode(" true\t");
+decode(" true\n");
+decode(" true\r");
+decode("\ttrue ");
+decode("\ttrue\t");
+decode("\ttrue\n");
+decode("\ttrue\r");
+decode("\ntrue ");
+decode("\ntrue\t");
+decode("\ntrue\n");
+decode("\ntrue\r");
+decode("\rtrue ");
+decode("\rtrue\t");
+decode("\rtrue\n");
+decode("\rtrue\r");
+
+echo "Done\n";
+--EXPECT--
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+bool(true)
+bool(false)
+
+Done
diff --git a/ext/ldap/ldap.c b/ext/ldap/ldap.c
index e95f898c15..10daa82f36 100644
--- a/ext/ldap/ldap.c
+++ b/ext/ldap/ldap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -152,6 +152,15 @@ PHP_MINIT_FUNCTION(ldap)
REGISTER_LONG_CONSTANT("LDAP_DEREF_FINDING", LDAP_DEREF_FINDING, CONST_PERSISTENT | CONST_CS);
REGISTER_LONG_CONSTANT("LDAP_DEREF_ALWAYS", LDAP_DEREF_ALWAYS, CONST_PERSISTENT | CONST_CS);
+ /* Constants to be used with ldap_modify_batch() */
+ REGISTER_LONG_CONSTANT("LDAP_MODIFY_BATCH_ADD", LDAP_MODIFY_BATCH_ADD, CONST_PERSISTENT | CONST_CS);
+ REGISTER_LONG_CONSTANT("LDAP_MODIFY_BATCH_REMOVE", LDAP_MODIFY_BATCH_REMOVE, CONST_PERSISTENT | CONST_CS);
+ REGISTER_LONG_CONSTANT("LDAP_MODIFY_BATCH_REMOVE_ALL", LDAP_MODIFY_BATCH_REMOVE_ALL, CONST_PERSISTENT | CONST_CS);
+ REGISTER_LONG_CONSTANT("LDAP_MODIFY_BATCH_REPLACE", LDAP_MODIFY_BATCH_REPLACE, CONST_PERSISTENT | CONST_CS);
+ REGISTER_STRING_CONSTANT("LDAP_MODIFY_BATCH_ATTRIB", LDAP_MODIFY_BATCH_ATTRIB, CONST_PERSISTENT | CONST_CS);
+ REGISTER_STRING_CONSTANT("LDAP_MODIFY_BATCH_MODTYPE", LDAP_MODIFY_BATCH_MODTYPE, CONST_PERSISTENT | CONST_CS);
+ REGISTER_STRING_CONSTANT("LDAP_MODIFY_BATCH_VALUES", LDAP_MODIFY_BATCH_VALUES, CONST_PERSISTENT | CONST_CS);
+
#if (LDAP_API_VERSION > 2000) || HAVE_NSLDAP || HAVE_ORALDAP
/* LDAP options */
REGISTER_LONG_CONSTANT("LDAP_OPT_DEREF", LDAP_OPT_DEREF, CONST_PERSISTENT | CONST_CS);
@@ -1432,6 +1441,355 @@ PHP_FUNCTION(ldap_delete)
}
/* }}} */
+/* {{{ _ldap_str_equal_to_const
+ */
+static int _ldap_str_equal_to_const(const char *str, uint str_len, const char *cstr)
+{
+ int i;
+
+ if (strlen(cstr) != str_len)
+ return 0;
+
+ for (i = 0; i < str_len; ++i) {
+ if (str[i] != cstr[i]) {
+ return 0;
+ }
+ }
+
+ return 1;
+}
+/* }}} */
+
+/* {{{ _ldap_strlen_max
+ */
+static int _ldap_strlen_max(const char *str, uint max_len)
+{
+ int i;
+
+ for (i = 0; i < max_len; ++i) {
+ if (str[i] == '\0') {
+ return i;
+ }
+ }
+
+ return max_len;
+}
+/* }}} */
+
+/* {{{ _ldap_hash_fetch
+ */
+static void _ldap_hash_fetch(zval *hashTbl, const char *key, zval **out)
+{
+ zval **fetched;
+ if (zend_hash_find(Z_ARRVAL_P(hashTbl), key, strlen(key)+1, (void **) &fetched) == SUCCESS) {
+ *out = *fetched;
+ }
+ else {
+ *out = NULL;
+ }
+}
+/* }}} */
+
+/* {{{ proto bool ldap_modify_batch(resource link, string dn, array modifs)
+ Perform multiple modifications as part of one operation */
+PHP_FUNCTION(ldap_modify_batch)
+{
+ ldap_linkdata *ld;
+ zval *link, *mods, *mod, *modinfo, *modval;
+ zval *attrib, *modtype, *vals;
+ zval **fetched;
+ char *dn;
+ int dn_len;
+ int i, j, k;
+ int num_mods, num_modprops, num_modvals;
+ LDAPMod **ldap_mods;
+ uint oper;
+
+ /*
+ $mods = array(
+ array(
+ "attrib" => "unicodePwd",
+ "modtype" => LDAP_MODIFY_BATCH_REMOVE,
+ "values" => array($oldpw)
+ ),
+ array(
+ "attrib" => "unicodePwd",
+ "modtype" => LDAP_MODIFY_BATCH_ADD,
+ "values" => array($newpw)
+ ),
+ array(
+ "attrib" => "userPrincipalName",
+ "modtype" => LDAP_MODIFY_BATCH_REPLACE,
+ "values" => array("janitor@corp.contoso.com")
+ ),
+ array(
+ "attrib" => "userCert",
+ "modtype" => LDAP_MODIFY_BATCH_REMOVE_ALL
+ )
+ );
+ */
+
+ if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rsa", &link, &dn, &dn_len, &mods) != SUCCESS) {
+ return;
+ }
+
+ ZEND_FETCH_RESOURCE(ld, ldap_linkdata *, &link, -1, "ldap link", le_link);
+
+ /* perform validation */
+ {
+ char *modkey;
+ uint modkeylen;
+ long modtype;
+
+ /* to store the wrongly-typed keys */
+ ulong tmpUlong;
+
+ /* make sure the DN contains no NUL bytes */
+ if (_ldap_strlen_max(dn, dn_len) != dn_len) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "DN must not contain NUL bytes");
+ RETURN_FALSE;
+ }
+
+ /* make sure the top level is a normal array */
+ zend_hash_internal_pointer_reset(Z_ARRVAL_P(mods));
+ if (zend_hash_get_current_key_type(Z_ARRVAL_P(mods)) != HASH_KEY_IS_LONG) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Modifications array must not be string-indexed");
+ RETURN_FALSE;
+ }
+
+ num_mods = zend_hash_num_elements(Z_ARRVAL_P(mods));
+
+ for (i = 0; i < num_mods; i++) {
+ /* is the numbering consecutive? */
+ if (zend_hash_index_find(Z_ARRVAL_P(mods), i, (void **) &fetched) != SUCCESS) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Modifications array must have consecutive indices 0, 1, ...");
+ RETURN_FALSE;
+ }
+ mod = *fetched;
+
+ /* is it an array? */
+ if (Z_TYPE_P(mod) != IS_ARRAY) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Each entry of modifications array must be an array itself");
+ RETURN_FALSE;
+ }
+
+ /* for the modification hashtable... */
+ zend_hash_internal_pointer_reset(Z_ARRVAL_P(mod));
+ num_modprops = zend_hash_num_elements(Z_ARRVAL_P(mod));
+
+ for (j = 0; j < num_modprops; j++) {
+ /* are the keys strings? */
+ if (zend_hash_get_current_key_ex(Z_ARRVAL_P(mod), &modkey, &modkeylen, &tmpUlong, 0, NULL) != HASH_KEY_IS_STRING) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Each entry of modifications array must be string-indexed");
+ RETURN_FALSE;
+ }
+
+ /* modkeylen includes the terminating NUL byte; remove that */
+ --modkeylen;
+
+ /* is this a valid entry? */
+ if (
+ !_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_ATTRIB) &&
+ !_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_MODTYPE) &&
+ !_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_VALUES)
+ ) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "The only allowed keys in entries of the modifications array are '" LDAP_MODIFY_BATCH_ATTRIB "', '" LDAP_MODIFY_BATCH_MODTYPE "' and '" LDAP_MODIFY_BATCH_VALUES "'");
+ RETURN_FALSE;
+ }
+
+ zend_hash_get_current_data(Z_ARRVAL_P(mod), (void **) &fetched);
+ modinfo = *fetched;
+
+ /* does the value type match the key? */
+ if (_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_ATTRIB)) {
+ if (Z_TYPE_P(modinfo) != IS_STRING) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_ATTRIB "' value must be a string");
+ RETURN_FALSE;
+ }
+
+ if (Z_STRLEN_P(modinfo) != _ldap_strlen_max(Z_STRVAL_P(modinfo), Z_STRLEN_P(modinfo))) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_ATTRIB "' value must not contain NUL bytes");
+ RETURN_FALSE;
+ }
+ }
+ else if (_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_MODTYPE)) {
+ if (Z_TYPE_P(modinfo) != IS_LONG) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_MODTYPE "' value must be a long");
+ RETURN_FALSE;
+ }
+
+ /* is the value in range? */
+ modtype = Z_LVAL_P(modinfo);
+ if (
+ modtype != LDAP_MODIFY_BATCH_ADD &&
+ modtype != LDAP_MODIFY_BATCH_REMOVE &&
+ modtype != LDAP_MODIFY_BATCH_REPLACE &&
+ modtype != LDAP_MODIFY_BATCH_REMOVE_ALL
+ ) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "The '" LDAP_MODIFY_BATCH_MODTYPE "' value must match one of the LDAP_MODIFY_BATCH_* constants");
+ RETURN_FALSE;
+ }
+
+ /* if it's REMOVE_ALL, there must not be a values array; otherwise, there must */
+ if (modtype == LDAP_MODIFY_BATCH_REMOVE_ALL) {
+ if (zend_hash_exists(Z_ARRVAL_P(mod), LDAP_MODIFY_BATCH_VALUES, strlen(LDAP_MODIFY_BATCH_VALUES) + 1)) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "If '" LDAP_MODIFY_BATCH_MODTYPE "' is LDAP_MODIFY_BATCH_REMOVE_ALL, a '" LDAP_MODIFY_BATCH_VALUES "' array must not be provided");
+ RETURN_FALSE;
+ }
+ }
+ else {
+ if (!zend_hash_exists(Z_ARRVAL_P(mod), LDAP_MODIFY_BATCH_VALUES, strlen(LDAP_MODIFY_BATCH_VALUES) + 1)) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "If '" LDAP_MODIFY_BATCH_MODTYPE "' is not LDAP_MODIFY_BATCH_REMOVE_ALL, a '" LDAP_MODIFY_BATCH_VALUES "' array must be provided");
+ RETURN_FALSE;
+ }
+ }
+ }
+ else if (_ldap_str_equal_to_const(modkey, modkeylen, LDAP_MODIFY_BATCH_VALUES)) {
+ if (Z_TYPE_P(modinfo) != IS_ARRAY) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_VALUES "' value must be an array");
+ RETURN_FALSE;
+ }
+
+ /* is the array not empty? */
+ zend_hash_internal_pointer_reset(Z_ARRVAL_P(modinfo));
+ num_modvals = zend_hash_num_elements(Z_ARRVAL_P(modinfo));
+ if (num_modvals == 0) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_VALUES "' array must have at least one element");
+ RETURN_FALSE;
+ }
+
+ /* are its keys integers? */
+ if (zend_hash_get_current_key_type(Z_ARRVAL_P(modinfo)) != HASH_KEY_IS_LONG) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_VALUES "' array must not be string-indexed");
+ RETURN_FALSE;
+ }
+
+ /* are the keys consecutive? */
+ for (k = 0; k < num_modvals; k++) {
+ if (zend_hash_index_find(Z_ARRVAL_P(modinfo), k, (void **) &fetched) != SUCCESS) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "A '" LDAP_MODIFY_BATCH_VALUES "' array must have consecutive indices 0, 1, ...");
+ RETURN_FALSE;
+ }
+ modval = *fetched;
+
+ /* is the data element a string? */
+ if (Z_TYPE_P(modval) != IS_STRING) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Each element of a '" LDAP_MODIFY_BATCH_VALUES "' array must be a string");
+ RETURN_FALSE;
+ }
+ }
+ }
+
+ zend_hash_move_forward(Z_ARRVAL_P(mod));
+ }
+ }
+ }
+ /* validation was successful */
+
+ /* allocate array of modifications */
+ ldap_mods = safe_emalloc((num_mods+1), sizeof(LDAPMod *), 0);
+
+ /* for each modification */
+ for (i = 0; i < num_mods; i++) {
+ /* allocate the modification struct */
+ ldap_mods[i] = safe_emalloc(1, sizeof(LDAPMod), 0);
+
+ /* fetch the relevant data */
+ zend_hash_index_find(Z_ARRVAL_P(mods), i, (void **) &fetched);
+ mod = *fetched;
+
+ _ldap_hash_fetch(mod, LDAP_MODIFY_BATCH_ATTRIB, &attrib);
+ _ldap_hash_fetch(mod, LDAP_MODIFY_BATCH_MODTYPE, &modtype);
+ _ldap_hash_fetch(mod, LDAP_MODIFY_BATCH_VALUES, &vals);
+
+ /* map the modification type */
+ switch (Z_LVAL_P(modtype)) {
+ case LDAP_MODIFY_BATCH_ADD:
+ oper = LDAP_MOD_ADD;
+ break;
+ case LDAP_MODIFY_BATCH_REMOVE:
+ case LDAP_MODIFY_BATCH_REMOVE_ALL:
+ oper = LDAP_MOD_DELETE;
+ break;
+ case LDAP_MODIFY_BATCH_REPLACE:
+ oper = LDAP_MOD_REPLACE;
+ break;
+ default:
+ php_error_docref(NULL TSRMLS_CC, E_ERROR, "Unknown and uncaught modification type.");
+ RETURN_FALSE;
+ }
+
+ /* fill in the basic info */
+ ldap_mods[i]->mod_op = oper | LDAP_MOD_BVALUES;
+ ldap_mods[i]->mod_type = estrndup(Z_STRVAL_P(attrib), Z_STRLEN_P(attrib));
+
+ if (Z_LVAL_P(modtype) == LDAP_MODIFY_BATCH_REMOVE_ALL) {
+ /* no values */
+ ldap_mods[i]->mod_bvalues = NULL;
+ }
+ else {
+ /* allocate space for the values as part of this modification */
+ num_modvals = zend_hash_num_elements(Z_ARRVAL_P(vals));
+ ldap_mods[i]->mod_bvalues = safe_emalloc((num_modvals+1), sizeof(struct berval *), 0);
+
+ /* for each value */
+ for (j = 0; j < num_modvals; j++) {
+ /* fetch it */
+ zend_hash_index_find(Z_ARRVAL_P(vals), j, (void **) &fetched);
+ modval = *fetched;
+
+ /* allocate the data struct */
+ ldap_mods[i]->mod_bvalues[j] = safe_emalloc(1, sizeof(struct berval), 0);
+
+ /* fill it */
+ ldap_mods[i]->mod_bvalues[j]->bv_len = Z_STRLEN_P(modval);
+ ldap_mods[i]->mod_bvalues[j]->bv_val = estrndup(Z_STRVAL_P(modval), Z_STRLEN_P(modval));
+ }
+
+ /* NULL-terminate values */
+ ldap_mods[i]->mod_bvalues[num_modvals] = NULL;
+ }
+ }
+
+ /* NULL-terminate modifications */
+ ldap_mods[num_mods] = NULL;
+
+ /* perform (finally) */
+ if ((i = ldap_modify_ext_s(ld->link, dn, ldap_mods, NULL, NULL)) != LDAP_SUCCESS) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Batch Modify: %s", ldap_err2string(i));
+ RETVAL_FALSE;
+ } else RETVAL_TRUE;
+
+ /* clean up */
+ {
+ for (i = 0; i < num_mods; i++) {
+ /* attribute */
+ efree(ldap_mods[i]->mod_type);
+
+ if (ldap_mods[i]->mod_bvalues != NULL) {
+ /* each BER value */
+ for (j = 0; ldap_mods[i]->mod_bvalues[j] != NULL; j++) {
+ /* free the data bytes */
+ efree(ldap_mods[i]->mod_bvalues[j]->bv_val);
+
+ /* free the bvalue struct */
+ efree(ldap_mods[i]->mod_bvalues[j]);
+ }
+
+ /* the BER value array */
+ efree(ldap_mods[i]->mod_bvalues);
+ }
+
+ /* the modification */
+ efree(ldap_mods[i]);
+ }
+
+ /* the modifications array */
+ efree(ldap_mods);
+ }
+}
+/* }}} */
+
/* {{{ proto int ldap_errno(resource link)
Get the current ldap error number */
PHP_FUNCTION(ldap_errno)
@@ -2516,6 +2874,12 @@ ZEND_BEGIN_ARG_INFO_EX(arginfo_ldap_modify, 0, 0, 3)
ZEND_ARG_INFO(0, entry)
ZEND_END_ARG_INFO()
+ZEND_BEGIN_ARG_INFO_EX(arginfo_ldap_modify_batch, 0, 0, 3)
+ ZEND_ARG_INFO(0, link_identifier)
+ ZEND_ARG_INFO(0, dn)
+ ZEND_ARG_ARRAY_INFO(0, modifications_info, 0)
+ZEND_END_ARG_INFO()
+
ZEND_BEGIN_ARG_INFO_EX(arginfo_ldap_mod_add, 0, 0, 3)
ZEND_ARG_INFO(0, link_identifier)
ZEND_ARG_INFO(0, dn)
@@ -2669,6 +3033,7 @@ const zend_function_entry ldap_functions[] = {
PHP_FE(ldap_dn2ufn, arginfo_ldap_dn2ufn)
PHP_FE(ldap_add, arginfo_ldap_add)
PHP_FE(ldap_delete, arginfo_ldap_delete)
+ PHP_FE(ldap_modify_batch, arginfo_ldap_modify_batch)
PHP_FALIAS(ldap_modify, ldap_mod_replace, arginfo_ldap_modify)
/* additional functions for attribute based modifications, Gerrit Thomson */
diff --git a/ext/ldap/php_ldap.h b/ext/ldap/php_ldap.h
index 2ed8fd822d..bd3731819d 100644
--- a/ext/ldap/php_ldap.h
+++ b/ext/ldap/php_ldap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -50,4 +50,14 @@ ZEND_END_MODULE_GLOBALS(ldap)
#define phpext_ldap_ptr ldap_module_ptr
+/* Constants for ldap_modify_batch */
+#define LDAP_MODIFY_BATCH_ADD 0x01
+#define LDAP_MODIFY_BATCH_REMOVE 0x02
+#define LDAP_MODIFY_BATCH_REMOVE_ALL 0x12
+#define LDAP_MODIFY_BATCH_REPLACE 0x03
+
+#define LDAP_MODIFY_BATCH_ATTRIB "attrib"
+#define LDAP_MODIFY_BATCH_MODTYPE "modtype"
+#define LDAP_MODIFY_BATCH_VALUES "values"
+
#endif /* PHP_LDAP_H */
diff --git a/ext/ldap/tests/ldap_modify_batch_basic.phpt b/ext/ldap/tests/ldap_modify_batch_basic.phpt
new file mode 100644
index 0000000000..4f6705c7e8
--- /dev/null
+++ b/ext/ldap/tests/ldap_modify_batch_basic.phpt
@@ -0,0 +1,109 @@
+--TEST--
+ldap_modify_batch() - Basic batch modify operation
+--CREDITS--
+Patrick Allaert <patrickallaert@php.net>
+Ondřej Hošek <ondra.hosek@gmail.com>
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php require_once('skipifbindfailure.inc'); ?>
+--FILE--
+<?php
+require "connect.inc";
+
+$link = ldap_connect_and_bind($host, $port, $user, $passwd, $protocol_version);
+insert_dummy_data($link);
+
+$mods = array(
+ array(
+ "attrib" => "telephoneNumber",
+ "modtype" => LDAP_MODIFY_BATCH_ADD,
+ "values" => array(
+ "+1 555 5551717"
+ )
+ ),
+ array(
+ "attrib" => "sn",
+ "modtype" => LDAP_MODIFY_BATCH_REPLACE,
+ "values" => array("Brown-Smith")
+ ),
+ array(
+ "attrib" => "description",
+ "modtype" => LDAP_MODIFY_BATCH_REMOVE_ALL
+ )
+);
+
+var_dump(
+ ldap_modify_batch($link, "cn=userA,dc=my-domain,dc=com", $mods),
+ ldap_get_entries($link, ldap_search($link, "dc=my-domain,dc=com", "(sn=Brown-Smith)"))
+);
+?>
+===DONE===
+--CLEAN--
+<?php
+require "connect.inc";
+
+$link = ldap_connect_and_bind($host, $port, $user, $passwd, $protocol_version);
+
+remove_dummy_data($link);
+?>
+--EXPECT--
+bool(true)
+array(2) {
+ ["count"]=>
+ int(1)
+ [0]=>
+ array(12) {
+ ["objectclass"]=>
+ array(2) {
+ ["count"]=>
+ int(1)
+ [0]=>
+ string(6) "person"
+ }
+ [0]=>
+ string(11) "objectclass"
+ ["cn"]=>
+ array(2) {
+ ["count"]=>
+ int(1)
+ [0]=>
+ string(5) "userA"
+ }
+ [1]=>
+ string(2) "cn"
+ ["userpassword"]=>
+ array(2) {
+ ["count"]=>
+ int(1)
+ [0]=>
+ string(4) "oops"
+ }
+ [2]=>
+ string(12) "userpassword"
+ ["telephonenumber"]=>
+ array(3) {
+ ["count"]=>
+ int(2)
+ [0]=>
+ string(14) "xx-xx-xx-xx-xx"
+ [1]=>
+ string(14) "+1 555 5551717"
+ }
+ [3]=>
+ string(15) "telephonenumber"
+ ["sn"]=>
+ array(2) {
+ ["count"]=>
+ int(1)
+ [0]=>
+ string(11) "Brown-Smith"
+ }
+ [4]=>
+ string(2) "sn"
+ ["count"]=>
+ int(5)
+ ["dn"]=>
+ string(28) "cn=userA,dc=my-domain,dc=com"
+ }
+}
+===DONE===
diff --git a/ext/ldap/tests/ldap_modify_batch_error.phpt b/ext/ldap/tests/ldap_modify_batch_error.phpt
new file mode 100644
index 0000000000..687c371c4d
--- /dev/null
+++ b/ext/ldap/tests/ldap_modify_batch_error.phpt
@@ -0,0 +1,104 @@
+--TEST--
+ldap_modify_batch() - Batch modify operations that should fail
+--CREDITS--
+Patrick Allaert <patrickallaert@php.net>
+Ondřej Hošek <ondra.hosek@gmail.com>
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php require_once('skipifbindfailure.inc'); ?>
+--FILE--
+<?php
+require "connect.inc";
+
+$link = ldap_connect_and_bind($host, $port, $user, $passwd, $protocol_version);
+
+$addGivenName = array(
+ array(
+ "attrib" => "givenName",
+ "modtype" => LDAP_MODIFY_BATCH_ADD,
+ "values" => array("Jack")
+ )
+);
+
+// Too few parameters
+var_dump(ldap_modify_batch());
+var_dump(ldap_modify_batch($link));
+var_dump(ldap_modify_batch($link, "dc=my-domain,dc=com"));
+
+// Too many parameters
+var_dump(ldap_modify_batch($link, "dc=my-domain,dc=com", $addGivenName, "Invalid additional parameter"));
+
+// DN not found
+var_dump(ldap_modify_batch($link, "dc=my-domain,dc=com", $addGivenName));
+
+// Invalid DN
+var_dump(ldap_modify_batch($link, "weirdAttribute=val", $addGivenName));
+
+// prepare
+$entry = array(
+ "objectClass" => array(
+ "top",
+ "dcObject",
+ "organization"),
+ "dc" => "my-domain",
+ "o" => "my-domain",
+);
+
+ldap_add($link, "dc=my-domain,dc=com", $entry);
+
+// invalid domain
+$mods = array(
+ array(
+ "attrib" => "dc",
+ "modtype" => LDAP_MODIFY_BATCH_REPLACE,
+ "values" => array("Wrong Domain")
+ )
+);
+
+var_dump(ldap_modify_batch($link, "dc=my-domain,dc=com", $mods));
+
+// invalid attribute
+$mods = array(
+ array(
+ "attrib" => "weirdAttribute",
+ "modtype" => LDAP_MODIFY_BATCH_ADD,
+ "values" => array("weirdVal", "anotherWeirdval")
+ )
+);
+
+var_dump(ldap_modify_batch($link, "dc=my-domain,dc=com", $mods));
+?>
+===DONE===
+--CLEAN--
+<?php
+require "connect.inc";
+
+$link = ldap_connect_and_bind($host, $port, $user, $passwd, $protocol_version);
+
+ldap_delete($link, "dc=my-domain,dc=com");
+?>
+--EXPECTF--
+Warning: ldap_modify_batch() expects exactly 3 parameters, 0 given in %s on line %d
+NULL
+
+Warning: ldap_modify_batch() expects exactly 3 parameters, 1 given in %s on line %d
+NULL
+
+Warning: ldap_modify_batch() expects exactly 3 parameters, 2 given in %s on line %d
+NULL
+
+Warning: ldap_modify_batch() expects exactly 3 parameters, 4 given in %s on line %d
+NULL
+
+Warning: ldap_modify_batch(): Batch Modify: No such object in %s on line %d
+bool(false)
+
+Warning: ldap_modify_batch(): Batch Modify: Invalid DN syntax in %s on line %d
+bool(false)
+
+Warning: ldap_modify_batch(): Batch Modify: Naming violation in %s on line %d
+bool(false)
+
+Warning: ldap_modify_batch(): Batch Modify: Undefined attribute type in %s on line %d
+bool(false)
+===DONE===
diff --git a/ext/libxml/libxml.c b/ext/libxml/libxml.c
index 354cb548a7..2438463ebb 100644
--- a/ext/libxml/libxml.c
+++ b/ext/libxml/libxml.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -88,7 +88,7 @@ static PHP_MINIT_FUNCTION(libxml);
static PHP_RINIT_FUNCTION(libxml);
static PHP_MSHUTDOWN_FUNCTION(libxml);
static PHP_MINFO_FUNCTION(libxml);
-static int php_libxml_post_deactivate();
+static int php_libxml_post_deactivate(void);
/* }}} */
@@ -875,7 +875,7 @@ static PHP_MSHUTDOWN_FUNCTION(libxml)
return SUCCESS;
}
-static int php_libxml_post_deactivate()
+static int php_libxml_post_deactivate(void)
{
TSRMLS_FETCH();
/* reset libxml generic error handling */
diff --git a/ext/libxml/php_libxml.h b/ext/libxml/php_libxml.h
index 04f8b4933b..901e321aac 100644
--- a/ext/libxml/php_libxml.h
+++ b/ext/libxml/php_libxml.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/mb_gpc.c b/ext/mbstring/mb_gpc.c
index 5ecc8f365e..8924b065c8 100644
--- a/ext/mbstring/mb_gpc.c
+++ b/ext/mbstring/mb_gpc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/mbstring.c b/ext/mbstring/mbstring.c
index 4e430b6ea2..7ac0b5349b 100644
--- a/ext/mbstring/mbstring.c
+++ b/ext/mbstring/mbstring.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/mbstring.h b/ext/mbstring/mbstring.h
index 70f9f48fb0..8e6310f75f 100644
--- a/ext/mbstring/mbstring.h
+++ b/ext/mbstring/mbstring.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/php_mbregex.c b/ext/mbstring/php_mbregex.c
index 607921ebb6..4b1b924d06 100644
--- a/ext/mbstring/php_mbregex.c
+++ b/ext/mbstring/php_mbregex.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/php_mbregex.h b/ext/mbstring/php_mbregex.h
index 276220ac11..3d2e2b8e46 100644
--- a/ext/mbstring/php_mbregex.h
+++ b/ext/mbstring/php_mbregex.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/php_unicode.c b/ext/mbstring/php_unicode.c
index 9380045e6f..a1db6819e9 100644
--- a/ext/mbstring/php_unicode.c
+++ b/ext/mbstring/php_unicode.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/php_unicode.h b/ext/mbstring/php_unicode.h
index b1e395cac1..5932b8d2da 100644
--- a/ext/mbstring/php_unicode.h
+++ b/ext/mbstring/php_unicode.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mbstring/tests/zend_multibyte-01.phpt b/ext/mbstring/tests/zend_multibyte-01.phpt
index d96e0f07d3..f2403abcac 100644
--- a/ext/mbstring/tests/zend_multibyte-01.phpt
+++ b/ext/mbstring/tests/zend_multibyte-01.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (1)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=Shift_JIS
+zend.multibyte=On
+zend.script_encoding=Shift_JIS
mbstring.internal_encoding=Shift_JIS
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-02.phpt b/ext/mbstring/tests/zend_multibyte-02.phpt
index c94dee5a28..ebc10b48be 100644
--- a/ext/mbstring/tests/zend_multibyte-02.phpt
+++ b/ext/mbstring/tests/zend_multibyte-02.phpt
@@ -1,18 +1,14 @@
--TEST--
zend multibyte (2)
---SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--XFAIL--
+https://bugs.php.net/bug.php?id=66582
--INI--
-mbstring.script_encoding=UTF-8
+zend.multibyte=On
+zend.script_encoding=UTF-8
mbstring.internal_encoding=CP932
--FILE--
<?php
var_dump(bin2hex("テスト"));
?>
---EXPECT--
-string(12) "836583588367"
+--EXPECTF--
+php: Zend/zend_language_scanner.l:%d: encoding_filter_script_to_internal: Assertion `internal_encoding && zend_multibyte_check_lexer_compatibility(internal_encoding)' failed.
diff --git a/ext/mbstring/tests/zend_multibyte-03.phpt b/ext/mbstring/tests/zend_multibyte-03.phpt
index 46a262c32e..99c58bce70 100644
--- a/ext/mbstring/tests/zend_multibyte-03.phpt
+++ b/ext/mbstring/tests/zend_multibyte-03.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (3)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=UTF-8
+zend.multibyte=On
+zend.script_encoding=UTF-8
mbstring.internal_encoding=EUC-JP
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-04.phpt b/ext/mbstring/tests/zend_multibyte-04.phpt
index f1295b6afe..e7fdf81cdd 100644
--- a/ext/mbstring/tests/zend_multibyte-04.phpt
+++ b/ext/mbstring/tests/zend_multibyte-04.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (4)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=CP932
+zend.multibyte=On
+zend.script_encoding=CP932
mbstring.internal_encoding=UTF-8
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-05.phpt b/ext/mbstring/tests/zend_multibyte-05.phpt
index 0a01c231fc..3dd56d043d 100644
--- a/ext/mbstring/tests/zend_multibyte-05.phpt
+++ b/ext/mbstring/tests/zend_multibyte-05.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (5)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=EUC-JP
+zend.multibyte=On
+zend.script_encoding=EUC-JP
mbstring.internal_encoding=UTF-8
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-06.phpt b/ext/mbstring/tests/zend_multibyte-06.phpt
index 9acd6a951d..e0b4ead545 100644
--- a/ext/mbstring/tests/zend_multibyte-06.phpt
+++ b/ext/mbstring/tests/zend_multibyte-06.phpt
@@ -1,19 +1,15 @@
--TEST--
zend multibyte (6)
---SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--XFAIL--
+https://bugs.php.net/bug.php?id=66582
--INI--
-mbstring.script_encoding=EUC-JP
+zend.multibyte=On
+zend.script_encoding=EUC-JP
mbstring.internal_encoding=CP932
--FILE--
<?php
declare(encoding="UTF-8");
var_dump(bin2hex("テスト"));
?>
---EXPECT--
-string(12) "836583588367"
+--EXPECTF--
+php: Zend/zend_language_scanner.l:%d: encoding_filter_script_to_internal: Assertion `internal_encoding && zend_multibyte_check_lexer_compatibility(internal_encoding)' failed.
diff --git a/ext/mbstring/tests/zend_multibyte-07.phpt b/ext/mbstring/tests/zend_multibyte-07.phpt
index 30305f5fdf..08db1d0f70 100644
--- a/ext/mbstring/tests/zend_multibyte-07.phpt
+++ b/ext/mbstring/tests/zend_multibyte-07.phpt
@@ -1,14 +1,11 @@
--TEST--
zend multibyte (7)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--XFAIL--
+https://bugs.php.net/bug.php?id=66582
--INI--
-mbstring.script_encoding=ISO-8859-1
+zend.multibyte=On
+zend.script_encoding=ISO-8859-1
mbstring.internal_encoding=EUC-JP
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-08.phpt b/ext/mbstring/tests/zend_multibyte-08.phpt
index ab27461355..488e2a00ca 100644
--- a/ext/mbstring/tests/zend_multibyte-08.phpt
+++ b/ext/mbstring/tests/zend_multibyte-08.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (8)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=ISO-8859-1
+zend.multibyte=On
+zend.script_encoding=ISO-8859-1
mbstring.internal_encoding=UTF-8
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-09.phpt b/ext/mbstring/tests/zend_multibyte-09.phpt
index 79ee435aa0..8ad00b4e1e 100644
--- a/ext/mbstring/tests/zend_multibyte-09.phpt
+++ b/ext/mbstring/tests/zend_multibyte-09.phpt
@@ -1,14 +1,11 @@
--TEST--
zend multibyte (9)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--XFAIL--
+https://bugs.php.net/bug.php?id=66582
--INI--
-mbstring.script_encoding=cp1251
+zend.multibyte=On
+zend.script_encoding=cp1251
mbstring.internal_encoding=UTF-8
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-10.phpt b/ext/mbstring/tests/zend_multibyte-10.phpt
index 435c339752..139d973b95 100644
--- a/ext/mbstring/tests/zend_multibyte-10.phpt
+++ b/ext/mbstring/tests/zend_multibyte-10.phpt
@@ -1,12 +1,8 @@
--TEST--
zend multibyte (10)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--INI--
+zend.multibyte=1
--FILE--
<?php
declare(encoding="ISO-8859-15");
diff --git a/ext/mbstring/tests/zend_multibyte-11.phpt b/ext/mbstring/tests/zend_multibyte-11.phpt
index b79e4339ba..c6e45fa5cd 100644
--- a/ext/mbstring/tests/zend_multibyte-11.phpt
+++ b/ext/mbstring/tests/zend_multibyte-11.phpt
@@ -1,12 +1,8 @@
--TEST--
zend multibyte (11)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--INI--
+zend.multibyte=1
--FILE--
<?php
declare(encoding="ISO-8859-15") {
diff --git a/ext/mbstring/tests/zend_multibyte-12.phpt b/ext/mbstring/tests/zend_multibyte-12.phpt
index e1c8ce52d1..90968e8820 100644
--- a/ext/mbstring/tests/zend_multibyte-12.phpt
+++ b/ext/mbstring/tests/zend_multibyte-12.phpt
@@ -1,12 +1,8 @@
--TEST--
zend multibyte (12)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
+--INI--
+zend.multibyte=1
--FILE--
<?php
declare(encoding="ISO-8859-15");
diff --git a/ext/mbstring/tests/zend_multibyte-13.phpt b/ext/mbstring/tests/zend_multibyte-13.phpt
index e601a6ceed..6eaef985f5 100644
--- a/ext/mbstring/tests/zend_multibyte-13.phpt
+++ b/ext/mbstring/tests/zend_multibyte-13.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (13)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=UTF-8
+zend.multibyte=On
+zend.script_encoding=UTF-8
mbstring.internal_encoding=ISO-8859-1
--FILE--
<?php
diff --git a/ext/mbstring/tests/zend_multibyte-14.phpt b/ext/mbstring/tests/zend_multibyte-14.phpt
index 04bc409fb6..98c2f87e25 100644
--- a/ext/mbstring/tests/zend_multibyte-14.phpt
+++ b/ext/mbstring/tests/zend_multibyte-14.phpt
@@ -1,14 +1,9 @@
--TEST--
zend multibyte (14)
--SKIPIF--
-<?php
-ini_set("mbstring.script_encoding","SJIS");
-if (ini_set("mbstring.script_encoding","SJIS") != "SJIS") {
- die("skip zend-multibyte is not available");
-}
-?>
--INI--
-mbstring.script_encoding=UTF-8
+zend.multibyte=On
+zend.script_encoding=UTF-8
mbstring.internal_encoding=UTF-8
--FILE--
<?php
diff --git a/ext/mcrypt/mcrypt.c b/ext/mcrypt/mcrypt.c
index 07568e6c2a..89ad83f6bf 100644
--- a/ext/mcrypt/mcrypt.c
+++ b/ext/mcrypt/mcrypt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mcrypt/mcrypt_filter.c b/ext/mcrypt/mcrypt_filter.c
index da8215bd9e..cc32be649a 100644
--- a/ext/mcrypt/mcrypt_filter.c
+++ b/ext/mcrypt/mcrypt_filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mcrypt/php_mcrypt.h b/ext/mcrypt/php_mcrypt.h
index 4eb2c56f0e..9dfa1d8185 100644
--- a/ext/mcrypt/php_mcrypt.h
+++ b/ext/mcrypt/php_mcrypt.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mcrypt/php_mcrypt_filter.h b/ext/mcrypt/php_mcrypt_filter.h
index 0139130328..bfb0d7288f 100644
--- a/ext/mcrypt/php_mcrypt_filter.h
+++ b/ext/mcrypt/php_mcrypt_filter.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mssql/php_mssql.c b/ext/mssql/php_mssql.c
index d74f0829d9..eef472aa3f 100644
--- a/ext/mssql/php_mssql.c
+++ b/ext/mssql/php_mssql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mssql/php_mssql.h b/ext/mssql/php_mssql.h
index 2b7d3e19c3..5b2456e9bd 100644
--- a/ext/mssql/php_mssql.h
+++ b/ext/mssql/php_mssql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysql/php_mysql.c b/ext/mysql/php_mysql.c
index 88bb9ab21e..3d092b2d6a 100644
--- a/ext/mysql/php_mysql.c
+++ b/ext/mysql/php_mysql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysql/php_mysql.h b/ext/mysql/php_mysql.h
index 7b9ab8d6fb..0368140580 100644
--- a/ext/mysql/php_mysql.h
+++ b/ext/mysql/php_mysql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysql/php_mysql_structs.h b/ext/mysql/php_mysql_structs.h
index bf09b24b0c..ee1286d989 100644
--- a/ext/mysql/php_mysql_structs.h
+++ b/ext/mysql/php_mysql_structs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli.c b/ext/mysqli/mysqli.c
index ad4e25c66f..86de2ed919 100644
--- a/ext/mysqli/mysqli.c
+++ b/ext/mysqli/mysqli.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -176,8 +176,11 @@ void php_clear_stmt_bind(MY_STMT *stmt TSRMLS_DC)
php_free_stmt_bind_buffer(stmt->param, FETCH_SIMPLE);
/* Clean output bind */
php_free_stmt_bind_buffer(stmt->result, FETCH_RESULT);
-#endif
+ if (stmt->link_handle) {
+ zend_objects_store_del_ref_by_handle(stmt->link_handle TSRMLS_CC);
+ }
+#endif
if (stmt->query) {
efree(stmt->query);
}
@@ -1069,6 +1072,10 @@ PHP_FUNCTION(mysqli_stmt_construct)
efree(stmt);
RETURN_FALSE;
}
+#ifndef MYSQLI_USE_MYSQLND
+ stmt->link_handle = Z_OBJ_HANDLE(*mysql_link);
+ zend_objects_store_add_ref_by_handle(stmt->link_handle TSRMLS_CC);
+#endif
mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));
mysqli_resource->ptr = (void *)stmt;
diff --git a/ext/mysqli/mysqli_api.c b/ext/mysqli/mysqli_api.c
index 3ee5c803a5..719dffff3d 100644
--- a/ext/mysqli/mysqli_api.c
+++ b/ext/mysqli/mysqli_api.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -385,7 +385,7 @@ mysqli_stmt_bind_result_do_bind(MY_STMT *stmt, zval ***args, unsigned int argc,
/* Changed to my_bool in MySQL 5.1. See MySQL Bug #16144 */
my_bool tmp;
#else
- uint tmp = 0;
+ ulong tmp = 0;
#endif
stmt->result.buf[ofs].type = IS_STRING;
/*
@@ -1869,6 +1869,10 @@ PHP_FUNCTION(mysqli_prepare)
efree(stmt);
RETURN_FALSE;
}
+#ifndef MYSQLI_USE_MYSQLND
+ stmt->link_handle = Z_OBJ_HANDLE(*mysql_link);
+ zend_objects_store_add_ref_by_handle(stmt->link_handle TSRMLS_CC);
+#endif
mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));
mysqli_resource->ptr = (void *)stmt;
@@ -2413,6 +2417,10 @@ PHP_FUNCTION(mysqli_stmt_init)
efree(stmt);
RETURN_FALSE;
}
+#ifndef MYSQLI_USE_MYSQLND
+ stmt->link_handle = Z_OBJ_HANDLE(*mysql_link);
+ zend_objects_store_add_ref_by_handle(stmt->link_handle TSRMLS_CC);
+#endif
mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));
mysqli_resource->status = MYSQLI_STATUS_INITIALIZED;
diff --git a/ext/mysqli/mysqli_driver.c b/ext/mysqli/mysqli_driver.c
index 8684edcb47..d90d37c2ec 100644
--- a/ext/mysqli/mysqli_driver.c
+++ b/ext/mysqli/mysqli_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_embedded.c b/ext/mysqli/mysqli_embedded.c
index 3693777b25..e56e936f63 100644
--- a/ext/mysqli/mysqli_embedded.c
+++ b/ext/mysqli/mysqli_embedded.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_exception.c b/ext/mysqli/mysqli_exception.c
index dafc3098c7..82cf5cd7bf 100644
--- a/ext/mysqli/mysqli_exception.c
+++ b/ext/mysqli/mysqli_exception.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_fe.c b/ext/mysqli/mysqli_fe.c
index 6f2e404087..78fe02ab76 100644
--- a/ext/mysqli/mysqli_fe.c
+++ b/ext/mysqli/mysqli_fe.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_fe.h b/ext/mysqli/mysqli_fe.h
index 7e447c63e5..d5ae8a6ff9 100644
--- a/ext/mysqli/mysqli_fe.h
+++ b/ext/mysqli/mysqli_fe.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_libmysql.h b/ext/mysqli/mysqli_libmysql.h
index e10e3702ea..5e7f730aec 100644
--- a/ext/mysqli/mysqli_libmysql.h
+++ b/ext/mysqli/mysqli_libmysql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_nonapi.c b/ext/mysqli/mysqli_nonapi.c
index c24b974de8..db0352baeb 100644
--- a/ext/mysqli/mysqli_nonapi.c
+++ b/ext/mysqli/mysqli_nonapi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -775,7 +775,7 @@ PHP_FUNCTION(mysqli_poll)
MYSQLND **new_r_array = NULL, **new_e_array = NULL, **new_dont_poll_array = NULL;
long sec = 0, usec = 0;
enum_func_status ret;
- uint desc_num;
+ int desc_num;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a!a!al|l", &r_array, &e_array, &dont_poll_array, &sec, &usec) == FAILURE) {
return;
diff --git a/ext/mysqli/mysqli_priv.h b/ext/mysqli/mysqli_priv.h
index d823ea89eb..190572b689 100644
--- a/ext/mysqli/mysqli_priv.h
+++ b/ext/mysqli/mysqli_priv.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_prop.c b/ext/mysqli/mysqli_prop.c
index bd9cee28f1..7060367394 100644
--- a/ext/mysqli/mysqli_prop.c
+++ b/ext/mysqli/mysqli_prop.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_report.c b/ext/mysqli/mysqli_report.c
index 52135ce43e..bdd3adaf5f 100644
--- a/ext/mysqli/mysqli_report.c
+++ b/ext/mysqli/mysqli_report.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_result_iterator.c b/ext/mysqli/mysqli_result_iterator.c
index 3ea7bafe49..a84060316b 100644
--- a/ext/mysqli/mysqli_result_iterator.c
+++ b/ext/mysqli/mysqli_result_iterator.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/mysqli_warning.c b/ext/mysqli/mysqli_warning.c
index 25653e3358..e100319e61 100644
--- a/ext/mysqli/mysqli_warning.c
+++ b/ext/mysqli/mysqli_warning.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/php_mysqli.h b/ext/mysqli/php_mysqli.h
index 6dac3f0979..e036cf42b7 100644
--- a/ext/mysqli/php_mysqli.h
+++ b/ext/mysqli/php_mysqli.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqli/php_mysqli_structs.h b/ext/mysqli/php_mysqli_structs.h
index 8b329bb5d0..899c0c97c8 100644
--- a/ext/mysqli/php_mysqli_structs.h
+++ b/ext/mysqli/php_mysqli_structs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -116,6 +116,10 @@ typedef struct {
BIND_BUFFER param;
BIND_BUFFER result;
char *query;
+#ifndef MYSQLI_USE_MYSQLND
+ /* used to manage refcount with libmysql (already implement in mysqlnd) */
+ zend_object_handle link_handle;
+#endif
} MY_STMT;
typedef struct {
diff --git a/ext/mysqli/tests/bug66043.phpt b/ext/mysqli/tests/bug66043.phpt
new file mode 100644
index 0000000000..d0e8b1c3d3
--- /dev/null
+++ b/ext/mysqli/tests/bug66043.phpt
@@ -0,0 +1,24 @@
+--TEST--
+Bug #66043 (Segfault calling bind_param() on mysqli)
+--SKIPIF--
+<?php
+require_once('skipif.inc');
+require_once("connect.inc");
+if ($IS_MYSQLND) {
+ die("skip libmysql only test");
+}
+require_once('skipifconnectfailure.inc');
+?>
+--FILE--
+<?php
+require 'connect.inc';
+$db = new mysqli($host, $user, $passwd, 'mysql');
+
+$stmt = $db->stmt_init();
+$stmt->prepare("SELECT User FROM user WHERE password=\"\"");
+$stmt->execute();
+$stmt->bind_result($testArg);
+echo "Okey";
+?>
+--EXPECTF--
+Okey
diff --git a/ext/mysqli/tests/bug66124.phpt b/ext/mysqli/tests/bug66124.phpt
new file mode 100644
index 0000000000..8c0027f9e6
--- /dev/null
+++ b/ext/mysqli/tests/bug66124.phpt
@@ -0,0 +1,101 @@
+--TEST--
+Bug #66124 (mysqli under mysqlnd loses precision when bind_param with 'i')
+--SKIPIF--
+<?php
+require_once('skipif.inc');
+require_once('connect.inc');
+require_once('skipifconnectfailure.inc');
+?>
+--FILE--
+<?php
+$table_drop = "DROP TABLE IF EXISTS `bug66124`";
+$table_create = "CREATE TABLE `bug66124` (
+ `id` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
+ PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8";
+
+$table_insert = "INSERT INTO `bug66124` SET `id`=?";
+$table_select = "SELECT * FROM `bug66124`";
+$table_delete = "DELETE FROM `bug66124`";
+$id = '1311200011005001566';
+
+
+require_once('connect.inc');
+
+if (!$link = my_mysqli_connect($host, $user, $passwd, $db, $port, $socket)) {
+ printf("Cannot connect to the server using host=%s, user=%s, passwd=***, dbname=%s, port=%s, socket=%s\n",
+ $host, $user, $db, $port, $socket);
+ exit(1);
+}
+
+$link->query($table_drop);
+$link->query($table_create);
+
+$stmt = $link->prepare($table_insert);
+if (!$stmt) {
+ printf("Can't prepare\n");
+ exit(1);
+}
+
+echo "Using 'i':\n";
+$stmt->bind_param('i', $id);
+
+if ($stmt->execute()){
+ echo "insert id:{$id}=>{$stmt->insert_id}\n";
+} else {
+ printf("Can't execute\n");
+ exit(1);
+}
+
+
+$result = $link->query($table_select);
+
+if ($result){
+ while ($row = $result->fetch_assoc()) {
+ echo "fetch id:{$row['id']}\n";
+ }
+} else {
+ printf("Can't select\n");
+ exit(1);
+}
+
+$stmt->close();
+
+$link->query($table_drop);
+$link->query($table_create);
+
+
+$stmt = $link->prepare($table_insert);
+$stmt->bind_param('s', $id);
+
+echo "Using 's':\n";
+
+if ($stmt->execute()){
+ echo "insert id:{$id}\n";
+} else{
+ printf("Can't execute\n");
+ exit(1);
+}
+
+$result = $link->query($table_select);
+
+if ($result){
+ while ($row = $result->fetch_assoc()) {
+ echo "fetch id:{$row['id']}\n";
+ }
+} else {
+ printf("Can't select\n");
+ exit(1);
+}
+
+$link->close();
+?>
+done
+--EXPECTF--
+Using 'i':
+insert id:1311200011005001566=>1311200011005001566
+fetch id:1311200011005001566
+Using 's':
+insert id:1311200011005001566
+fetch id:1311200011005001566
+done \ No newline at end of file
diff --git a/ext/mysqli/tests/bug66762.phpt b/ext/mysqli/tests/bug66762.phpt
new file mode 100644
index 0000000000..2b8a92c7fd
--- /dev/null
+++ b/ext/mysqli/tests/bug66762.phpt
@@ -0,0 +1,26 @@
+--TEST--
+Bug #66762 mysqli@libmysql segfault in mysqli_stmt::bind_result() when link closed
+--SKIPIF--
+<?php
+require_once('skipif.inc');
+require_once('skipifconnectfailure.inc');
+?>
+--FILE--
+<?php
+ require_once("connect.inc");
+
+ $mysqli = new mysqli($host, $user, $passwd, $db);
+
+ $read_stmt = $mysqli->prepare("SELECT 1");
+
+ var_dump($read_stmt->bind_result($data));
+
+ unset($mysqli);
+ var_dump($read_stmt->bind_result($data));
+
+?>
+done!
+--EXPECT--
+bool(true)
+bool(true)
+done! \ No newline at end of file
diff --git a/ext/mysqlnd/CREDITS b/ext/mysqlnd/CREDITS
index 5a7d69d665..08ebb21aa7 100644
--- a/ext/mysqlnd/CREDITS
+++ b/ext/mysqlnd/CREDITS
@@ -1,2 +1,2 @@
MySQLnd
-Andrey Hristov, Ulf Wendel, Georg Richter, Johannes Schlüter
+Andrey Hristov, Ulf Wendel, Georg Richter, Johannes Schlüter
diff --git a/ext/mysqlnd/mysqlnd.c b/ext/mysqlnd/mysqlnd.c
index 169577ff97..39813145ba 100644
--- a/ext/mysqlnd/mysqlnd.c
+++ b/ext/mysqlnd/mysqlnd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -257,6 +257,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, simple_command_handle_response)(MYSQLND_CONN_D
conn->persistent);
if (!ignore_upsert_status) {
+ memset(conn->upsert_status, 0, sizeof(*conn->upsert_status));
conn->upsert_status->warning_count = ok_response->warning_count;
conn->upsert_status->server_status = ok_response->server_status;
conn->upsert_status->affected_rows = ok_response->affected_rows;
@@ -319,6 +320,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, simple_command_send_request)(MYSQLND_CONN_DATA
DBG_ENTER("mysqlnd_conn_data::simple_command_send_request");
DBG_INF_FMT("command=%s silent=%u", mysqlnd_command_to_text[command], silent);
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
switch (CONN_GET_STATE(conn)) {
case CONN_READY:
@@ -333,10 +335,6 @@ MYSQLND_METHOD(mysqlnd_conn_data, simple_command_send_request)(MYSQLND_CONN_DATA
DBG_RETURN(FAIL);
}
- /* clean UPSERT info */
- if (!ignore_upsert_status) {
- memset(conn->upsert_status, 0, sizeof(*conn->upsert_status));
- }
SET_ERROR_AFF_ROWS(conn);
SET_EMPTY_ERROR(*conn->error_info);
@@ -811,6 +809,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, connect_handshake)(MYSQLND_CONN_DATA * conn,
{
goto err;
}
+ memset(conn->upsert_status, 0, sizeof(*conn->upsert_status));
conn->upsert_status->warning_count = 0;
conn->upsert_status->server_status = greet_packet->server_status;
conn->upsert_status->affected_rows = 0;
@@ -1183,6 +1182,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, send_query)(MYSQLND_CONN_DATA * conn, const ch
enum_func_status ret = FAIL;
DBG_ENTER("mysqlnd_conn_data::send_query");
DBG_INF_FMT("conn=%llu query=%s", conn->thread_id, query);
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
if (PASS == conn->m->local_tx_start(conn, this_func TSRMLS_CC)) {
ret = conn->m->simple_command(conn, COM_QUERY, (zend_uchar *) query, query_len,
@@ -1193,6 +1193,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, send_query)(MYSQLND_CONN_DATA * conn, const ch
}
conn->m->local_tx_end(conn, this_func, ret TSRMLS_CC);
}
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
DBG_RETURN(ret);
}
/* }}} */
@@ -1208,6 +1209,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, reap_query)(MYSQLND_CONN_DATA * conn TSRMLS_DC
DBG_ENTER("mysqlnd_conn_data::reap_query");
DBG_INF_FMT("conn=%llu", conn->thread_id);
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
if (PASS == conn->m->local_tx_start(conn, this_func TSRMLS_CC)) {
if (state <= CONN_READY || state == CONN_QUIT_SENT) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Connection not opened, clear or has been closed");
@@ -1218,6 +1220,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, reap_query)(MYSQLND_CONN_DATA * conn TSRMLS_DC
conn->m->local_tx_end(conn, this_func, ret TSRMLS_CC);
}
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
DBG_RETURN(ret);
}
/* }}} */
@@ -1337,7 +1340,7 @@ static int mysqlnd_stream_array_from_fd_set(MYSQLND ** conn_array, fd_set * fds
/* {{{ _mysqlnd_poll */
PHPAPI enum_func_status
-_mysqlnd_poll(MYSQLND **r_array, MYSQLND **e_array, MYSQLND ***dont_poll, long sec, long usec, uint * desc_num TSRMLS_DC)
+_mysqlnd_poll(MYSQLND **r_array, MYSQLND **e_array, MYSQLND ***dont_poll, long sec, long usec, int * desc_num TSRMLS_DC)
{
struct timeval tv;
struct timeval *tv_p = NULL;
@@ -1603,6 +1606,7 @@ MYSQLND_METHOD(mysqlnd_conn_data, escape_string)(MYSQLND_CONN_DATA * const conn,
DBG_INF_FMT("conn=%llu", conn->thread_id);
if (PASS == conn->m->local_tx_start(conn, this_func TSRMLS_CC)) {
+ DBG_INF_FMT("server_status=%u", conn->upsert_status->server_status);
if (conn->upsert_status->server_status & SERVER_STATUS_NO_BACKSLASH_ESCAPES) {
ret = mysqlnd_cset_escape_quotes(conn->charset, newstr, escapestr, escapestr_len TSRMLS_CC);
} else {
@@ -2247,7 +2251,6 @@ MYSQLND_METHOD(mysqlnd_conn_data, change_user)(MYSQLND_CONN_DATA * const conn,
}
if (!db) {
db = "";
-
}
/* XXX: passwords that have \0 inside work during auth, but in this case won't work with change user */
diff --git a/ext/mysqlnd/mysqlnd.h b/ext/mysqlnd/mysqlnd.h
index 40933630ed..bf9ad53b11 100644
--- a/ext/mysqlnd/mysqlnd.h
+++ b/ext/mysqlnd/mysqlnd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -117,7 +117,7 @@ PHPAPI void _mysqlnd_debug(const char *mode TSRMLS_DC);
#define mysqlnd_reap_async_query(conn) ((conn)->data)->m->reap_query((conn)->data TSRMLS_CC)
#define mysqlnd_unbuffered_skip_result(result) (result)->m.skip_result((result) TSRMLS_CC)
-PHPAPI enum_func_status _mysqlnd_poll(MYSQLND **r_array, MYSQLND **e_array, MYSQLND ***dont_poll, long sec, long usec, uint * desc_num TSRMLS_DC);
+PHPAPI enum_func_status _mysqlnd_poll(MYSQLND **r_array, MYSQLND **e_array, MYSQLND ***dont_poll, long sec, long usec, int * desc_num TSRMLS_DC);
#define mysqlnd_use_result(conn) ((conn)->data)->m->use_result((conn)->data TSRMLS_CC)
#define mysqlnd_store_result(conn) ((conn)->data)->m->store_result((conn)->data TSRMLS_CC)
diff --git a/ext/mysqlnd/mysqlnd_alloc.c b/ext/mysqlnd/mysqlnd_alloc.c
index 80e8156016..42ce55a36a 100644
--- a/ext/mysqlnd/mysqlnd_alloc.c
+++ b/ext/mysqlnd/mysqlnd_alloc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_alloc.h b/ext/mysqlnd/mysqlnd_alloc.h
index e6b0f08815..eef5988829 100644
--- a/ext/mysqlnd/mysqlnd_alloc.h
+++ b/ext/mysqlnd/mysqlnd_alloc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_auth.c b/ext/mysqlnd/mysqlnd_auth.c
index 8611d99864..7f554dcb7b 100644
--- a/ext/mysqlnd/mysqlnd_auth.c
+++ b/ext/mysqlnd/mysqlnd_auth.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_block_alloc.c b/ext/mysqlnd/mysqlnd_block_alloc.c
index b9d7887287..100e807bae 100644
--- a/ext/mysqlnd/mysqlnd_block_alloc.c
+++ b/ext/mysqlnd/mysqlnd_block_alloc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_block_alloc.h b/ext/mysqlnd/mysqlnd_block_alloc.h
index 39ccbdc6b3..f9627744d5 100644
--- a/ext/mysqlnd/mysqlnd_block_alloc.h
+++ b/ext/mysqlnd/mysqlnd_block_alloc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_bt.c b/ext/mysqlnd/mysqlnd_bt.c
index 9ed109b7dc..a93af6b395 100644
--- a/ext/mysqlnd/mysqlnd_bt.c
+++ b/ext/mysqlnd/mysqlnd_bt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_charset.c b/ext/mysqlnd/mysqlnd_charset.c
index 0ca419b5a8..c2f2b8890e 100644
--- a/ext/mysqlnd/mysqlnd_charset.c
+++ b/ext/mysqlnd/mysqlnd_charset.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_charset.h b/ext/mysqlnd/mysqlnd_charset.h
index 09d0eb4171..cf3eada8af 100644
--- a/ext/mysqlnd/mysqlnd_charset.h
+++ b/ext/mysqlnd/mysqlnd_charset.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_debug.c b/ext/mysqlnd/mysqlnd_debug.c
index 5e617f5b2b..9fbcc4768f 100644
--- a/ext/mysqlnd/mysqlnd_debug.c
+++ b/ext/mysqlnd/mysqlnd_debug.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_debug.h b/ext/mysqlnd/mysqlnd_debug.h
index de0bbae073..861851378b 100644
--- a/ext/mysqlnd/mysqlnd_debug.h
+++ b/ext/mysqlnd/mysqlnd_debug.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_driver.c b/ext/mysqlnd/mysqlnd_driver.c
index 699346c999..98826b9ce3 100644
--- a/ext/mysqlnd/mysqlnd_driver.c
+++ b/ext/mysqlnd/mysqlnd_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_enum_n_def.h b/ext/mysqlnd/mysqlnd_enum_n_def.h
index 4ace69adcf..5511db433a 100644
--- a/ext/mysqlnd/mysqlnd_enum_n_def.h
+++ b/ext/mysqlnd/mysqlnd_enum_n_def.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -561,6 +561,10 @@ enum mysqlnd_packet_type
};
+/*
+ After adding new elements please update
+ `mysqlnd_command_to_text` in mysqlnd_wireprotocol.c
+*/
enum php_mysqlnd_server_command
{
COM_SLEEP = 0,
@@ -593,6 +597,8 @@ enum php_mysqlnd_server_command
COM_SET_OPTION = 27,
COM_STMT_FETCH = 28,
COM_DAEMON,
+ COM_BINLOG_DUMP_GTID,
+ COM_RESET_CONNECTION,
COM_END
};
diff --git a/ext/mysqlnd/mysqlnd_ext_plugin.c b/ext/mysqlnd/mysqlnd_ext_plugin.c
index 7116943cd5..f40688b272 100644
--- a/ext/mysqlnd/mysqlnd_ext_plugin.c
+++ b/ext/mysqlnd/mysqlnd_ext_plugin.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_ext_plugin.h b/ext/mysqlnd/mysqlnd_ext_plugin.h
index ef9d085a9b..2a2416a042 100644
--- a/ext/mysqlnd/mysqlnd_ext_plugin.h
+++ b/ext/mysqlnd/mysqlnd_ext_plugin.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_libmysql_compat.h b/ext/mysqlnd/mysqlnd_libmysql_compat.h
index 516200e0d5..b8ff959d18 100644
--- a/ext/mysqlnd/mysqlnd_libmysql_compat.h
+++ b/ext/mysqlnd/mysqlnd_libmysql_compat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_loaddata.c b/ext/mysqlnd/mysqlnd_loaddata.c
index a1c589a8b7..94d69a4008 100644
--- a/ext/mysqlnd/mysqlnd_loaddata.c
+++ b/ext/mysqlnd/mysqlnd_loaddata.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_net.c b/ext/mysqlnd/mysqlnd_net.c
index fabceb4c8d..fadcbd87f6 100644
--- a/ext/mysqlnd/mysqlnd_net.c
+++ b/ext/mysqlnd/mysqlnd_net.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_net.h b/ext/mysqlnd/mysqlnd_net.h
index 568a0e18b2..76a474bc5f 100644
--- a/ext/mysqlnd/mysqlnd_net.h
+++ b/ext/mysqlnd/mysqlnd_net.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_plugin.c b/ext/mysqlnd/mysqlnd_plugin.c
index aa914061d6..86543a05c2 100644
--- a/ext/mysqlnd/mysqlnd_plugin.c
+++ b/ext/mysqlnd/mysqlnd_plugin.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_priv.h b/ext/mysqlnd/mysqlnd_priv.h
index 38ef6cc855..deb0bdc8c8 100644
--- a/ext/mysqlnd/mysqlnd_priv.h
+++ b/ext/mysqlnd/mysqlnd_priv.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_ps.c b/ext/mysqlnd/mysqlnd_ps.c
index 15b293825b..8096cbbbd9 100644
--- a/ext/mysqlnd/mysqlnd_ps.c
+++ b/ext/mysqlnd/mysqlnd_ps.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -486,6 +486,7 @@ mysqlnd_stmt_execute_parse_response(MYSQLND_STMT * const s TSRMLS_DC)
ret = mysqlnd_query_read_result_set_header(stmt->conn, s TSRMLS_CC);
if (ret == FAIL) {
COPY_CLIENT_ERROR(*stmt->error_info, *conn->error_info);
+ memset(stmt->upsert_status, 0, sizeof(*stmt->upsert_status));
stmt->upsert_status->affected_rows = conn->upsert_status->affected_rows;
if (CONN_GET_STATE(conn) == CONN_QUIT_SENT) {
/* close the statement here, the connection has been closed */
@@ -905,6 +906,7 @@ mysqlnd_stmt_fetch_row_unbuffered(MYSQLND_RES *result, void *param, unsigned int
DBG_INF("EOF");
/* Mark the connection as usable again */
result->unbuf->eof_reached = TRUE;
+ memset(result->conn->upsert_status, 0, sizeof(*result->conn->upsert_status));
result->conn->upsert_status->warning_count = row_packet->warning_count;
result->conn->upsert_status->server_status = row_packet->server_status;
/*
@@ -1014,6 +1016,7 @@ mysqlnd_fetch_stmt_row_cursor(MYSQLND_RES *result, void *param, unsigned int fla
row_packet->skip_extraction = stmt->result_bind? FALSE:TRUE;
+ memset(stmt->upsert_status, 0, sizeof(*stmt->upsert_status));
if (PASS == (ret = PACKET_READ(row_packet, result->conn)) && !row_packet->eof) {
unsigned int i, field_count = result->field_count;
diff --git a/ext/mysqlnd/mysqlnd_ps_codec.c b/ext/mysqlnd/mysqlnd_ps_codec.c
index d8ad06c608..d0e44fa275 100644
--- a/ext/mysqlnd/mysqlnd_ps_codec.c
+++ b/ext/mysqlnd/mysqlnd_ps_codec.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -569,9 +569,8 @@ mysqlnd_stmt_execute_store_params(MYSQLND_STMT * s, zend_uchar **buf, zend_uchar
occur, and force resend for the next execution.
*/
for (i = 0; i < stmt->param_count; i++) {
- if (Z_TYPE_P(stmt->param_bind[i].zv) != IS_NULL &&
- (stmt->param_bind[i].type == MYSQL_TYPE_LONG || stmt->param_bind[i].type == MYSQL_TYPE_LONGLONG))
- {
+ short current_type = stmt->param_bind[i].type;
+ if (Z_TYPE_P(stmt->param_bind[i].zv) != IS_NULL && (current_type == MYSQL_TYPE_LONG || current_type == MYSQL_TYPE_LONGLONG)) {
/* always copy the var, because we do many conversions */
if (Z_TYPE_P(stmt->param_bind[i].zv) != IS_LONG &&
PASS != mysqlnd_stmt_copy_it(&copies, stmt->param_bind[i].zv, stmt->param_count, i TSRMLS_CC))
@@ -585,10 +584,31 @@ mysqlnd_stmt_execute_store_params(MYSQLND_STMT * s, zend_uchar **buf, zend_uchar
*/
if (Z_TYPE_P(stmt->param_bind[i].zv) != IS_LONG) {
zval *tmp_data = (copies && copies[i])? copies[i]: stmt->param_bind[i].zv;
- convert_to_double_ex(&tmp_data);
- if (Z_DVAL_P(tmp_data) > LONG_MAX || Z_DVAL_P(tmp_data) < LONG_MIN) {
+ /*
+ Because converting to double and back to long can lead
+ to losing precision we need second variable. Conversion to double is to see if
+ value is too big for a long. As said, precision could be lost.
+ */
+ zval *tmp_data_copy;
+ MAKE_STD_ZVAL(tmp_data_copy);
+ *tmp_data_copy = *tmp_data;
+ Z_SET_REFCOUNT_P(tmp_data_copy, 1);
+ zval_copy_ctor(tmp_data_copy);
+ convert_to_double_ex(&tmp_data_copy);
+
+ /*
+ if it doesn't fit in a long send it as a string.
+ Check bug #52891 : Wrong data inserted with mysqli/mysqlnd when using bind_param, value > LONG_MAX
+ We do transformation here, which will be used later when sending types. The code later relies on this.
+ */
+ if (Z_DVAL_P(tmp_data_copy) > LONG_MAX || Z_DVAL_P(tmp_data_copy) < LONG_MIN) {
stmt->send_types_to_server = resend_types_next_time = 1;
+ convert_to_string_ex(&tmp_data);
+ } else {
+ convert_to_long_ex(&tmp_data);
}
+
+ zval_ptr_dtor(&tmp_data_copy);
}
}
}
@@ -631,10 +651,11 @@ mysqlnd_stmt_execute_store_params(MYSQLND_STMT * s, zend_uchar **buf, zend_uchar
*/
if (Z_TYPE_P(stmt->param_bind[i].zv) != IS_LONG) {
zval *tmp_data = (copies && copies[i])? copies[i]: stmt->param_bind[i].zv;
-
- convert_to_double_ex(&tmp_data);
- if (Z_DVAL_P(tmp_data) > LONG_MAX || Z_DVAL_P(tmp_data) < LONG_MIN) {
- convert_to_string_ex(&tmp_data);
+ /*
+ In case of IS_LONG we do nothing, it is ok, in case of string, we just need to set current_type.
+ The actual transformation has been performed several dozens line above.
+ */
+ if (Z_TYPE_P(tmp_data) == IS_STRING) {
current_type = MYSQL_TYPE_VAR_STRING;
/*
don't change stmt->param_bind[i].type to MYSQL_TYPE_VAR_STRING
@@ -642,8 +663,6 @@ mysqlnd_stmt_execute_store_params(MYSQLND_STMT * s, zend_uchar **buf, zend_uchar
if the type is however not long, then we will do a goto in the next switch.
We want to preserve the original bind type given by the user. Thus, we do these hacks.
*/
- } else {
- convert_to_long_ex(&tmp_data);
}
}
}
diff --git a/ext/mysqlnd/mysqlnd_result.c b/ext/mysqlnd/mysqlnd_result.c
index 20d941e05b..fbf8ea031c 100644
--- a/ext/mysqlnd/mysqlnd_result.c
+++ b/ext/mysqlnd/mysqlnd_result.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -187,9 +187,11 @@ MYSQLND_METHOD(mysqlnd_res, free_buffered_data)(MYSQLND_RES * result TSRMLS_DC)
if (set->data) {
unsigned int copy_on_write_performed = 0;
unsigned int copy_on_write_saved = 0;
+ zval **data = set->data;
+ set->data = NULL; /* prevent double free if following loop is interrupted */
for (row = set->row_count - 1; row >= 0; row--) {
- zval **current_row = set->data + row * field_count;
+ zval **current_row = data + row * field_count;
MYSQLND_MEMORY_POOL_CHUNK *current_buffer = set->row_buffers[row];
int64_t col;
@@ -211,8 +213,7 @@ MYSQLND_METHOD(mysqlnd_res, free_buffered_data)(MYSQLND_RES * result TSRMLS_DC)
MYSQLND_INC_GLOBAL_STATISTIC_W_VALUE2(STAT_COPY_ON_WRITE_PERFORMED, copy_on_write_performed,
STAT_COPY_ON_WRITE_SAVED, copy_on_write_saved);
- mnd_efree(set->data);
- set->data = NULL;
+ mnd_efree(data);
}
if (set->row_buffers) {
@@ -415,6 +416,7 @@ mysqlnd_query_read_result_set_header(MYSQLND_CONN_DATA * conn, MYSQLND_STMT * s
DBG_INF("UPSERT");
conn->last_query_type = QUERY_UPSERT;
conn->field_count = rset_header->field_count;
+ memset(conn->upsert_status, 0, sizeof(*conn->upsert_status));
conn->upsert_status->warning_count = rset_header->warning_count;
conn->upsert_status->server_status = rset_header->server_status;
conn->upsert_status->affected_rows = rset_header->affected_rows;
@@ -702,6 +704,7 @@ mysqlnd_fetch_row_unbuffered_c(MYSQLND_RES * result TSRMLS_DC)
/* Mark the connection as usable again */
DBG_INF_FMT("warnings=%u server_status=%u", row_packet->warning_count, row_packet->server_status);
result->unbuf->eof_reached = TRUE;
+ memset(result->conn->upsert_status, 0, sizeof(*result->conn->upsert_status));
result->conn->upsert_status->warning_count = row_packet->warning_count;
result->conn->upsert_status->server_status = row_packet->server_status;
/*
@@ -828,6 +831,7 @@ mysqlnd_fetch_row_unbuffered(MYSQLND_RES * result, void *param, unsigned int fla
/* Mark the connection as usable again */
DBG_INF_FMT("warnings=%u server_status=%u", row_packet->warning_count, row_packet->server_status);
result->unbuf->eof_reached = TRUE;
+ memset(result->conn->upsert_status, 0, sizeof(*result->conn->upsert_status));
result->conn->upsert_status->warning_count = row_packet->warning_count;
result->conn->upsert_status->server_status = row_packet->server_status;
/*
@@ -1175,6 +1179,7 @@ MYSQLND_METHOD(mysqlnd_res, store_result_fetch_data)(MYSQLND_CONN_DATA * const c
/* Finally clean */
if (row_packet->eof) {
+ memset(conn->upsert_status, 0, sizeof(*conn->upsert_status));
conn->upsert_status->warning_count = row_packet->warning_count;
conn->upsert_status->server_status = row_packet->server_status;
}
diff --git a/ext/mysqlnd/mysqlnd_result.h b/ext/mysqlnd/mysqlnd_result.h
index f821b916ea..54f3b03d7d 100644
--- a/ext/mysqlnd/mysqlnd_result.h
+++ b/ext/mysqlnd/mysqlnd_result.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_result_meta.c b/ext/mysqlnd/mysqlnd_result_meta.c
index 989781d665..6523a431ca 100644
--- a/ext/mysqlnd/mysqlnd_result_meta.c
+++ b/ext/mysqlnd/mysqlnd_result_meta.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_result_meta.h b/ext/mysqlnd/mysqlnd_result_meta.h
index 8fa9989700..97720adba1 100644
--- a/ext/mysqlnd/mysqlnd_result_meta.h
+++ b/ext/mysqlnd/mysqlnd_result_meta.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_reverse_api.c b/ext/mysqlnd/mysqlnd_reverse_api.c
index daa43ec513..cd490fa62c 100644
--- a/ext/mysqlnd/mysqlnd_reverse_api.c
+++ b/ext/mysqlnd/mysqlnd_reverse_api.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_reverse_api.h b/ext/mysqlnd/mysqlnd_reverse_api.h
index ae07bb7b51..028a1f6b13 100644
--- a/ext/mysqlnd/mysqlnd_reverse_api.h
+++ b/ext/mysqlnd/mysqlnd_reverse_api.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_statistics.c b/ext/mysqlnd/mysqlnd_statistics.c
index f52eb65b06..ce193275ec 100644
--- a/ext/mysqlnd/mysqlnd_statistics.c
+++ b/ext/mysqlnd/mysqlnd_statistics.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_statistics.h b/ext/mysqlnd/mysqlnd_statistics.h
index d1fd03b00e..0493d89396 100644
--- a/ext/mysqlnd/mysqlnd_statistics.h
+++ b/ext/mysqlnd/mysqlnd_statistics.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_structs.h b/ext/mysqlnd/mysqlnd_structs.h
index 99981f7e75..a9048b2b13 100644
--- a/ext/mysqlnd/mysqlnd_structs.h
+++ b/ext/mysqlnd/mysqlnd_structs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/mysqlnd_wireprotocol.c b/ext/mysqlnd/mysqlnd_wireprotocol.c
index 669970789b..df9dde592a 100644
--- a/ext/mysqlnd/mysqlnd_wireprotocol.c
+++ b/ext/mysqlnd/mysqlnd_wireprotocol.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -90,7 +90,8 @@ const char * const mysqlnd_command_to_text[COM_END] =
"TIME", "DELAYED_INSERT", "CHANGE_USER", "BINLOG_DUMP",
"TABLE_DUMP", "CONNECT_OUT", "REGISTER_SLAVE",
"STMT_PREPARE", "STMT_EXECUTE", "STMT_SEND_LONG_DATA", "STMT_CLOSE",
- "STMT_RESET", "SET_OPTION", "STMT_FETCH", "DAEMON"
+ "STMT_RESET", "SET_OPTION", "STMT_FETCH", "DAEMON", "BINLOG_DUMP_GTID",
+ "RESET_CONNECTION"
};
/* }}} */
@@ -827,6 +828,7 @@ php_mysqlnd_ok_read(void * _packet, MYSQLND_CONN_DATA * conn TSRMLS_DC)
packet->error, sizeof(packet->error),
&packet->error_no, packet->sqlstate
TSRMLS_CC);
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
DBG_RETURN(PASS);
}
/* Everything was fine! */
@@ -1069,6 +1071,7 @@ php_mysqlnd_rset_header_read(void * _packet, MYSQLND_CONN_DATA * conn TSRMLS_DC)
packet->error_info.error, sizeof(packet->error_info.error),
&packet->error_info.error_no, packet->error_info.sqlstate
TSRMLS_CC);
+ DBG_INF_FMT("conn->server_status=%u", conn->upsert_status->server_status);
DBG_RETURN(PASS);
}
diff --git a/ext/mysqlnd/mysqlnd_wireprotocol.h b/ext/mysqlnd/mysqlnd_wireprotocol.h
index 26dd4c65ae..4bd33592bf 100644
--- a/ext/mysqlnd/mysqlnd_wireprotocol.h
+++ b/ext/mysqlnd/mysqlnd_wireprotocol.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/php_mysqlnd.c b/ext/mysqlnd/php_mysqlnd.c
index 016840cf04..7712f1ecb8 100644
--- a/ext/mysqlnd/php_mysqlnd.c
+++ b/ext/mysqlnd/php_mysqlnd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/mysqlnd/php_mysqlnd.h b/ext/mysqlnd/php_mysqlnd.h
index 14ad234e1b..dc39028900 100644
--- a/ext/mysqlnd/php_mysqlnd.h
+++ b/ext/mysqlnd/php_mysqlnd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/oci8.c b/ext/oci8/oci8.c
index 44bfa71398..cdb1302d37 100644
--- a/ext/oci8/oci8.c
+++ b/ext/oci8/oci8.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/oci8_collection.c b/ext/oci8/oci8_collection.c
index 763e12e924..365baf4131 100644
--- a/ext/oci8/oci8_collection.c
+++ b/ext/oci8/oci8_collection.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/oci8_interface.c b/ext/oci8/oci8_interface.c
index e51d3c92f5..136718dbc2 100644
--- a/ext/oci8/oci8_interface.c
+++ b/ext/oci8/oci8_interface.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/oci8_lob.c b/ext/oci8/oci8_lob.c
index d05e053919..a6cdd647c9 100644
--- a/ext/oci8/oci8_lob.c
+++ b/ext/oci8/oci8_lob.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/oci8_statement.c b/ext/oci8/oci8_statement.c
index 89facb0703..de963c7cde 100644
--- a/ext/oci8/oci8_statement.c
+++ b/ext/oci8/oci8_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/php_oci8.h b/ext/oci8/php_oci8.h
index f1079526f6..65b8851ed0 100644
--- a/ext/oci8/php_oci8.h
+++ b/ext/oci8/php_oci8.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/php_oci8_int.h b/ext/oci8/php_oci8_int.h
index 155e57d2cd..0bc80c3d9c 100644
--- a/ext/oci8/php_oci8_int.h
+++ b/ext/oci8/php_oci8_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/oci8/tests/drcp_cclass1.phpt b/ext/oci8/tests/drcp_cclass1.phpt
index 068331e5a9..5c78a2943e 100644
--- a/ext/oci8/tests/drcp_cclass1.phpt
+++ b/ext/oci8/tests/drcp_cclass1.phpt
@@ -3,9 +3,21 @@ DRCP: Test setting connection class inline
--SKIPIF--
<?php
if (!extension_loaded('oci8')) die ("skip no oci8 extension");
-require(dirname(__FILE__)."/details.inc");
+require(dirname(__FILE__).'/connect.inc');
if (!$test_drcp) die("skip testing DRCP connection class only works in DRCP mode");
if (strcasecmp($user, "system") && strcasecmp($user, "sys")) die("skip needs to be run as a DBA user");
+
+preg_match('/.*Release ([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)\.([[:digit:]]+)*/', oci_server_version($c), $matches_sv);
+// This test in Oracle 12c needs a non-CDB or the root container
+if (isset($matches_sv[0]) && $matches_sv[1] >= 12) {
+ $s = oci_parse($c, "select nvl(sys_context('userenv', 'con_name'), 'notacdb') as dbtype from dual");
+ $r = @oci_execute($s);
+ if (!$r)
+ die('skip could not identify container type');
+ $r = oci_fetch_array($s);
+ if ($r['DBTYPE'] !== 'CDB$ROOT')
+ die('skip cannot run test using a PDB');
+}
?>
--FILE--
<?php
diff --git a/ext/oci8/tests/lob_015.phpt b/ext/oci8/tests/lob_015.phpt
index b4a19684a3..59e8fec42a 100644
--- a/ext/oci8/tests/lob_015.phpt
+++ b/ext/oci8/tests/lob_015.phpt
@@ -48,7 +48,7 @@ Warning: oci_bind_by_name() expects at least 3 parameters, 2 given in %s on line
Warning: oci_bind_by_name() expects at least 3 parameters, 1 given in %s on line %d
-Warning: oci_execute(): ORA-00932: %s NUMBER %s BLOB in %s on line %d
+Warning: oci_execute(): ORA-00932: %s on line %d
object(OCI-Lob)#%d (1) {
["descriptor"]=>
resource(%d) of type (oci8 descriptor)
diff --git a/ext/odbc/birdstep.c b/ext/odbc/birdstep.c
index 0af58d0cd6..7bc3833d86 100644
--- a/ext/odbc/birdstep.c
+++ b/ext/odbc/birdstep.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/odbc/php_birdstep.h b/ext/odbc/php_birdstep.h
index 17f4fdee50..90180d0641 100644
--- a/ext/odbc/php_birdstep.h
+++ b/ext/odbc/php_birdstep.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/odbc/php_odbc.c b/ext/odbc/php_odbc.c
index c84a4ecc60..4d21b3a136 100644
--- a/ext/odbc/php_odbc.c
+++ b/ext/odbc/php_odbc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/odbc/php_odbc.h b/ext/odbc/php_odbc.h
index 7e8d26d0cc..bd78e88f52 100644
--- a/ext/odbc/php_odbc.h
+++ b/ext/odbc/php_odbc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/odbc/php_odbc_includes.h b/ext/odbc/php_odbc_includes.h
index c00583b16a..a9b0acfa0c 100644
--- a/ext/odbc/php_odbc_includes.h
+++ b/ext/odbc/php_odbc_includes.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/Optimizer/block_pass.c b/ext/opcache/Optimizer/block_pass.c
index 1c34cffbf7..79eee8bcc1 100644
--- a/ext/opcache/Optimizer/block_pass.c
+++ b/ext/opcache/Optimizer/block_pass.c
@@ -643,8 +643,11 @@ static void zend_optimize_block(zend_code_block *block, zend_op_array *op_array,
opline->opcode != ZEND_FREE
) {
zend_op *src = VAR_SOURCE(opline->op1);
+ zval c = ZEND_OP1_LITERAL(src);
VAR_UNSET(opline->op1);
- COPY_NODE(opline->op1, src->op1);
+ zval_copy_ctor(&c);
+ update_op1_const(op_array, opline, &c TSRMLS_CC);
+ literal_dtor(&ZEND_OP1_LITERAL(src));
MAKE_NOP(src);
}
@@ -654,51 +657,12 @@ static void zend_optimize_block(zend_code_block *block, zend_op_array *op_array,
VAR_SOURCE(opline->op2)->opcode == ZEND_QM_ASSIGN &&
ZEND_OP1_TYPE(VAR_SOURCE(opline->op2)) == IS_CONST) {
zend_op *src = VAR_SOURCE(opline->op2);
+ zval c = ZEND_OP1_LITERAL(src);
VAR_UNSET(opline->op2);
- COPY_NODE(opline->op2, src->op1);
+ zval_copy_ctor(&c);
+ update_op2_const(op_array, opline, &c TSRMLS_CC);
+ literal_dtor(&ZEND_OP1_LITERAL(src));
MAKE_NOP(src);
-
-#if ZEND_EXTENSION_API_NO >= PHP_5_4_X_API_NO
- /* numeric string constants used as array indeces have to be
- converted to long at compile time */
- if (opline->opcode == ZEND_ADD_ARRAY_ELEMENT ||
- opline->opcode == ZEND_INIT_ARRAY ||
- opline->opcode == ZEND_UNSET_DIM ||
- opline->opcode == ZEND_ISSET_ISEMPTY_DIM_OBJ ||
- opline->opcode == ZEND_FETCH_DIM_R ||
- opline->opcode == ZEND_FETCH_DIM_W ||
- opline->opcode == ZEND_FETCH_DIM_RW ||
- opline->opcode == ZEND_FETCH_DIM_IS ||
- opline->opcode == ZEND_FETCH_DIM_FUNC_ARG ||
- opline->opcode == ZEND_FETCH_DIM_UNSET ||
- opline->opcode == ZEND_FETCH_DIM_TMP_VAR ||
- (opline->opcode == ZEND_OP_DATA &&
- ((opline-1)->opcode == ZEND_ASSIGN_DIM ||
- ((opline-1)->extended_value == ZEND_ASSIGN_DIM &&
- ((opline-1)->opcode == ZEND_ASSIGN_ADD ||
- (opline-1)->opcode == ZEND_ASSIGN_SUB ||
- (opline-1)->opcode == ZEND_ASSIGN_MUL ||
- (opline-1)->opcode == ZEND_ASSIGN_DIV ||
- (opline-1)->opcode == ZEND_ASSIGN_MOD ||
- (opline-1)->opcode == ZEND_ASSIGN_SL ||
- (opline-1)->opcode == ZEND_ASSIGN_SR ||
- (opline-1)->opcode == ZEND_ASSIGN_CONCAT ||
- (opline-1)->opcode == ZEND_ASSIGN_BW_OR ||
- (opline-1)->opcode == ZEND_ASSIGN_BW_AND ||
- (opline-1)->opcode == ZEND_ASSIGN_BW_XOR))))) {
-
- if (Z_TYPE(ZEND_OP2_LITERAL(opline)) == IS_STRING) {
- ulong index;
- int numeric = 0;
-
- ZEND_HANDLE_NUMERIC_EX(Z_STRVAL(ZEND_OP2_LITERAL(opline)), Z_STRLEN(ZEND_OP2_LITERAL(opline))+1, index, numeric = 1);
- if (numeric) {
- zval_dtor(&ZEND_OP2_LITERAL(opline));
- ZVAL_LONG(&ZEND_OP2_LITERAL(opline), index);
- }
- }
- }
-#endif
}
/* T = PRINT(X), F(T) => ECHO(X), F(1) */
@@ -1070,10 +1034,9 @@ static void zend_optimize_block(zend_code_block *block, zend_op_array *op_array,
literal_dtor(&ZEND_OP1_LITERAL(opline));
literal_dtor(&ZEND_OP2_LITERAL(opline));
- ZEND_OP1_LITERAL(opline) = result;
- SET_UNUSED(opline->op2);
-
opline->opcode = ZEND_QM_ASSIGN;
+ SET_UNUSED(opline->op2);
+ update_op1_const(op_array, opline, &result TSRMLS_CC);
}
EG(error_reporting) = er;
} else if ((opline->opcode == ZEND_BOOL ||
@@ -1094,11 +1057,12 @@ static void zend_optimize_block(zend_code_block *block, zend_op_array *op_array,
/* BOOL */
result = ZEND_OP1_LITERAL(opline);
convert_to_boolean(&result);
+ Z_TYPE(ZEND_OP1_LITERAL(opline)) = IS_NULL;
}
PZ_SET_REFCOUNT_P(&result, 1);
PZ_UNSET_ISREF_P(&result);
- ZEND_OP1_LITERAL(opline) = result;
opline->opcode = ZEND_QM_ASSIGN;
+ update_op1_const(op_array, opline, &result TSRMLS_CC);
} else if ((opline->opcode == ZEND_RETURN || opline->opcode == ZEND_EXIT) &&
ZEND_OP1_TYPE(opline) == IS_TMP_VAR &&
VAR_SOURCE(opline->op1) &&
diff --git a/ext/opcache/Optimizer/pass1_5.c b/ext/opcache/Optimizer/pass1_5.c
index 70ec6d5e2e..ca5b882901 100644
--- a/ext/opcache/Optimizer/pass1_5.c
+++ b/ext/opcache/Optimizer/pass1_5.c
@@ -219,15 +219,11 @@ if (ZEND_OPTIMIZER_PASS_1 & OPTIMIZATION_LEVEL) {
EG(in_execution) = 1;
EG(active_op_array) = op_array;
if (zend_get_constant("__COMPILER_HALT_OFFSET__", sizeof("__COMPILER_HALT_OFFSET__") - 1, &offset TSRMLS_CC)) {
+ zend_uint tv = ZEND_RESULT(opline).var;
+
literal_dtor(&ZEND_OP2_LITERAL(opline));
- ZEND_OP1_TYPE(opline) = IS_CONST;
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
- opline->op1.constant = zend_optimizer_add_literal(op_array, &offset TSRMLS_CC);
-#else
- ZEND_OP1_LITERAL(opline) = offset;
-#endif
- SET_UNUSED(opline->op2);
- opline->opcode = ZEND_QM_ASSIGN;
+ MAKE_NOP(opline);
+ replace_tmp_by_const(op_array, opline, tv, &offset TSRMLS_CC);
}
EG(active_op_array) = orig_op_array;
EG(in_execution) = orig_in_execution;
@@ -238,20 +234,15 @@ if (ZEND_OPTIMIZER_PASS_1 & OPTIMIZATION_LEVEL) {
ZEND_OP2_TYPE(opline) == IS_CONST &&
ZEND_OP2_LITERAL(opline).type == IS_STRING) {
/* substitute persistent constants */
+ zend_uint tv = ZEND_RESULT(opline).var;
zval c;
if (!zend_get_persistent_constant(Z_STRVAL(ZEND_OP2_LITERAL(opline)), Z_STRLEN(ZEND_OP2_LITERAL(opline)), &c, 1 TSRMLS_CC)) {
break;
}
literal_dtor(&ZEND_OP2_LITERAL(opline));
- ZEND_OP1_TYPE(opline) = IS_CONST;
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
- opline->op1.constant = zend_optimizer_add_literal(op_array, &c TSRMLS_CC);
-#else
- ZEND_OP1_LITERAL(opline) = c;
-#endif
- SET_UNUSED(opline->op2);
- opline->opcode = ZEND_QM_ASSIGN;
+ MAKE_NOP(opline);
+ replace_tmp_by_const(op_array, opline, tv, &c TSRMLS_CC);
}
break;
diff --git a/ext/opcache/Optimizer/zend_optimizer.c b/ext/opcache/Optimizer/zend_optimizer.c
index 28085cb441..fd0f77dbc8 100644
--- a/ext/opcache/Optimizer/zend_optimizer.c
+++ b/ext/opcache/Optimizer/zend_optimizer.c
@@ -1,292 +1,351 @@
-/*
- +----------------------------------------------------------------------+
- | Zend OPcache |
- +----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
- +----------------------------------------------------------------------+
- | This source file is subject to version 3.01 of the PHP license, |
- | that is bundled with this package in the file LICENSE, and is |
- | available through the world-wide-web at the following url: |
- | http://www.php.net/license/3_01.txt |
- | If you did not receive a copy of the PHP license and are unable to |
- | obtain it through the world-wide-web, please send a note to |
- | license@php.net so we can mail you a copy immediately. |
- +----------------------------------------------------------------------+
- | Authors: Andi Gutmans <andi@zend.com> |
- | Zeev Suraski <zeev@zend.com> |
- | Stanislav Malyshev <stas@zend.com> |
- | Dmitry Stogov <dmitry@zend.com> |
- +----------------------------------------------------------------------+
-*/
-
-#include "Optimizer/zend_optimizer.h"
-#include "Optimizer/zend_optimizer_internal.h"
-#include "zend_API.h"
-#include "zend_constants.h"
-#include "zend_execute.h"
-
-#define OPTIMIZATION_LEVEL \
- ZCG(accel_directives).optimization_level
-
-#if ZEND_EXTENSION_API_NO >= PHP_5_5_X_API_NO
-static int zend_optimizer_lookup_cv(zend_op_array *op_array, char* name, int name_len)
-{
- int i = 0;
- ulong hash_value = zend_inline_hash_func(name, name_len+1);
-
- while (i < op_array->last_var) {
- if (op_array->vars[i].name == name ||
- (op_array->vars[i].hash_value == hash_value &&
- op_array->vars[i].name_len == name_len &&
- memcmp(op_array->vars[i].name, name, name_len) == 0)) {
- return i;
- }
- i++;
- }
- i = op_array->last_var;
- op_array->last_var++;
- op_array->vars = erealloc(op_array->vars, op_array->last_var * sizeof(zend_compiled_variable));
- if (IS_INTERNED(name)) {
- op_array->vars[i].name = name;
- } else {
- op_array->vars[i].name = estrndup(name, name_len);
- }
- op_array->vars[i].name_len = name_len;
- op_array->vars[i].hash_value = hash_value;
- return i;
-}
-#endif
-
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
-int zend_optimizer_add_literal(zend_op_array *op_array, const zval *zv TSRMLS_DC)
-{
- int i = op_array->last_literal;
- op_array->last_literal++;
- if (i >= CG(context).literals_size) {
- CG(context).literals_size += 16; /* FIXME */
- op_array->literals = (zend_literal*)erealloc(op_array->literals, CG(context).literals_size * sizeof(zend_literal));
- }
- op_array->literals[i].constant = *zv;
- op_array->literals[i].hash_value = 0;
- op_array->literals[i].cache_slot = -1;
- Z_SET_REFCOUNT(op_array->literals[i].constant, 2);
- Z_SET_ISREF(op_array->literals[i].constant);
- return i;
-}
-
-# define LITERAL_LONG(op, val) do { \
- zval _c; \
- ZVAL_LONG(&_c, val); \
- op.constant = zend_optimizer_add_literal(op_array, &_c TSRMLS_CC); \
- } while (0)
-
-# define LITERAL_BOOL(op, val) do { \
- zval _c; \
- ZVAL_BOOL(&_c, val); \
- op.constant = zend_optimizer_add_literal(op_array, &_c TSRMLS_CC); \
- } while (0)
-
-# define literal_dtor(zv) do { \
- zval_dtor(zv); \
- Z_TYPE_P(zv) = IS_NULL; \
- } while (0)
-
-#define COPY_NODE(target, src) do { \
- target ## _type = src ## _type; \
- target = src; \
- } while (0)
-
-#else
-
-# define LITERAL_LONG(op, val) ZVAL_LONG(&op.u.constant, val)
-
-# define LITERAL_BOOL(op, val) ZVAL_BOOL(&op.u.constant, val)
-
-# define literal_dtor(zv) zval_dtor(zv)
-
-#define COPY_NODE(target, src) do { \
- target = src; \
- } while (0)
-
-#endif
-
-static void replace_tmp_by_const(zend_op_array *op_array,
- zend_op *opline,
- zend_uint var,
- zval *val
- TSRMLS_DC)
-{
- zend_op *end = op_array->opcodes + op_array->last;
-
- while (opline < end) {
- if (ZEND_OP1_TYPE(opline) == IS_TMP_VAR &&
- ZEND_OP1(opline).var == var) {
-
- if (opline->opcode == ZEND_FREE) {
- MAKE_NOP(opline);
- zval_dtor(val);
- } else {
- ZEND_OP1_TYPE(opline) = IS_CONST;
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
- if (Z_TYPE_P(val) == IS_STRING) {
- switch (opline->opcode) {
- case ZEND_INIT_STATIC_METHOD_CALL:
- case ZEND_CATCH:
- case ZEND_FETCH_CONSTANT:
- opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
- op_array->literals[opline->op1.constant].cache_slot = op_array->last_cache_slot++;
- zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
- zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- op_array->literals[opline->op1.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op1.constant+1].constant), Z_STRLEN(op_array->literals[opline->op1.constant+1].constant) + 1);
- break;
- case ZEND_DO_FCALL:
- zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
- opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
- op_array->literals[opline->op1.constant].cache_slot = op_array->last_cache_slot++;
- break;
- default:
- opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
- break;
- }
- } else {
- opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- }
-#else
- ZEND_OP1_LITERAL(opline) = *val;
-#endif
- }
- /* TMP_VAR my be used only once */
- break;
- }
-
- if (ZEND_OP2_TYPE(opline) == IS_TMP_VAR &&
- ZEND_OP2(opline).var == var) {
-
- ZEND_OP2_TYPE(opline) = IS_CONST;
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
- opline->op2.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- if (Z_TYPE_P(val) == IS_STRING) {
- Z_HASH_P(&ZEND_OP2_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP2_LITERAL(opline)), Z_STRLEN(ZEND_OP2_LITERAL(opline)) + 1);
- switch (opline->opcode) {
- case ZEND_FETCH_R:
- case ZEND_FETCH_W:
- case ZEND_FETCH_RW:
- case ZEND_FETCH_IS:
- case ZEND_FETCH_UNSET:
- case ZEND_FETCH_FUNC_ARG:
- case ZEND_FETCH_CLASS:
- case ZEND_INIT_FCALL_BY_NAME:
- /*case ZEND_INIT_NS_FCALL_BY_NAME:*/
- case ZEND_UNSET_VAR:
- case ZEND_ISSET_ISEMPTY_VAR:
- case ZEND_ADD_INTERFACE:
- case ZEND_ADD_TRAIT:
- op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot++;
- zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
- zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- op_array->literals[opline->op2.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op2.constant+1].constant), Z_STRLEN(op_array->literals[opline->op2.constant+1].constant) + 1);
- break;
- case ZEND_INIT_METHOD_CALL:
- case ZEND_INIT_STATIC_METHOD_CALL:
- zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
- zend_optimizer_add_literal(op_array, val TSRMLS_CC);
- op_array->literals[opline->op2.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op2.constant+1].constant), Z_STRLEN(op_array->literals[opline->op2.constant+1].constant) + 1);
- /* break missing intentionally */
- /*case ZEND_FETCH_CONSTANT:*/
- case ZEND_ASSIGN_OBJ:
- case ZEND_FETCH_OBJ_R:
- case ZEND_FETCH_OBJ_W:
- case ZEND_FETCH_OBJ_RW:
- case ZEND_FETCH_OBJ_IS:
- case ZEND_FETCH_OBJ_UNSET:
- case ZEND_FETCH_OBJ_FUNC_ARG:
- case ZEND_UNSET_OBJ:
- case ZEND_PRE_INC_OBJ:
- case ZEND_PRE_DEC_OBJ:
- case ZEND_POST_INC_OBJ:
- case ZEND_POST_DEC_OBJ:
- case ZEND_ISSET_ISEMPTY_PROP_OBJ:
- op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot;
- op_array->last_cache_slot += 2;
- break;
- case ZEND_ASSIGN_ADD:
- case ZEND_ASSIGN_SUB:
- case ZEND_ASSIGN_MUL:
- case ZEND_ASSIGN_DIV:
- case ZEND_ASSIGN_MOD:
- case ZEND_ASSIGN_SL:
- case ZEND_ASSIGN_SR:
- case ZEND_ASSIGN_CONCAT:
- case ZEND_ASSIGN_BW_OR:
- case ZEND_ASSIGN_BW_AND:
- case ZEND_ASSIGN_BW_XOR:
- if (opline->extended_value == ZEND_ASSIGN_OBJ) {
- op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot;
- op_array->last_cache_slot += 2;
- }
- break;
- default:
- break;
- }
- }
-#else
- ZEND_OP2_LITERAL(opline) = *val;
-#endif
- break;
- }
- opline++;
- }
-}
-
-#include "Optimizer/nop_removal.c"
-#include "Optimizer/block_pass.c"
-#include "Optimizer/optimize_temp_vars_5.c"
-
-void zend_optimizer(zend_op_array *op_array TSRMLS_DC)
-{
- if (op_array->type == ZEND_EVAL_CODE ||
- (op_array->fn_flags & ZEND_ACC_INTERACTIVE)) {
- return;
- }
-
- /* pass 1
- * - substitute persistent constants (true, false, null, etc)
- * - perform compile-time evaluation of constant binary and unary operations
- * - optimize series of ADD_STRING and/or ADD_CHAR
- * - convert CAST(IS_BOOL,x) into BOOL(x)
- * - convert INTI_FCALL_BY_NAME + DO_FCALL_BY_NAME into DO_FCALL
- */
-#include "Optimizer/pass1_5.c"
-
- /* pass 2:
- * - convert non-numeric constants to numeric constants in numeric operators
- * - optimize constant conditional JMPs
- * - optimize static BRKs and CONTs
- */
-#include "Optimizer/pass2.c"
-
- /* pass 3:
- * - optimize $i = $i+expr to $i+=expr
- * - optimize series of JMPs
- * - change $i++ to ++$i where possible
- */
-#include "Optimizer/pass3.c"
-
- /* pass 5:
- * - CFG optimization
- */
-#include "Optimizer/pass5.c"
-
- /* pass 9:
- * - Optimize temp variables usage
- */
-#include "Optimizer/pass9.c"
-
- /* pass 10:
- * - remove NOPs
- */
-#include "Optimizer/pass10.c"
-}
+/*
+ +----------------------------------------------------------------------+
+ | Zend OPcache |
+ +----------------------------------------------------------------------+
+ | Copyright (c) 1998-2014 The PHP Group |
+ +----------------------------------------------------------------------+
+ | This source file is subject to version 3.01 of the PHP license, |
+ | that is bundled with this package in the file LICENSE, and is |
+ | available through the world-wide-web at the following url: |
+ | http://www.php.net/license/3_01.txt |
+ | If you did not receive a copy of the PHP license and are unable to |
+ | obtain it through the world-wide-web, please send a note to |
+ | license@php.net so we can mail you a copy immediately. |
+ +----------------------------------------------------------------------+
+ | Authors: Andi Gutmans <andi@zend.com> |
+ | Zeev Suraski <zeev@zend.com> |
+ | Stanislav Malyshev <stas@zend.com> |
+ | Dmitry Stogov <dmitry@zend.com> |
+ +----------------------------------------------------------------------+
+*/
+
+#include "php.h"
+#include "Optimizer/zend_optimizer.h"
+#include "Optimizer/zend_optimizer_internal.h"
+#include "zend_API.h"
+#include "zend_constants.h"
+#include "zend_execute.h"
+
+#define OPTIMIZATION_LEVEL \
+ ZCG(accel_directives).optimization_level
+
+#if ZEND_EXTENSION_API_NO >= PHP_5_5_X_API_NO
+static int zend_optimizer_lookup_cv(zend_op_array *op_array, char* name, int name_len)
+{
+ int i = 0;
+ ulong hash_value = zend_inline_hash_func(name, name_len+1);
+
+ while (i < op_array->last_var) {
+ if (op_array->vars[i].name == name ||
+ (op_array->vars[i].hash_value == hash_value &&
+ op_array->vars[i].name_len == name_len &&
+ memcmp(op_array->vars[i].name, name, name_len) == 0)) {
+ return i;
+ }
+ i++;
+ }
+ i = op_array->last_var;
+ op_array->last_var++;
+ op_array->vars = erealloc(op_array->vars, op_array->last_var * sizeof(zend_compiled_variable));
+ if (IS_INTERNED(name)) {
+ op_array->vars[i].name = name;
+ } else {
+ op_array->vars[i].name = estrndup(name, name_len);
+ }
+ op_array->vars[i].name_len = name_len;
+ op_array->vars[i].hash_value = hash_value;
+ return i;
+}
+#endif
+
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+int zend_optimizer_add_literal(zend_op_array *op_array, const zval *zv TSRMLS_DC)
+{
+ int i = op_array->last_literal;
+ op_array->last_literal++;
+ if (i >= CG(context).literals_size) {
+ CG(context).literals_size += 16; /* FIXME */
+ op_array->literals = (zend_literal*)erealloc(op_array->literals, CG(context).literals_size * sizeof(zend_literal));
+ }
+ op_array->literals[i].constant = *zv;
+ op_array->literals[i].hash_value = 0;
+ op_array->literals[i].cache_slot = -1;
+ Z_SET_REFCOUNT(op_array->literals[i].constant, 2);
+ Z_SET_ISREF(op_array->literals[i].constant);
+ return i;
+}
+
+# define LITERAL_LONG(op, val) do { \
+ zval _c; \
+ ZVAL_LONG(&_c, val); \
+ op.constant = zend_optimizer_add_literal(op_array, &_c TSRMLS_CC); \
+ } while (0)
+
+# define LITERAL_BOOL(op, val) do { \
+ zval _c; \
+ ZVAL_BOOL(&_c, val); \
+ op.constant = zend_optimizer_add_literal(op_array, &_c TSRMLS_CC); \
+ } while (0)
+
+# define literal_dtor(zv) do { \
+ zval_dtor(zv); \
+ Z_TYPE_P(zv) = IS_NULL; \
+ } while (0)
+
+#define COPY_NODE(target, src) do { \
+ target ## _type = src ## _type; \
+ target = src; \
+ } while (0)
+
+#else
+
+# define LITERAL_LONG(op, val) ZVAL_LONG(&op.u.constant, val)
+
+# define LITERAL_BOOL(op, val) ZVAL_BOOL(&op.u.constant, val)
+
+# define literal_dtor(zv) zval_dtor(zv)
+
+#define COPY_NODE(target, src) do { \
+ target = src; \
+ } while (0)
+
+#endif
+
+static void update_op1_const(zend_op_array *op_array,
+ zend_op *opline,
+ zval *val TSRMLS_DC)
+{
+ if (opline->opcode == ZEND_FREE) {
+ MAKE_NOP(opline);
+ zval_dtor(val);
+ } else {
+ ZEND_OP1_TYPE(opline) = IS_CONST;
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ if (Z_TYPE_P(val) == IS_STRING) {
+ switch (opline->opcode) {
+ case ZEND_INIT_STATIC_METHOD_CALL:
+ case ZEND_CATCH:
+ case ZEND_FETCH_CONSTANT:
+ opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
+ op_array->literals[opline->op1.constant].cache_slot = op_array->last_cache_slot++;
+ zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
+ zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ op_array->literals[opline->op1.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op1.constant+1].constant), Z_STRLEN(op_array->literals[opline->op1.constant+1].constant) + 1);
+ break;
+ case ZEND_DO_FCALL:
+ zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
+ opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
+ op_array->literals[opline->op1.constant].cache_slot = op_array->last_cache_slot++;
+ break;
+ default:
+ opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ Z_HASH_P(&ZEND_OP1_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP1_LITERAL(opline)), Z_STRLEN(ZEND_OP1_LITERAL(opline)) + 1);
+ break;
+ }
+ } else {
+ opline->op1.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ }
+#else
+ ZEND_OP1_LITERAL(opline) = *val;
+#endif
+ }
+}
+
+static void update_op2_const(zend_op_array *op_array,
+ zend_op *opline,
+ zval *val TSRMLS_DC)
+{
+ ZEND_OP2_TYPE(opline) = IS_CONST;
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ opline->op2.constant = zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ if (Z_TYPE_P(val) == IS_STRING) {
+ Z_HASH_P(&ZEND_OP2_LITERAL(opline)) = zend_hash_func(Z_STRVAL(ZEND_OP2_LITERAL(opline)), Z_STRLEN(ZEND_OP2_LITERAL(opline)) + 1);
+ switch (opline->opcode) {
+ case ZEND_FETCH_R:
+ case ZEND_FETCH_W:
+ case ZEND_FETCH_RW:
+ case ZEND_FETCH_IS:
+ case ZEND_FETCH_UNSET:
+ case ZEND_FETCH_FUNC_ARG:
+ case ZEND_FETCH_CLASS:
+ case ZEND_INIT_FCALL_BY_NAME:
+ /*case ZEND_INIT_NS_FCALL_BY_NAME:*/
+ case ZEND_UNSET_VAR:
+ case ZEND_ISSET_ISEMPTY_VAR:
+ case ZEND_ADD_INTERFACE:
+ case ZEND_ADD_TRAIT:
+ op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot++;
+ zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
+ zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ op_array->literals[opline->op2.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op2.constant+1].constant), Z_STRLEN(op_array->literals[opline->op2.constant+1].constant) + 1);
+ break;
+ case ZEND_INIT_METHOD_CALL:
+ case ZEND_INIT_STATIC_METHOD_CALL:
+ zend_str_tolower(Z_STRVAL_P(val), Z_STRLEN_P(val));
+ zend_optimizer_add_literal(op_array, val TSRMLS_CC);
+ op_array->literals[opline->op2.constant+1].hash_value = zend_hash_func(Z_STRVAL(op_array->literals[opline->op2.constant+1].constant), Z_STRLEN(op_array->literals[opline->op2.constant+1].constant) + 1);
+ /* break missing intentionally */
+ /*case ZEND_FETCH_CONSTANT:*/
+ case ZEND_ASSIGN_OBJ:
+ case ZEND_FETCH_OBJ_R:
+ case ZEND_FETCH_OBJ_W:
+ case ZEND_FETCH_OBJ_RW:
+ case ZEND_FETCH_OBJ_IS:
+ case ZEND_FETCH_OBJ_UNSET:
+ case ZEND_FETCH_OBJ_FUNC_ARG:
+ case ZEND_UNSET_OBJ:
+ case ZEND_PRE_INC_OBJ:
+ case ZEND_PRE_DEC_OBJ:
+ case ZEND_POST_INC_OBJ:
+ case ZEND_POST_DEC_OBJ:
+ case ZEND_ISSET_ISEMPTY_PROP_OBJ:
+ op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot;
+ op_array->last_cache_slot += 2;
+ break;
+ case ZEND_ASSIGN_ADD:
+ case ZEND_ASSIGN_SUB:
+ case ZEND_ASSIGN_MUL:
+ case ZEND_ASSIGN_DIV:
+ case ZEND_ASSIGN_MOD:
+ case ZEND_ASSIGN_SL:
+ case ZEND_ASSIGN_SR:
+ case ZEND_ASSIGN_CONCAT:
+ case ZEND_ASSIGN_BW_OR:
+ case ZEND_ASSIGN_BW_AND:
+ case ZEND_ASSIGN_BW_XOR:
+ if (opline->extended_value == ZEND_ASSIGN_OBJ) {
+ op_array->literals[opline->op2.constant].cache_slot = op_array->last_cache_slot;
+ op_array->last_cache_slot += 2;
+ }
+ break;
+#if ZEND_EXTENSION_API_NO >= PHP_5_4_X_API_NO
+ case ZEND_OP_DATA:
+ if ((opline-1)->opcode == ZEND_ASSIGN_DIM ||
+ ((opline-1)->extended_value == ZEND_ASSIGN_DIM &&
+ ((opline-1)->opcode == ZEND_ASSIGN_ADD ||
+ (opline-1)->opcode == ZEND_ASSIGN_SUB ||
+ (opline-1)->opcode == ZEND_ASSIGN_MUL ||
+ (opline-1)->opcode == ZEND_ASSIGN_DIV ||
+ (opline-1)->opcode == ZEND_ASSIGN_MOD ||
+ (opline-1)->opcode == ZEND_ASSIGN_SL ||
+ (opline-1)->opcode == ZEND_ASSIGN_SR ||
+ (opline-1)->opcode == ZEND_ASSIGN_CONCAT ||
+ (opline-1)->opcode == ZEND_ASSIGN_BW_OR ||
+ (opline-1)->opcode == ZEND_ASSIGN_BW_AND ||
+ (opline-1)->opcode == ZEND_ASSIGN_BW_XOR))) {
+ goto check_numeric;
+ }
+ break;
+ case ZEND_ISSET_ISEMPTY_DIM_OBJ:
+ case ZEND_ADD_ARRAY_ELEMENT:
+ case ZEND_INIT_ARRAY:
+ case ZEND_UNSET_DIM:
+ case ZEND_FETCH_DIM_R:
+ case ZEND_FETCH_DIM_W:
+ case ZEND_FETCH_DIM_RW:
+ case ZEND_FETCH_DIM_IS:
+ case ZEND_FETCH_DIM_FUNC_ARG:
+ case ZEND_FETCH_DIM_UNSET:
+ case ZEND_FETCH_DIM_TMP_VAR:
+check_numeric:
+ {
+ ulong index;
+ int numeric = 0;
+
+ ZEND_HANDLE_NUMERIC_EX(Z_STRVAL_P(val), Z_STRLEN_P(val)+1, index, numeric = 1);
+ if (numeric) {
+ zval_dtor(val);
+ ZVAL_LONG(val, index);
+ op_array->literals[opline->op2.constant].constant = *val;
+ }
+ }
+ break;
+#endif
+ default:
+ break;
+ }
+ }
+#else
+ ZEND_OP2_LITERAL(opline) = *val;
+#endif
+}
+
+static void replace_tmp_by_const(zend_op_array *op_array,
+ zend_op *opline,
+ zend_uint var,
+ zval *val
+ TSRMLS_DC)
+{
+ zend_op *end = op_array->opcodes + op_array->last;
+
+ while (opline < end) {
+ if (ZEND_OP1_TYPE(opline) == IS_TMP_VAR &&
+ ZEND_OP1(opline).var == var) {
+
+ update_op1_const(op_array, opline, val TSRMLS_CC);
+ /* TMP_VAR my be used only once */
+ break;
+ }
+
+ if (ZEND_OP2_TYPE(opline) == IS_TMP_VAR &&
+ ZEND_OP2(opline).var == var) {
+
+ update_op2_const(op_array, opline, val TSRMLS_CC);
+ /* TMP_VAR my be used only once */
+ break;
+ }
+ opline++;
+ }
+}
+
+#include "Optimizer/nop_removal.c"
+#include "Optimizer/block_pass.c"
+#include "Optimizer/optimize_temp_vars_5.c"
+
+void zend_optimizer(zend_op_array *op_array TSRMLS_DC)
+{
+ if (op_array->type == ZEND_EVAL_CODE ||
+ (op_array->fn_flags & ZEND_ACC_INTERACTIVE)) {
+ return;
+ }
+
+ /* pass 1
+ * - substitute persistent constants (true, false, null, etc)
+ * - perform compile-time evaluation of constant binary and unary operations
+ * - optimize series of ADD_STRING and/or ADD_CHAR
+ * - convert CAST(IS_BOOL,x) into BOOL(x)
+ * - convert INTI_FCALL_BY_NAME + DO_FCALL_BY_NAME into DO_FCALL
+ */
+#include "Optimizer/pass1_5.c"
+
+ /* pass 2:
+ * - convert non-numeric constants to numeric constants in numeric operators
+ * - optimize constant conditional JMPs
+ * - optimize static BRKs and CONTs
+ */
+#include "Optimizer/pass2.c"
+
+ /* pass 3:
+ * - optimize $i = $i+expr to $i+=expr
+ * - optimize series of JMPs
+ * - change $i++ to ++$i where possible
+ */
+#include "Optimizer/pass3.c"
+
+ /* pass 5:
+ * - CFG optimization
+ */
+#include "Optimizer/pass5.c"
+
+ /* pass 9:
+ * - Optimize temp variables usage
+ */
+#include "Optimizer/pass9.c"
+
+ /* pass 10:
+ * - remove NOPs
+ */
+#include "Optimizer/pass10.c"
+}
diff --git a/ext/opcache/Optimizer/zend_optimizer.h b/ext/opcache/Optimizer/zend_optimizer.h
index 98275a20aa..7802d6df98 100644
--- a/ext/opcache/Optimizer/zend_optimizer.h
+++ b/ext/opcache/Optimizer/zend_optimizer.h
@@ -1,49 +1,49 @@
-/*
- +----------------------------------------------------------------------+
- | Zend OPcache |
- +----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
- +----------------------------------------------------------------------+
- | This source file is subject to version 3.01 of the PHP license, |
- | that is bundled with this package in the file LICENSE, and is |
- | available through the world-wide-web at the following url: |
- | http://www.php.net/license/3_01.txt |
- | If you did not receive a copy of the PHP license and are unable to |
- | obtain it through the world-wide-web, please send a note to |
- | license@php.net so we can mail you a copy immediately. |
- +----------------------------------------------------------------------+
- | Authors: Andi Gutmans <andi@zend.com> |
- | Zeev Suraski <zeev@zend.com> |
- | Stanislav Malyshev <stas@zend.com> |
- | Dmitry Stogov <dmitry@zend.com> |
- +----------------------------------------------------------------------+
-*/
-
-#ifndef ZEND_OPTIMIZER_H
-#define ZEND_OPTIMIZER_H
-
-#include "zend.h"
-#include "zend_compile.h"
-
-#define ZEND_OPTIMIZER_PASS_1 (1<<0) /* CSE, STRING construction */
-#define ZEND_OPTIMIZER_PASS_2 (1<<1) /* Constant conversion and jumps */
-#define ZEND_OPTIMIZER_PASS_3 (1<<2) /* ++, +=, series of jumps */
-#define ZEND_OPTIMIZER_PASS_4 (1<<3)
-#define ZEND_OPTIMIZER_PASS_5 (1<<4) /* CFG based optimization */
-#define ZEND_OPTIMIZER_PASS_6 (1<<5)
-#define ZEND_OPTIMIZER_PASS_7 (1<<6)
-#define ZEND_OPTIMIZER_PASS_8 (1<<7)
-#define ZEND_OPTIMIZER_PASS_9 (1<<8) /* TMP VAR usage */
-#define ZEND_OPTIMIZER_PASS_10 (1<<9) /* NOP removal */
-#define ZEND_OPTIMIZER_PASS_11 (1<<10)
-#define ZEND_OPTIMIZER_PASS_12 (1<<11)
-#define ZEND_OPTIMIZER_PASS_13 (1<<12)
-#define ZEND_OPTIMIZER_PASS_14 (1<<13)
-
-#define ZEND_OPTIMIZER_ALL_PASSES 0xFFFFFFFF
-
-#define DEFAULT_OPTIMIZATION_LEVEL "0xFFFFFFFF"
-
-void zend_optimizer(zend_op_array *op_array TSRMLS_DC);
-
-#endif
+/*
+ +----------------------------------------------------------------------+
+ | Zend OPcache |
+ +----------------------------------------------------------------------+
+ | Copyright (c) 1998-2014 The PHP Group |
+ +----------------------------------------------------------------------+
+ | This source file is subject to version 3.01 of the PHP license, |
+ | that is bundled with this package in the file LICENSE, and is |
+ | available through the world-wide-web at the following url: |
+ | http://www.php.net/license/3_01.txt |
+ | If you did not receive a copy of the PHP license and are unable to |
+ | obtain it through the world-wide-web, please send a note to |
+ | license@php.net so we can mail you a copy immediately. |
+ +----------------------------------------------------------------------+
+ | Authors: Andi Gutmans <andi@zend.com> |
+ | Zeev Suraski <zeev@zend.com> |
+ | Stanislav Malyshev <stas@zend.com> |
+ | Dmitry Stogov <dmitry@zend.com> |
+ +----------------------------------------------------------------------+
+*/
+
+#ifndef ZEND_OPTIMIZER_H
+#define ZEND_OPTIMIZER_H
+
+#include "zend.h"
+#include "zend_compile.h"
+
+#define ZEND_OPTIMIZER_PASS_1 (1<<0) /* CSE, STRING construction */
+#define ZEND_OPTIMIZER_PASS_2 (1<<1) /* Constant conversion and jumps */
+#define ZEND_OPTIMIZER_PASS_3 (1<<2) /* ++, +=, series of jumps */
+#define ZEND_OPTIMIZER_PASS_4 (1<<3)
+#define ZEND_OPTIMIZER_PASS_5 (1<<4) /* CFG based optimization */
+#define ZEND_OPTIMIZER_PASS_6 (1<<5)
+#define ZEND_OPTIMIZER_PASS_7 (1<<6)
+#define ZEND_OPTIMIZER_PASS_8 (1<<7)
+#define ZEND_OPTIMIZER_PASS_9 (1<<8) /* TMP VAR usage */
+#define ZEND_OPTIMIZER_PASS_10 (1<<9) /* NOP removal */
+#define ZEND_OPTIMIZER_PASS_11 (1<<10)
+#define ZEND_OPTIMIZER_PASS_12 (1<<11)
+#define ZEND_OPTIMIZER_PASS_13 (1<<12)
+#define ZEND_OPTIMIZER_PASS_14 (1<<13)
+
+#define ZEND_OPTIMIZER_ALL_PASSES 0xFFFFFFFF
+
+#define DEFAULT_OPTIMIZATION_LEVEL "0xFFFFFFFF"
+
+void zend_optimizer(zend_op_array *op_array TSRMLS_DC);
+
+#endif
diff --git a/ext/opcache/Optimizer/zend_optimizer_internal.h b/ext/opcache/Optimizer/zend_optimizer_internal.h
index 616bdf74f6..d4baf531e1 100644
--- a/ext/opcache/Optimizer/zend_optimizer_internal.h
+++ b/ext/opcache/Optimizer/zend_optimizer_internal.h
@@ -1,86 +1,86 @@
-/*
- +----------------------------------------------------------------------+
- | Zend OPcache |
- +----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
- +----------------------------------------------------------------------+
- | This source file is subject to version 3.01 of the PHP license, |
- | that is bundled with this package in the file LICENSE, and is |
- | available through the world-wide-web at the following url: |
- | http://www.php.net/license/3_01.txt |
- | If you did not receive a copy of the PHP license and are unable to |
- | obtain it through the world-wide-web, please send a note to |
- | license@php.net so we can mail you a copy immediately. |
- +----------------------------------------------------------------------+
- | Authors: Andi Gutmans <andi@zend.com> |
- | Zeev Suraski <zeev@zend.com> |
- | Stanislav Malyshev <stas@zend.com> |
- | Dmitry Stogov <dmitry@zend.com> |
- +----------------------------------------------------------------------+
-*/
-
-#ifndef ZEND_OPTIMIZER_INTERNAL_H
-#define ZEND_OPTIMIZER_INTERNAL_H
-
-#include "ZendAccelerator.h"
-
-#if ZEND_EXTENSION_API_NO > PHP_5_4_X_API_NO
-# define VAR_NUM(v) ((zend_uint)(EX_TMP_VAR_NUM(0, 0) - EX_TMP_VAR(0, v)))
-# define NUM_VAR(v) ((zend_uint)(zend_uintptr_t)EX_TMP_VAR_NUM(0, v))
-#elif ZEND_EXTENSION_API_NO > PHP_5_2_X_API_NO
-# define VAR_NUM(v) ((v)/ZEND_MM_ALIGNED_SIZE(sizeof(temp_variable)))
-# define NUM_VAR(v) ((v)*ZEND_MM_ALIGNED_SIZE(sizeof(temp_variable)))
-#else
-# define VAR_NUM(v) ((v)/(sizeof(temp_variable)))
-# define NUM_VAR(v) ((v)*(sizeof(temp_variable)))
-#endif
-
-#define INV_COND(op) ((op) == ZEND_JMPZ ? ZEND_JMPNZ : ZEND_JMPZ)
-#define INV_EX_COND(op) ((op) == ZEND_JMPZ_EX ? ZEND_JMPNZ : ZEND_JMPZ)
-#define INV_COND_EX(op) ((op) == ZEND_JMPZ ? ZEND_JMPNZ_EX : ZEND_JMPZ_EX)
-#define INV_EX_COND_EX(op) ((op) == ZEND_JMPZ_EX ? ZEND_JMPNZ_EX : ZEND_JMPZ_EX)
-
-#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
-# define MAKE_NOP(opline) { opline->opcode = ZEND_NOP; memset(&opline->result,0,sizeof(opline->result)); memset(&opline->op1,0,sizeof(opline->op1)); memset(&opline->op2,0,sizeof(opline->op2)); opline->result_type=opline->op1_type=opline->op2_type=IS_UNUSED; opline->handler = zend_opcode_handlers[ZEND_NOP]; }
-# define RESULT_USED(op) (((op->result_type & IS_VAR) && !(op->result_type & EXT_TYPE_UNUSED)) || op->result_type == IS_TMP_VAR)
-# define RESULT_UNUSED(op) ((op->result_type & EXT_TYPE_UNUSED) != 0)
-# define SAME_VAR(op1, op2) ((((op1 ## _type & IS_VAR) && (op2 ## _type & IS_VAR)) || (op1 ## _type == IS_TMP_VAR && op2 ## _type == IS_TMP_VAR)) && op1.var == op2.var)
-#else
-# define MAKE_NOP(opline) { opline->opcode = ZEND_NOP; memset(&opline->result,0,sizeof(znode)); memset(&opline->op1,0,sizeof(znode)); memset(&opline->op2,0,sizeof(znode)); opline->result.op_type=opline->op1.op_type=opline->op2.op_type=IS_UNUSED; opline->handler = zend_opcode_handlers[ZEND_NOP]; }
-# define RESULT_USED(op) ((op->result.op_type == IS_VAR && (op->result.u.EA.type & EXT_TYPE_UNUSED) == 0) || (op->result.op_type == IS_TMP_VAR))
-# define RESULT_UNUSED(op) ((op->result.op_type == IS_VAR) && (op->result.u.EA.type == EXT_TYPE_UNUSED))
-# define SAME_VAR(op1, op2) (((op1.op_type == IS_VAR && op2.op_type == IS_VAR) || (op1.op_type == IS_TMP_VAR && op2.op_type == IS_TMP_VAR)) && op1.u.var == op2.u.var)
-#endif
-
-typedef struct _zend_code_block zend_code_block;
-typedef struct _zend_block_source zend_block_source;
-
-struct _zend_code_block {
- int access;
- zend_op *start_opline;
- int start_opline_no;
- int len;
- zend_code_block *op1_to;
- zend_code_block *op2_to;
- zend_code_block *ext_to;
- zend_code_block *follow_to;
- zend_code_block *next;
- zend_block_source *sources;
- zend_bool protected; /* don't merge this block with others */
-};
-
-typedef struct _zend_cfg {
- zend_code_block *blocks;
- zend_code_block **try;
- zend_code_block **catch;
- zend_code_block **loop_start;
- zend_code_block **loop_cont;
- zend_code_block **loop_brk;
-} zend_cfg;
-
-struct _zend_block_source {
- zend_code_block *from;
- zend_block_source *next;
-};
-
-#endif
+/*
+ +----------------------------------------------------------------------+
+ | Zend OPcache |
+ +----------------------------------------------------------------------+
+ | Copyright (c) 1998-2014 The PHP Group |
+ +----------------------------------------------------------------------+
+ | This source file is subject to version 3.01 of the PHP license, |
+ | that is bundled with this package in the file LICENSE, and is |
+ | available through the world-wide-web at the following url: |
+ | http://www.php.net/license/3_01.txt |
+ | If you did not receive a copy of the PHP license and are unable to |
+ | obtain it through the world-wide-web, please send a note to |
+ | license@php.net so we can mail you a copy immediately. |
+ +----------------------------------------------------------------------+
+ | Authors: Andi Gutmans <andi@zend.com> |
+ | Zeev Suraski <zeev@zend.com> |
+ | Stanislav Malyshev <stas@zend.com> |
+ | Dmitry Stogov <dmitry@zend.com> |
+ +----------------------------------------------------------------------+
+*/
+
+#ifndef ZEND_OPTIMIZER_INTERNAL_H
+#define ZEND_OPTIMIZER_INTERNAL_H
+
+#include "ZendAccelerator.h"
+
+#if ZEND_EXTENSION_API_NO > PHP_5_4_X_API_NO
+# define VAR_NUM(v) ((zend_uint)(EX_TMP_VAR_NUM(0, 0) - EX_TMP_VAR(0, v)))
+# define NUM_VAR(v) ((zend_uint)(zend_uintptr_t)EX_TMP_VAR_NUM(0, v))
+#elif ZEND_EXTENSION_API_NO > PHP_5_2_X_API_NO
+# define VAR_NUM(v) ((v)/ZEND_MM_ALIGNED_SIZE(sizeof(temp_variable)))
+# define NUM_VAR(v) ((v)*ZEND_MM_ALIGNED_SIZE(sizeof(temp_variable)))
+#else
+# define VAR_NUM(v) ((v)/(sizeof(temp_variable)))
+# define NUM_VAR(v) ((v)*(sizeof(temp_variable)))
+#endif
+
+#define INV_COND(op) ((op) == ZEND_JMPZ ? ZEND_JMPNZ : ZEND_JMPZ)
+#define INV_EX_COND(op) ((op) == ZEND_JMPZ_EX ? ZEND_JMPNZ : ZEND_JMPZ)
+#define INV_COND_EX(op) ((op) == ZEND_JMPZ ? ZEND_JMPNZ_EX : ZEND_JMPZ_EX)
+#define INV_EX_COND_EX(op) ((op) == ZEND_JMPZ_EX ? ZEND_JMPNZ_EX : ZEND_JMPZ_EX)
+
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+# define MAKE_NOP(opline) { opline->opcode = ZEND_NOP; memset(&opline->result,0,sizeof(opline->result)); memset(&opline->op1,0,sizeof(opline->op1)); memset(&opline->op2,0,sizeof(opline->op2)); opline->result_type=opline->op1_type=opline->op2_type=IS_UNUSED; opline->handler = zend_opcode_handlers[ZEND_NOP]; }
+# define RESULT_USED(op) (((op->result_type & IS_VAR) && !(op->result_type & EXT_TYPE_UNUSED)) || op->result_type == IS_TMP_VAR)
+# define RESULT_UNUSED(op) ((op->result_type & EXT_TYPE_UNUSED) != 0)
+# define SAME_VAR(op1, op2) ((((op1 ## _type & IS_VAR) && (op2 ## _type & IS_VAR)) || (op1 ## _type == IS_TMP_VAR && op2 ## _type == IS_TMP_VAR)) && op1.var == op2.var)
+#else
+# define MAKE_NOP(opline) { opline->opcode = ZEND_NOP; memset(&opline->result,0,sizeof(znode)); memset(&opline->op1,0,sizeof(znode)); memset(&opline->op2,0,sizeof(znode)); opline->result.op_type=opline->op1.op_type=opline->op2.op_type=IS_UNUSED; opline->handler = zend_opcode_handlers[ZEND_NOP]; }
+# define RESULT_USED(op) ((op->result.op_type == IS_VAR && (op->result.u.EA.type & EXT_TYPE_UNUSED) == 0) || (op->result.op_type == IS_TMP_VAR))
+# define RESULT_UNUSED(op) ((op->result.op_type == IS_VAR) && (op->result.u.EA.type == EXT_TYPE_UNUSED))
+# define SAME_VAR(op1, op2) (((op1.op_type == IS_VAR && op2.op_type == IS_VAR) || (op1.op_type == IS_TMP_VAR && op2.op_type == IS_TMP_VAR)) && op1.u.var == op2.u.var)
+#endif
+
+typedef struct _zend_code_block zend_code_block;
+typedef struct _zend_block_source zend_block_source;
+
+struct _zend_code_block {
+ int access;
+ zend_op *start_opline;
+ int start_opline_no;
+ int len;
+ zend_code_block *op1_to;
+ zend_code_block *op2_to;
+ zend_code_block *ext_to;
+ zend_code_block *follow_to;
+ zend_code_block *next;
+ zend_block_source *sources;
+ zend_bool protected; /* don't merge this block with others */
+};
+
+typedef struct _zend_cfg {
+ zend_code_block *blocks;
+ zend_code_block **try;
+ zend_code_block **catch;
+ zend_code_block **loop_start;
+ zend_code_block **loop_cont;
+ zend_code_block **loop_brk;
+} zend_cfg;
+
+struct _zend_block_source {
+ zend_code_block *from;
+ zend_block_source *next;
+};
+
+#endif
diff --git a/ext/opcache/README b/ext/opcache/README
index 2e30d92c00..693a7b4e3c 100644
--- a/ext/opcache/README
+++ b/ext/opcache/README
@@ -40,7 +40,8 @@ after OPcache.
Speed Tuning
-------------
-We recommend the following configuration options for best performance.
+We recommend the following configuration options for best performance
+in a production environment.
opcache.memory_consumption=128
opcache.interned_strings_buffer=8
@@ -59,6 +60,9 @@ opcache.enable_file_override=1
In some cases you may like to prefer enabling/disabling some features
to avoid incompatibilities at the cost of some performance degradation.
+For development environment we would recommend setting opcache.revalidate_freq
+into 0.
+
Configuration Directives
------------------------
@@ -103,6 +107,12 @@ opcache.revalidate_freq (default "2")
memory storage allocation. ("1" means validate once per second, but only
once per request. "0" means always validate)
+opcache.file_update_protection (default "2")
+ Prevents caching files that are less than this number of seconds old.
+ It protects from caching of incompletely updated files. In case all file
+ updates on your site are atomic, you may increase performance setting it
+ to "0".
+
opcache.revalidate_path (default "0")
Enables or disables file search in include_path optimization
If the file search is disabled and a cached file is found that uses
diff --git a/ext/opcache/ZendAccelerator.c b/ext/opcache/ZendAccelerator.c
index 8cee80f776..44064004f8 100644
--- a/ext/opcache/ZendAccelerator.c
+++ b/ext/opcache/ZendAccelerator.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -37,7 +37,6 @@
#include "zend_API.h"
#include "zend_ini.h"
#include "TSRM/tsrm_virtual_cwd.h"
-#include "ext/phar/php_phar.h"
#include "zend_accelerator_util_funcs.h"
#include "zend_accelerator_hash.h"
@@ -145,21 +144,6 @@ static inline int is_cacheable_stream_path(const char *filename)
memcmp(filename, "phar://", sizeof("phar://") - 1) == 0;
}
-static inline int is_phar_relative_alias_path(const char *filename, char **alias, int *alias_len)
-{
- if (memcmp(filename, "phar://", sizeof("phar://") - 1) == 0
- && filename[sizeof("phar://") - 1] != '\0' && filename[sizeof("phar://") - 1] != '/') {
- char *slash;
- *alias = (char*)filename + sizeof("phar://") - 1;
- slash = strstr(*alias, "/");
- if (slash) {
- *alias_len = slash - *alias;
- return 1;
- }
- }
- return 0;
-}
-
/* O+ overrides PHP chdir() function and remembers the current working directory
* in ZCG(cwd) and ZCG(cwd_len). Later accel_getcwd() can use stored value and
* avoid getcwd() call.
@@ -354,6 +338,7 @@ const char *accel_new_interned_string(const char *arKey, int nKeyLength, int fre
if (ZCSG(interned_strings_top) + ZEND_MM_ALIGNED_SIZE(sizeof(Bucket) + nKeyLength) >=
ZCSG(interned_strings_end)) {
/* no memory, return the same non-interned string */
+ zend_accel_error(ACCEL_LOG_WARNING, "Interned string buffer overflow");
return arKey;
}
@@ -893,7 +878,7 @@ static inline int do_validate_timestamps(zend_persistent_script *persistent_scri
return FAILURE;
}
-static inline int validate_timestamp_and_record(zend_persistent_script *persistent_script, zend_file_handle *file_handle TSRMLS_DC)
+int validate_timestamp_and_record(zend_persistent_script *persistent_script, zend_file_handle *file_handle TSRMLS_DC)
{
if (ZCG(accel_directives).revalidate_freq &&
(persistent_script->dynamic_members.revalidate >= ZCSG(revalidate_at))) {
@@ -1044,33 +1029,15 @@ char *accel_make_persistent_key_ex(zend_file_handle *file_handle, int path_lengt
}
memcpy(ZCG(key) + cur_len, include_path, include_path_len);
ZCG(key)[key_length] = '\0';
- } else {
- /* not use_cwd */
- key_length = path_length;
+ } else {
+ /* not use_cwd */
+ key_length = path_length;
if ((size_t)key_length >= sizeof(ZCG(key))) {
ZCG(key_len) = 0;
return NULL;
- } else {
- char *alias;
- int alias_len;
- if (is_phar_relative_alias_path(file_handle->filename, &alias, &alias_len)) {
- char *phar_path;
- int phar_path_len;
- if (phar_resolve_alias(alias, alias_len, &phar_path, &phar_path_len TSRMLS_CC) == SUCCESS) {
- int filename_len = strlen(file_handle->filename);
- memcpy(ZCG(key), "phar://", sizeof("phar://") -1);
- memcpy(ZCG(key) + sizeof("phar://") - 1, phar_path, phar_path_len);
- memcpy(ZCG(key) + sizeof("phar://") - 1 + phar_path_len,
- alias + alias_len, filename_len - alias_len - sizeof("phar://") + 2);
- key_length = filename_len + (phar_path_len - alias_len);
- } else {
- memcpy(ZCG(key), file_handle->filename, key_length + 1);
- }
- } else {
- memcpy(ZCG(key), file_handle->filename, key_length + 1);
- }
}
- }
+ memcpy(ZCG(key), file_handle->filename, key_length + 1);
+ }
*key_len = ZCG(key_len) = key_length;
return ZCG(key);
@@ -1146,7 +1113,9 @@ static void zend_accel_add_key(char *key, unsigned int key_length, zend_accel_ha
char *new_key = zend_shared_alloc(key_length + 1);
if (new_key) {
memcpy(new_key, key, key_length + 1);
- zend_accel_hash_update(&ZCSG(hash), new_key, key_length + 1, 1, bucket);
+ if (zend_accel_hash_update(&ZCSG(hash), new_key, key_length + 1, 1, bucket)) {
+ zend_accel_error(ACCEL_LOG_INFO, "Added key '%s'", new_key);
+ }
} else {
zend_accel_schedule_restart_if_necessary(ACCEL_RESTART_OOM TSRMLS_CC);
}
@@ -1187,8 +1156,9 @@ static zend_persistent_script *cache_script_in_shared_memory(zend_persistent_scr
zend_persistent_script *existing_persistent_script = (zend_persistent_script *)bucket->data;
if (!existing_persistent_script->corrupted) {
- if (!ZCG(accel_directives).validate_timestamps ||
- (new_persistent_script->timestamp == existing_persistent_script->timestamp)) {
+ if (!ZCG(accel_directives).revalidate_path &&
+ (!ZCG(accel_directives).validate_timestamps ||
+ (new_persistent_script->timestamp == existing_persistent_script->timestamp))) {
zend_accel_add_key(key, key_length, bucket TSRMLS_CC);
}
zend_shared_alloc_unlock(TSRMLS_C);
@@ -1229,14 +1199,21 @@ static zend_persistent_script *cache_script_in_shared_memory(zend_persistent_scr
/* store script structure in the hash table */
bucket = zend_accel_hash_update(&ZCSG(hash), new_persistent_script->full_path, new_persistent_script->full_path_len + 1, 0, new_persistent_script);
- if (bucket &&
- (new_persistent_script->full_path_len != key_length ||
- memcmp(new_persistent_script->full_path, key, key_length) != 0)) {
- /* link key to the same persistent script in hash table */
- if (!zend_accel_hash_update(&ZCSG(hash), key, key_length + 1, 1, bucket)) {
- zend_accel_error(ACCEL_LOG_DEBUG, "No more entries in hash table!");
- ZSMMG(memory_exhausted) = 1;
- zend_accel_schedule_restart_if_necessary(ACCEL_RESTART_HASH TSRMLS_CC);
+ if (bucket) {
+ zend_accel_error(ACCEL_LOG_INFO, "Cached script '%s'", new_persistent_script->full_path);
+ if (!ZCG(accel_directives).revalidate_path &&
+ /* key may contain non-persistent PHAR aliases (see issues #115 and #149) */
+ memcmp(key, "phar://", sizeof("phar://") - 1) != 0 &&
+ (new_persistent_script->full_path_len != key_length ||
+ memcmp(new_persistent_script->full_path, key, key_length) != 0)) {
+ /* link key to the same persistent script in hash table */
+ if (zend_accel_hash_update(&ZCSG(hash), key, key_length + 1, 1, bucket)) {
+ zend_accel_error(ACCEL_LOG_INFO, "Added key '%s'", key);
+ } else {
+ zend_accel_error(ACCEL_LOG_DEBUG, "No more entries in hash table!");
+ ZSMMG(memory_exhausted) = 1;
+ zend_accel_schedule_restart_if_necessary(ACCEL_RESTART_HASH TSRMLS_CC);
+ }
}
}
@@ -1363,7 +1340,9 @@ static zend_persistent_script *compile_and_cache_file(zend_file_handle *file_han
}
#endif
- if (ZCG(accel_directives).validate_timestamps || ZCG(accel_directives).max_file_size > 0) {
+ if (ZCG(accel_directives).validate_timestamps ||
+ ZCG(accel_directives).file_update_protection ||
+ ZCG(accel_directives).max_file_size > 0) {
size_t size = 0;
/* Obtain the file timestamps, *before* actually compiling them,
@@ -1379,6 +1358,13 @@ static zend_persistent_script *compile_and_cache_file(zend_file_handle *file_han
return NULL;
}
+ /* check if file is too new (may be it's not written completely yet) */
+ if (ZCG(accel_directives).file_update_protection &&
+ (ZCG(request_time) - ZCG(accel_directives).file_update_protection < timestamp)) {
+ *op_array_p = accelerator_orig_compile_file(file_handle, type TSRMLS_CC);
+ return NULL;
+ }
+
if (ZCG(accel_directives).max_file_size > 0 && size > (size_t)ZCG(accel_directives).max_file_size) {
ZCSG(blacklist_misses)++;
*op_array_p = accelerator_orig_compile_file(file_handle, type TSRMLS_CC);
@@ -1685,7 +1671,18 @@ zend_op_array *persistent_compile_file(zend_file_handle *file_handle, int type T
#endif
void *dummy = (void *) 1;
- zend_hash_quick_add(&EG(included_files), persistent_script->full_path, persistent_script->full_path_len + 1, persistent_script->hash_value, &dummy, sizeof(void *), NULL);
+ if (zend_hash_quick_add(&EG(included_files), persistent_script->full_path, persistent_script->full_path_len + 1, persistent_script->hash_value, &dummy, sizeof(void *), NULL) == SUCCESS) {
+ /* ext/phar has to load phar's metadata into memory */
+ if (strstr(persistent_script->full_path, ".phar") && !strstr(persistent_script->full_path, "://")) {
+ php_stream_statbuf ssb;
+ char *fname = emalloc(sizeof("phar://") + persistent_script->full_path_len);
+
+ memcpy(fname, "phar://", sizeof("phar://") - 1);
+ memcpy(fname + sizeof("phar://") - 1, persistent_script->full_path, persistent_script->full_path_len + 1);
+ php_stream_stat_path(fname, &ssb);
+ efree(fname);
+ }
+ }
}
}
#if ZEND_EXTENSION_API_NO < PHP_5_3_X_API_NO
@@ -2139,7 +2136,9 @@ static void accel_activate(void)
}
#if (ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO) && !defined(ZTS)
- accel_interned_strings_restore_state(TSRMLS_C);
+ if (ZCG(accel_directives).interned_strings_buffer) {
+ accel_interned_strings_restore_state(TSRMLS_C);
+ }
#endif
zend_shared_alloc_restore_state();
@@ -2457,36 +2456,39 @@ static int zend_accel_init_shm(TSRMLS_D)
#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ ZCSG(interned_strings_start) = ZCSG(interned_strings_end) = NULL;
# ifndef ZTS
zend_hash_init(&ZCSG(interned_strings), (ZCG(accel_directives).interned_strings_buffer * 1024 * 1024) / (sizeof(Bucket) + sizeof(Bucket*) + 8 /* average string length */), NULL, NULL, 1);
- ZCSG(interned_strings).nTableMask = ZCSG(interned_strings).nTableSize - 1;
- ZCSG(interned_strings).arBuckets = zend_shared_alloc(ZCSG(interned_strings).nTableSize * sizeof(Bucket *));
- ZCSG(interned_strings_start) = zend_shared_alloc((ZCG(accel_directives).interned_strings_buffer * 1024 * 1024));
- if (!ZCSG(interned_strings).arBuckets || !ZCSG(interned_strings_start)) {
- zend_accel_error(ACCEL_LOG_FATAL, ACCELERATOR_PRODUCT_NAME " cannot allocate buffer for interned strings");
- return FAILURE;
+ if (ZCG(accel_directives).interned_strings_buffer) {
+ ZCSG(interned_strings).nTableMask = ZCSG(interned_strings).nTableSize - 1;
+ ZCSG(interned_strings).arBuckets = zend_shared_alloc(ZCSG(interned_strings).nTableSize * sizeof(Bucket *));
+ ZCSG(interned_strings_start) = zend_shared_alloc((ZCG(accel_directives).interned_strings_buffer * 1024 * 1024));
+ if (!ZCSG(interned_strings).arBuckets || !ZCSG(interned_strings_start)) {
+ zend_accel_error(ACCEL_LOG_FATAL, ACCELERATOR_PRODUCT_NAME " cannot allocate buffer for interned strings");
+ return FAILURE;
+ }
+ ZCSG(interned_strings_end) = ZCSG(interned_strings_start) + (ZCG(accel_directives).interned_strings_buffer * 1024 * 1024);
+ ZCSG(interned_strings_top) = ZCSG(interned_strings_start);
+
+ orig_interned_strings_start = CG(interned_strings_start);
+ orig_interned_strings_end = CG(interned_strings_end);
+ CG(interned_strings_start) = ZCSG(interned_strings_start);
+ CG(interned_strings_end) = ZCSG(interned_strings_end);
}
- ZCSG(interned_strings_end) = ZCSG(interned_strings_start) + (ZCG(accel_directives).interned_strings_buffer * 1024 * 1024);
- ZCSG(interned_strings_top) = ZCSG(interned_strings_start);
-# else
- ZCSG(interned_strings_start) = ZCSG(interned_strings_end) = NULL;
# endif
- orig_interned_strings_start = CG(interned_strings_start);
- orig_interned_strings_end = CG(interned_strings_end);
orig_new_interned_string = zend_new_interned_string;
orig_interned_strings_snapshot = zend_interned_strings_snapshot;
orig_interned_strings_restore = zend_interned_strings_restore;
-
- CG(interned_strings_start) = ZCSG(interned_strings_start);
- CG(interned_strings_end) = ZCSG(interned_strings_end);
zend_new_interned_string = accel_new_interned_string_for_php;
zend_interned_strings_snapshot = accel_interned_strings_snapshot_for_php;
zend_interned_strings_restore = accel_interned_strings_restore_for_php;
# ifndef ZTS
- accel_use_shm_interned_strings(TSRMLS_C);
- accel_interned_strings_save_state(TSRMLS_C);
+ if (ZCG(accel_directives).interned_strings_buffer) {
+ accel_use_shm_interned_strings(TSRMLS_C);
+ accel_interned_strings_save_state(TSRMLS_C);
+ }
# endif
#endif
@@ -2711,27 +2713,28 @@ void accel_shutdown(TSRMLS_D)
return;
}
- accel_free_ts_resources();
- zend_shared_alloc_shutdown();
- zend_compile_file = accelerator_orig_compile_file;
-
- if (zend_hash_find(EG(ini_directives), "include_path", sizeof("include_path"), (void **) &ini_entry) == SUCCESS) {
- ini_entry->on_modify = orig_include_path_on_modify;
- }
-
#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ if (ZCG(accel_directives).interned_strings_buffer) {
# ifndef ZTS
- zend_hash_clean(CG(function_table));
- zend_hash_clean(CG(class_table));
- zend_hash_clean(EG(zend_constants));
+ zend_hash_clean(CG(function_table));
+ zend_hash_clean(CG(class_table));
+ zend_hash_clean(EG(zend_constants));
# endif
- CG(interned_strings_start) = orig_interned_strings_start;
- CG(interned_strings_end) = orig_interned_strings_end;
+ CG(interned_strings_start) = orig_interned_strings_start;
+ CG(interned_strings_end) = orig_interned_strings_end;
+ }
zend_new_interned_string = orig_new_interned_string;
zend_interned_strings_snapshot = orig_interned_strings_snapshot;
zend_interned_strings_restore = orig_interned_strings_restore;
#endif
+ accel_free_ts_resources();
+ zend_shared_alloc_shutdown();
+ zend_compile_file = accelerator_orig_compile_file;
+
+ if (zend_hash_find(EG(ini_directives), "include_path", sizeof("include_path"), (void **) &ini_entry) == SUCCESS) {
+ ini_entry->on_modify = orig_include_path_on_modify;
+ }
}
void zend_accel_schedule_restart(zend_accel_restart_reason reason TSRMLS_DC)
@@ -2742,6 +2745,7 @@ void zend_accel_schedule_restart(zend_accel_restart_reason reason TSRMLS_DC)
}
zend_accel_error(ACCEL_LOG_DEBUG, "Restart Scheduled!");
+ SHM_UNPROTECT();
ZCSG(restart_pending) = 1;
ZCSG(restart_reason) = reason;
ZCSG(cache_status_before_restart) = ZCSG(accelerator_enabled);
@@ -2752,6 +2756,7 @@ void zend_accel_schedule_restart(zend_accel_restart_reason reason TSRMLS_DC)
} else {
ZCSG(force_restart_time) = 0;
}
+ SHM_PROTECT();
}
/* this is needed because on WIN32 lock is not decreased unless ZCG(counted) is set */
@@ -2812,7 +2817,7 @@ ZEND_EXT_API zend_extension zend_extension_entry = {
ACCELERATOR_VERSION, /* version */
"Zend Technologies", /* author */
"http://www.zend.com/", /* URL */
- "Copyright (c) 1999-2013", /* copyright */
+ "Copyright (c) 1999-2014", /* copyright */
accel_startup, /* startup */
NULL, /* shutdown */
accel_activate, /* per-script activation */
diff --git a/ext/opcache/ZendAccelerator.h b/ext/opcache/ZendAccelerator.h
index b9d7ef3470..bba36316d9 100644
--- a/ext/opcache/ZendAccelerator.h
+++ b/ext/opcache/ZendAccelerator.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -27,7 +27,8 @@
#endif
#define ACCELERATOR_PRODUCT_NAME "Zend OPcache"
-#define ACCELERATOR_VERSION "7.0.3-dev"
+#define PHP_ZENDOPCACHE_VERSION "7.0.4-dev"
+#define ACCELERATOR_VERSION PHP_ZENDOPCACHE_VERSION
/* 2 - added Profiler support, on 20010712 */
/* 3 - added support for Optimizer's encoded-only-files mode */
/* 4 - works with the new Optimizer, that supports the file format with licenses */
@@ -229,6 +230,7 @@ typedef struct _zend_accel_directives {
zend_bool inherited_hack;
zend_bool enable_cli;
unsigned long revalidate_freq;
+ unsigned long file_update_protection;
char *error_log;
#ifdef ZEND_WIN32
char *mmap_base;
@@ -329,6 +331,7 @@ extern char *zps_api_failure_reason;
void accel_shutdown(TSRMLS_D);
void zend_accel_schedule_restart(zend_accel_restart_reason reason TSRMLS_DC);
void zend_accel_schedule_restart_if_necessary(zend_accel_restart_reason reason TSRMLS_DC);
+int validate_timestamp_and_record(zend_persistent_script *persistent_script, zend_file_handle *file_handle TSRMLS_DC);
int zend_accel_invalidate(const char *filename, int filename_len, zend_bool force TSRMLS_DC);
int accelerator_shm_read_lock(TSRMLS_D);
void accelerator_shm_read_unlock(TSRMLS_D);
diff --git a/ext/opcache/shared_alloc_mmap.c b/ext/opcache/shared_alloc_mmap.c
index 12f00554a1..d995e20f12 100644
--- a/ext/opcache/shared_alloc_mmap.c
+++ b/ext/opcache/shared_alloc_mmap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/shared_alloc_posix.c b/ext/opcache/shared_alloc_posix.c
index f3377dec60..e4a34bd795 100644
--- a/ext/opcache/shared_alloc_posix.c
+++ b/ext/opcache/shared_alloc_posix.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/shared_alloc_shm.c b/ext/opcache/shared_alloc_shm.c
index a88cc2e196..4d9e10fc6f 100644
--- a/ext/opcache/shared_alloc_shm.c
+++ b/ext/opcache/shared_alloc_shm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/shared_alloc_win32.c b/ext/opcache/shared_alloc_win32.c
index fb84857368..37431fb18a 100644
--- a/ext/opcache/shared_alloc_win32.c
+++ b/ext/opcache/shared_alloc_win32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/tests/blacklist-win32.phpt b/ext/opcache/tests/blacklist-win32.phpt
new file mode 100644
index 0000000000..909c695fcd
--- /dev/null
+++ b/ext/opcache/tests/blacklist-win32.phpt
@@ -0,0 +1,34 @@
+--TEST--
+Blacklist (with glob, quote and comments)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.blacklist_filename={PWD}/opcache-*.blacklist
+opcache.file_update_protection=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php if (substr(PHP_OS, 0, 3) != 'WIN') { die('skip only for Windows'); } ?>
+--FILE--
+<?php
+$conf = opcache_get_configuration();
+$conf = $conf['blacklist'];
+$conf[3] = preg_replace("!^\\Q".dirname(__FILE__)."\\E!", "__DIR__", $conf[3]);
+$conf[4] = preg_replace("!^\\Q".dirname(__FILE__)."\\E!", "__DIR__", $conf[4]);
+print_r($conf);
+include("blacklist.inc");
+$status = opcache_get_status();
+print_r(count($status['scripts']));
+?>
+--EXPECTF--
+Array
+(
+ [0] => C:\path\to\foo
+ [1] => C:\path\to\foo2
+ [2] => C:\path\to\bar
+ [3] => __DIR__\blacklist.inc
+ [4] => __DIR__\current.php
+ [5] => %scurrent.php
+ [6] => %scurrent.php
+)
+ok
+1
diff --git a/ext/opcache/tests/blacklist.phpt b/ext/opcache/tests/blacklist.phpt
index 57e4c306dd..0c60425dac 100644
--- a/ext/opcache/tests/blacklist.phpt
+++ b/ext/opcache/tests/blacklist.phpt
@@ -4,8 +4,10 @@ Blacklist (with glob, quote and comments)
opcache.enable=1
opcache.enable_cli=1
opcache.blacklist_filename={PWD}/opcache-*.blacklist
+opcache.file_update_protection=0
--SKIPIF--
<?php require_once('skipif.inc'); ?>
+<?php if (substr(PHP_OS, 0, 3) == 'WIN') { die('skip not for Windows'); } ?>
--FILE--
<?php
$conf = opcache_get_configuration();
diff --git a/ext/opcache/tests/bug65559.phpt b/ext/opcache/tests/bug65559.phpt
new file mode 100644
index 0000000000..0d40cf10f8
--- /dev/null
+++ b/ext/opcache/tests/bug65559.phpt
@@ -0,0 +1,22 @@
+--TEST--
+Bug #65559 (cache not cleared if changes occur while running)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.file_update_protection=2
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+$file = __DIR__ . "/bug6559.inc.php";
+file_put_contents($file, '<?php return 1;');
+$var = include $file;
+var_dump($var);
+file_put_contents($file, '<?php return 2;');
+$var = include $file;
+var_dump($var);
+@unlink($file);
+?>
+--EXPECT--
+int(1)
+int(2)
diff --git a/ext/opcache/tests/bug65915.phpt b/ext/opcache/tests/bug65915.phpt
new file mode 100644
index 0000000000..6496ee3253
--- /dev/null
+++ b/ext/opcache/tests/bug65915.phpt
@@ -0,0 +1,26 @@
+--TEST--
+Bug #65915 (Inconsistent results with require return value)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+$tmp = __DIR__ . "/bug65915.inc.php";
+
+file_put_contents($tmp, '<?php return function(){ return "a";};');
+$f = require $tmp;
+var_dump($f());
+
+opcache_invalidate($tmp, true);
+
+file_put_contents($tmp, '<?php return function(){ return "b";};');
+$f = require $tmp;
+var_dump($f());
+
+@unlink($tmp);
+?>
+--EXPECT--
+string(1) "a"
+string(1) "b"
diff --git a/ext/opcache/tests/bug66176.phpt b/ext/opcache/tests/bug66176.phpt
new file mode 100644
index 0000000000..a91024a616
--- /dev/null
+++ b/ext/opcache/tests/bug66176.phpt
@@ -0,0 +1,19 @@
+--TEST--
+Bug #66176 (Invalid constant substitution)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.optimization_level=-1
+opcache.file_update_protection=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+function foo($v) {
+ global $a;
+ return $a[$v];
+}
+$a = array(PHP_VERSION => 1);
+var_dump(foo(PHP_VERSION));
+--EXPECT--
+int(1)
diff --git a/ext/opcache/tests/bug66461.phpt b/ext/opcache/tests/bug66461.phpt
new file mode 100644
index 0000000000..33132abeed
--- /dev/null
+++ b/ext/opcache/tests/bug66461.phpt
@@ -0,0 +1,15 @@
+--TEST--
+Bug #66461 (PHP crashes if opcache.interned_strings_buffer=0)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.optimization_level=-1
+opcache.file_update_protection=0
+opcache.interned_strings_buffer=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+echo "ok\n";
+--EXPECT--
+ok
diff --git a/ext/opcache/tests/bug66474.phpt b/ext/opcache/tests/bug66474.phpt
new file mode 100644
index 0000000000..3bd038c0de
--- /dev/null
+++ b/ext/opcache/tests/bug66474.phpt
@@ -0,0 +1,18 @@
+--TEST--
+Bug #66474 (Optimizer bug in constant string to boolean conversion)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.optimization_level=-1
+opcache.file_update_protection=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+function foo() {
+ $speed = 'slow' || 'fast';
+}
+foo();
+echo "ok\n";
+--EXPECT--
+ok
diff --git a/ext/opcache/tests/is_script_cached.phpt b/ext/opcache/tests/is_script_cached.phpt
new file mode 100644
index 0000000000..6f40a7e35d
--- /dev/null
+++ b/ext/opcache/tests/is_script_cached.phpt
@@ -0,0 +1,15 @@
+--TEST--
+Test that script cached info is correct
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--FILE--
+<?php
+var_dump(opcache_is_script_cached(__FILE__));
+var_dump(opcache_is_script_cached("nonexistent.php"));
+?>
+--EXPECT--
+bool(true)
+bool(false)
diff --git a/ext/opcache/tests/issue0115.phpt b/ext/opcache/tests/issue0115.phpt
new file mode 100644
index 0000000000..0dfdd9f0eb
--- /dev/null
+++ b/ext/opcache/tests/issue0115.phpt
@@ -0,0 +1,48 @@
+--TEST--
+ISSUE #115 (path issue when using phar)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+phar.readonly=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php if (!extension_loaded("phar")) die("skip"); ?>
+<?php if (php_sapi_name() != "cli") die("skip CLI only"); ?>
+--FILE--
+<?php
+$stub = '<?php
+Phar::interceptFileFuncs();
+require "phar://this/index.php";
+__HALT_COMPILER(); ?>';
+$p = new Phar(__DIR__ . '/issue0115_1.phar.php', 0, 'this');
+$p['index.php'] = '<?php
+echo "Hello from Index 1.\n";
+require_once "phar://this/hello.php";
+';
+$p['hello.php'] = "Hello World 1!\n";
+$p->setStub($stub);
+unset($p);
+$p = new Phar(__DIR__ . '/issue0115_2.phar.php', 0, 'this');
+$p['index.php'] = '<?php
+echo "Hello from Index 2.\n";
+require_once "phar://this/hello.php";
+';
+$p['hello.php'] = "Hello World 2!\n";
+$p->setStub($stub);
+unset($p);
+
+include "php_cli_server.inc";
+php_cli_server_start('-d opcache.enable=1 -d opcache.enable_cli=1');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/issue0115_1.phar.php');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/issue0115_2.phar.php');
+?>
+--CLEAN--
+<?php
+@unlink(__DIR__ . '/issue0115_1.phar.php');
+@unlink(__DIR__ . '/issue0115_2.phar.php');
+?>
+--EXPECT--
+Hello from Index 1.
+Hello World 1!
+Hello from Index 2.
+Hello World 2!
diff --git a/ext/opcache/tests/issue0140.phpt b/ext/opcache/tests/issue0140.phpt
new file mode 100644
index 0000000000..98e0e45cc2
--- /dev/null
+++ b/ext/opcache/tests/issue0140.phpt
@@ -0,0 +1,43 @@
+--TEST--
+Issue #140: "opcache.enable_file_override" doesn't respect "opcache.revalidate_freq"
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.revalidate_freq=0
+opcache.file_update_protection=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php if (php_sapi_name() != "cli") die("skip CLI only"); ?>
+--FILE--
+<?php
+define("FILENAME", dirname(__FILE__) . "/issuer0140.inc.php");
+file_put_contents(FILENAME, "1\n");
+
+var_dump(is_readable(FILENAME));
+include(FILENAME);
+var_dump(filemtime(FILENAME));
+
+sleep(2);
+file_put_contents(FILENAME, "2\n");
+
+var_dump(is_readable(FILENAME));
+include(FILENAME);
+var_dump(filemtime(FILENAME));
+
+sleep(2);
+unlink(FILENAME);
+
+var_dump(is_readable(FILENAME));
+var_dump(@include(FILENAME));
+var_dump(@filemtime(FILENAME));
+?>
+--EXPECTF--
+bool(true)
+1
+int(%d)
+bool(true)
+2
+int(%d)
+bool(false)
+bool(false)
+bool(false)
diff --git a/ext/opcache/tests/issue0149.phpt b/ext/opcache/tests/issue0149.phpt
new file mode 100644
index 0000000000..8c7f1bb7e0
--- /dev/null
+++ b/ext/opcache/tests/issue0149.phpt
@@ -0,0 +1,35 @@
+--TEST--
+ISSUE #149 (Phar mount points not working this OPcache enabled)
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+phar.readonly=0
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php if (!extension_loaded("phar")) die("skip"); ?>
+<?php if (php_sapi_name() != "cli") die("skip CLI only"); ?>
+--FILE--
+<?php
+$stub = "<?php header('Content-Type: text/plain;');
+Phar::mount('this.file', '". __FILE__ . "');
+echo 'OK\n';
+__HALT_COMPILER(); ?>";
+$p = new Phar(__DIR__ . '/issue0149.phar.php', 0, 'this');
+$p['index.php'] = ""; # A Phar must have at least one file, hence this dummy
+$p->setStub($stub);
+unset($p);
+
+include "php_cli_server.inc";
+php_cli_server_start('-d opcache.enable=1 -d opcache.enable_cli=1');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/issue0149.phar.php');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/issue0149.phar.php');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/issue0149.phar.php');
+?>
+--CLEAN--
+<?php
+@unlink(__DIR__ . '/issue0149.phar.php');
+?>
+--EXPECT--
+OK
+OK
+OK
diff --git a/ext/opcache/tests/opcache-2.blacklist b/ext/opcache/tests/opcache-2.blacklist
index 575d9fab30..4e369bb073 100644
--- a/ext/opcache/tests/opcache-2.blacklist
+++ b/ext/opcache/tests/opcache-2.blacklist
@@ -1,5 +1,5 @@
/path/to/bar
-; wildcard and relative entires
+; wildcard and relative entries
blacklist.inc
./current.php
/tmp/path/?nocache.inc
diff --git a/ext/opcache/tests/php_cli_server.inc b/ext/opcache/tests/php_cli_server.inc
new file mode 100644
index 0000000000..0878bfafc0
--- /dev/null
+++ b/ext/opcache/tests/php_cli_server.inc
@@ -0,0 +1,47 @@
+<?php
+define ("PHP_CLI_SERVER_HOSTNAME", "localhost");
+define ("PHP_CLI_SERVER_PORT", 8964);
+define ("PHP_CLI_SERVER_ADDRESS", PHP_CLI_SERVER_HOSTNAME.":".PHP_CLI_SERVER_PORT);
+
+function php_cli_server_start($ini = "") {
+ $php_executable = getenv('TEST_PHP_EXECUTABLE');
+ $doc_root = __DIR__;
+
+ $descriptorspec = array(
+ 0 => STDIN,
+ 1 => STDOUT,
+ 2 => STDERR,
+ );
+
+ if (substr(PHP_OS, 0, 3) == 'WIN') {
+ $cmd = "{$php_executable} -t {$doc_root} $ini -S " . PHP_CLI_SERVER_ADDRESS;
+ $handle = proc_open(addslashes($cmd), $descriptorspec, $pipes, $doc_root, NULL, array("bypass_shell" => true, "suppress_errors" => true));
+ } else {
+ $cmd = "exec {$php_executable} -t {$doc_root} $ini -S " . PHP_CLI_SERVER_ADDRESS . " 2>/dev/null";
+ $handle = proc_open($cmd, $descriptorspec, $pipes, $doc_root);
+ }
+
+ // note: even when server prints 'Listening on localhost:8964...Press Ctrl-C to quit.'
+ // it might not be listening yet...need to wait until fsockopen() call returns
+ $i = 0;
+ while (($i++ < 30) && !($fp = @fsockopen(PHP_CLI_SERVER_HOSTNAME, PHP_CLI_SERVER_PORT))) {
+ usleep(10000);
+ }
+
+ if ($fp) {
+ fclose($fp);
+ }
+
+ register_shutdown_function(
+ function($handle) {
+ proc_terminate($handle);
+ },
+ $handle
+ );
+ // don't bother sleeping, server is already up
+ // server can take a variable amount of time to be up, so just sleeping a guessed amount of time
+ // does not work. this is why tests sometimes pass and sometimes fail. to get a reliable pass
+ // sleeping doesn't work.
+}
+?>
+
diff --git a/ext/opcache/tests/revalidate_path_01.phpt b/ext/opcache/tests/revalidate_path_01.phpt
new file mode 100644
index 0000000000..cf2ac0d829
--- /dev/null
+++ b/ext/opcache/tests/revalidate_path_01.phpt
@@ -0,0 +1,61 @@
+--TEST--
+revalidate_path 01: OPCache must cache only resolved real paths when revalidate_path is set
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.revalidate_path=1
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+<?php if (php_sapi_name() != "cli") die("skip CLI only"); ?>
+--FILE--
+<?php
+$dir = dirname(__FILE__);
+$dir1 = "$dir/test1";
+$dir2 = "$dir/test2";
+$link = "$dir/test";
+$file1 = "$dir1/index.php";
+$file2 = "$dir2/index.php";
+$main = "$dir/main.php";
+@mkdir($dir1);
+@mkdir($dir2);
+@file_put_contents($main, '<?php include(\'' . $link .'/index.php\');');
+@file_put_contents($file1, "TEST 1\n");
+@file_put_contents($file2, "TEST 2\n");
+while (filemtime($file1) != filemtime($file2)) {
+ touch($file1);
+ touch($file2);
+}
+@unlink($link);
+@symlink($dir1, $link);
+
+include "php_cli_server.inc";
+//php_cli_server_start('-d opcache.enable=1 -d opcache.enable_cli=1 -d opcache.revalidate_path=1');
+php_cli_server_start('-d opcache.enable=1 -d opcache.enable_cli=1 -d opcache.revalidate_path=1 -d opcache.file_update_protection=0 -d realpath_cache_size=0');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/main.php');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/main.php');
+@unlink($link);
+@symlink($dir2, $link);
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/main.php');
+echo file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . '/main.php');
+?>
+--CLEAN--
+<?php
+$dir = dirname(__FILE__);
+$dir1 = "$dir/test1";
+$dir2 = "$dir/test2";
+$link = "$dir/test";
+$file1 = "$dir1/index.php";
+$file2 = "$dir2/index.php";
+$main = "$dir/main.php";
+@unlink($main);
+@unlink($link);
+@unlink($file1);
+@unlink($file2);
+@rmdir($dir1);
+@rmdir($dir2);
+?>
+--EXPECT--
+TEST 1
+TEST 1
+TEST 2
+TEST 2
diff --git a/ext/opcache/zend_accelerator_blacklist.c b/ext/opcache/zend_accelerator_blacklist.c
index eb0bc2146c..0ca37dfa42 100644
--- a/ext/opcache/zend_accelerator_blacklist.c
+++ b/ext/opcache/zend_accelerator_blacklist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_blacklist.h b/ext/opcache/zend_accelerator_blacklist.h
index 626b8d2c47..869068410f 100644
--- a/ext/opcache/zend_accelerator_blacklist.h
+++ b/ext/opcache/zend_accelerator_blacklist.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_debug.c b/ext/opcache/zend_accelerator_debug.c
index 93349e3d17..d0198dccb3 100644
--- a/ext/opcache/zend_accelerator_debug.c
+++ b/ext/opcache/zend_accelerator_debug.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_debug.h b/ext/opcache/zend_accelerator_debug.h
index 2ff88e21d3..f773f6220a 100644
--- a/ext/opcache/zend_accelerator_debug.h
+++ b/ext/opcache/zend_accelerator_debug.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_hash.c b/ext/opcache/zend_accelerator_hash.c
index afd227c5d5..b75377d61b 100644
--- a/ext/opcache/zend_accelerator_hash.c
+++ b/ext/opcache/zend_accelerator_hash.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_hash.h b/ext/opcache/zend_accelerator_hash.h
index fdfddb4064..2de28bffa7 100644
--- a/ext/opcache/zend_accelerator_hash.h
+++ b/ext/opcache/zend_accelerator_hash.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_module.c b/ext/opcache/zend_accelerator_module.c
index 0914fb68dd..9d7a5a93f5 100644
--- a/ext/opcache/zend_accelerator_module.c
+++ b/ext/opcache/zend_accelerator_module.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -57,9 +57,14 @@ ZEND_BEGIN_ARG_INFO_EX(arginfo_opcache_invalidate, 0, 0, 1)
ZEND_ARG_INFO(0, force)
ZEND_END_ARG_INFO()
+ZEND_BEGIN_ARG_INFO_EX(arginfo_opcache_is_script_cached, 0, 0, 1)
+ ZEND_ARG_INFO(0, script)
+ZEND_END_ARG_INFO()
+
/* User functions */
static ZEND_FUNCTION(opcache_reset);
static ZEND_FUNCTION(opcache_invalidate);
+static ZEND_FUNCTION(opcache_is_script_cached);
/* Private functions */
static ZEND_FUNCTION(opcache_get_status);
@@ -71,6 +76,7 @@ static zend_function_entry accel_functions[] = {
ZEND_FE(opcache_reset, arginfo_opcache_none)
ZEND_FE(opcache_invalidate, arginfo_opcache_invalidate)
ZEND_FE(opcache_compile_file, arginfo_opcache_compile_file)
+ ZEND_FE(opcache_is_script_cached, arginfo_opcache_is_script_cached)
/* Private functions */
ZEND_FE(opcache_get_configuration, arginfo_opcache_none)
ZEND_FE(opcache_get_status, arginfo_opcache_get_status)
@@ -259,7 +265,8 @@ ZEND_INI_BEGIN()
STD_PHP_INI_ENTRY("opcache.consistency_checks" , "0" , PHP_INI_ALL , OnUpdateLong, accel_directives.consistency_checks, zend_accel_globals, accel_globals)
STD_PHP_INI_ENTRY("opcache.force_restart_timeout" , "180" , PHP_INI_SYSTEM, OnUpdateLong, accel_directives.force_restart_timeout, zend_accel_globals, accel_globals)
STD_PHP_INI_ENTRY("opcache.revalidate_freq" , "2" , PHP_INI_ALL , OnUpdateLong, accel_directives.revalidate_freq, zend_accel_globals, accel_globals)
- STD_PHP_INI_ENTRY("opcache.preferred_memory_model", "" , PHP_INI_SYSTEM, OnUpdateStringUnempty, accel_directives.memory_model, zend_accel_globals, accel_globals)
+ STD_PHP_INI_ENTRY("opcache.file_update_protection", "2" , PHP_INI_ALL , OnUpdateLong, accel_directives.file_update_protection, zend_accel_globals, accel_globals)
+ STD_PHP_INI_ENTRY("opcache.preferred_memory_model", "" , PHP_INI_SYSTEM, OnUpdateStringUnempty, accel_directives.memory_model, zend_accel_globals, accel_globals)
STD_PHP_INI_ENTRY("opcache.blacklist_filename" , "" , PHP_INI_SYSTEM, OnUpdateString, accel_directives.user_blacklist_filename, zend_accel_globals, accel_globals)
STD_PHP_INI_ENTRY("opcache.max_file_size" , "0" , PHP_INI_SYSTEM, OnUpdateLong, accel_directives.max_file_size, zend_accel_globals, accel_globals)
@@ -312,13 +319,15 @@ static int filename_is_in_cache(char *filename, int filename_len TSRMLS_DC)
if (IS_ABSOLUTE_PATH(filename, filename_len)) {
persistent_script = zend_accel_hash_find(&ZCSG(hash), filename, filename_len + 1);
if (persistent_script) {
- return !persistent_script->corrupted;
+ return !persistent_script->corrupted &&
+ validate_timestamp_and_record(persistent_script, &handle TSRMLS_CC) == SUCCESS;
}
}
if ((key = accel_make_persistent_key_ex(&handle, filename_len, &key_length TSRMLS_CC)) != NULL) {
persistent_script = zend_accel_hash_find(&ZCSG(hash), key, key_length + 1);
- return persistent_script && !persistent_script->corrupted;
+ return persistent_script && !persistent_script->corrupted &&
+ validate_timestamp_and_record(persistent_script, &handle TSRMLS_CC) == SUCCESS;
}
return 0;
@@ -435,6 +444,14 @@ void zend_accel_info(ZEND_MODULE_INFO_FUNC_ARGS)
php_info_print_table_row(2, "Free memory", buf);
snprintf(buf, sizeof(buf), "%ld", ZSMMG(wasted_shared_memory));
php_info_print_table_row(2, "Wasted memory", buf);
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ if (ZCSG(interned_strings_start) && ZCSG(interned_strings_end) && ZCSG(interned_strings_top)) {
+ snprintf(buf, sizeof(buf), "%ld", ZCSG(interned_strings_top) - ZCSG(interned_strings_start));
+ php_info_print_table_row(2, "Interned Strings Used memory", buf);
+ snprintf(buf, sizeof(buf), "%ld", ZCSG(interned_strings_end) - ZCSG(interned_strings_top));
+ php_info_print_table_row(2, "Interned Strings Free memory", buf);
+ }
+#endif
snprintf(buf, sizeof(buf), "%ld", ZCSG(hash).num_direct_entries);
php_info_print_table_row(2, "Cached scripts", buf);
snprintf(buf, sizeof(buf), "%ld", ZCSG(hash).num_entries);
@@ -564,6 +581,20 @@ static ZEND_FUNCTION(opcache_get_status)
add_assoc_double(memory_usage, "current_wasted_percentage", (((double) ZSMMG(wasted_shared_memory))/ZCG(accel_directives).memory_consumption)*100.0);
add_assoc_zval(return_value, "memory_usage", memory_usage);
+#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
+ if (ZCSG(interned_strings_start) && ZCSG(interned_strings_end) && ZCSG(interned_strings_top)) {
+ zval *interned_strings_usage;
+
+ MAKE_STD_ZVAL(interned_strings_usage);
+ array_init(interned_strings_usage);
+ add_assoc_long(interned_strings_usage, "buffer_size", ZCSG(interned_strings_end) - ZCSG(interned_strings_start));
+ add_assoc_long(interned_strings_usage, "used_memory", ZCSG(interned_strings_top) - ZCSG(interned_strings_start));
+ add_assoc_long(interned_strings_usage, "free_memory", ZCSG(interned_strings_end) - ZCSG(interned_strings_top));
+ add_assoc_long(interned_strings_usage, "number_of_strings", ZCSG(interned_strings).nNumOfElements);
+ add_assoc_zval(return_value, "interned_strings_usage", interned_strings_usage);
+ }
+#endif
+
/* Accelerator statistics */
MAKE_STD_ZVAL(statistics);
array_init(statistics);
@@ -756,3 +787,25 @@ static ZEND_FUNCTION(opcache_compile_file)
}
zend_destroy_file_handle(&handle TSRMLS_CC);
}
+
+/* {{{ proto bool opcache_is_script_cached(string $script)
+ Return true if the script is cached in OPCache, false if it is not cached or if OPCache is not running. */
+static ZEND_FUNCTION(opcache_is_script_cached)
+{
+ char *script_name;
+ int script_name_len;
+
+ if (!validate_api_restriction(TSRMLS_C)) {
+ RETURN_FALSE;
+ }
+
+ if (!ZCG(enabled) || !accel_startup_ok || !ZCSG(accelerator_enabled)) {
+ RETURN_FALSE;
+ }
+
+ if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &script_name, &script_name_len) == FAILURE) {
+ return;
+ }
+
+ RETURN_BOOL(filename_is_in_cache(script_name, script_name_len TSRMLS_CC));
+}
diff --git a/ext/opcache/zend_accelerator_module.h b/ext/opcache/zend_accelerator_module.h
index 539b4e85af..ece4a7d6b5 100644
--- a/ext/opcache/zend_accelerator_module.h
+++ b/ext/opcache/zend_accelerator_module.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_accelerator_util_funcs.c b/ext/opcache/zend_accelerator_util_funcs.c
index 894da63aaa..14c6f7490f 100644
--- a/ext/opcache/zend_accelerator_util_funcs.c
+++ b/ext/opcache/zend_accelerator_util_funcs.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -835,7 +835,19 @@ static int zend_hash_unique_copy(HashTable *target, HashTable *source, unique_co
}
} else {
if (p->nKeyLength > 0 && p->arKey[0] == 0) {
- /* Mangled key, ignore and wait for runtime */
+ /* Mangled key */
+#if ZEND_EXTENSION_API_NO >= PHP_5_3_X_API_NO
+ if (((zend_function*)p->pData)->common.fn_flags & ZEND_ACC_CLOSURE) {
+ /* update closure */
+ if (zend_hash_quick_update(target, p->arKey, p->nKeyLength, p->h, p->pData, size, &t) == SUCCESS) {
+ if (pCopyConstructor) {
+ pCopyConstructor(t);
+ }
+ }
+ } else {
+ /* ignore and wait for runtime */
+ }
+#endif
} else if (!ignore_dups && zend_hash_quick_find(target, p->arKey, p->nKeyLength, p->h, &t) == SUCCESS) {
*fail_data = p->pData;
*conflict_data = t;
diff --git a/ext/opcache/zend_accelerator_util_funcs.h b/ext/opcache/zend_accelerator_util_funcs.h
index ddaae86b28..2f515d85cc 100644
--- a/ext/opcache/zend_accelerator_util_funcs.h
+++ b/ext/opcache/zend_accelerator_util_funcs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_persist.c b/ext/opcache/zend_persist.c
index 9f1940e061..6e06cac436 100644
--- a/ext/opcache/zend_persist.c
+++ b/ext/opcache/zend_persist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_persist.h b/ext/opcache/zend_persist.h
index cf3fb73cdd..1b95a4ab04 100644
--- a/ext/opcache/zend_persist.h
+++ b/ext/opcache/zend_persist.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_persist_calc.c b/ext/opcache/zend_persist_calc.c
index 18af756f6e..e22b7d3952 100644
--- a/ext/opcache/zend_persist_calc.c
+++ b/ext/opcache/zend_persist_calc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -33,11 +33,13 @@
#if ZEND_EXTENSION_API_NO > PHP_5_3_X_API_NO
# define ADD_INTERNED_STRING(str, len) do { \
- const char *tmp = accel_new_interned_string((str), (len), !IS_INTERNED((str)) TSRMLS_CC); \
- if (tmp != (str)) { \
- (str) = (char*)tmp; \
- } else { \
- ADD_DUP_SIZE((str), (len)); \
+ if (!IS_INTERNED(str)) { \
+ const char *tmp = accel_new_interned_string((str), (len), 1 TSRMLS_CC); \
+ if (tmp != (str)) { \
+ (str) = (char*)tmp; \
+ } else { \
+ ADD_DUP_SIZE((str), (len)); \
+ } \
} \
} while (0)
#else
diff --git a/ext/opcache/zend_shared_alloc.c b/ext/opcache/zend_shared_alloc.c
index cf4e0ff0f7..e1a570a3a0 100644
--- a/ext/opcache/zend_shared_alloc.c
+++ b/ext/opcache/zend_shared_alloc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/opcache/zend_shared_alloc.h b/ext/opcache/zend_shared_alloc.h
index e94ecab9b3..57ea8d3fdd 100644
--- a/ext/opcache/zend_shared_alloc.h
+++ b/ext/opcache/zend_shared_alloc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| Zend OPcache |
+----------------------------------------------------------------------+
- | Copyright (c) 1998-2013 The PHP Group |
+ | Copyright (c) 1998-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/openssl/openssl.c b/ext/openssl/openssl.c
index 59a58b1c00..9d8f66cf90 100644..100755
--- a/ext/openssl/openssl.c
+++ b/ext/openssl/openssl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -77,6 +77,10 @@
#endif
#define DEBUG_SMIME 0
+#if !defined(OPENSSL_NO_EC) && defined(EVP_PKEY_EC)
+#define HAVE_EVP_PKEY_EC 1
+#endif
+
/* FIXME: Use the openssl constants instead of
* enum. It is now impossible to match real values
* against php constants. Also sorry to break the
@@ -87,7 +91,7 @@ enum php_openssl_key_type {
OPENSSL_KEYTYPE_DSA,
OPENSSL_KEYTYPE_DH,
OPENSSL_KEYTYPE_DEFAULT = OPENSSL_KEYTYPE_RSA,
-#ifdef EVP_PKEY_EC
+#ifdef HAVE_EVP_PKEY_EC
OPENSSL_KEYTYPE_EC = OPENSSL_KEYTYPE_DH +1
#endif
};
@@ -657,18 +661,28 @@ static time_t asn1_time_to_time_t(ASN1_UTCTIME * timestr TSRMLS_DC) /* {{{ */
char * thestr;
long gmadjust = 0;
- if (timestr->length < 13) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "extension author too lazy to parse %s correctly", timestr->data);
+ if (ASN1_STRING_type(timestr) != V_ASN1_UTCTIME) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "illegal ASN1 data type for timestamp");
+ return (time_t)-1;
+ }
+
+ if (ASN1_STRING_length(timestr) != strlen(ASN1_STRING_data(timestr))) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "illegal length in timestamp");
+ return (time_t)-1;
+ }
+
+ if (ASN1_STRING_length(timestr) < 13) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "unable to parse time string %s correctly", timestr->data);
return (time_t)-1;
}
- strbuf = estrdup((char *)timestr->data);
+ strbuf = estrdup((char *)ASN1_STRING_data(timestr));
memset(&thetime, 0, sizeof(thetime));
/* we work backwards so that we can use atoi more easily */
- thestr = strbuf + timestr->length - 3;
+ thestr = strbuf + ASN1_STRING_length(timestr) - 3;
thetime.tm_sec = atoi(thestr);
*thestr = '\0';
@@ -1118,7 +1132,7 @@ PHP_MINIT_FUNCTION(openssl)
REGISTER_LONG_CONSTANT("OPENSSL_KEYTYPE_DSA", OPENSSL_KEYTYPE_DSA, CONST_CS|CONST_PERSISTENT);
#endif
REGISTER_LONG_CONSTANT("OPENSSL_KEYTYPE_DH", OPENSSL_KEYTYPE_DH, CONST_CS|CONST_PERSISTENT);
-#ifdef EVP_PKEY_EC
+#ifdef HAVE_EVP_PKEY_EC
REGISTER_LONG_CONSTANT("OPENSSL_KEYTYPE_EC", OPENSSL_KEYTYPE_EC, CONST_CS|CONST_PERSISTENT);
#endif
@@ -3016,6 +3030,15 @@ static int php_openssl_is_private_key(EVP_PKEY* pkey TSRMLS_DC)
}
break;
#endif
+#ifdef HAVE_EVP_PKEY_EC
+ case EVP_PKEY_EC:
+ assert(pkey->pkey.ec != NULL);
+
+ if ( NULL == EC_KEY_get0_private_key(pkey->pkey.ec)) {
+ return 0;
+ }
+ break;
+#endif
default:
php_error_docref(NULL TSRMLS_CC, E_WARNING, "key type not supported in this PHP build!");
break;
@@ -3416,7 +3439,7 @@ PHP_FUNCTION(openssl_pkey_get_details)
}
break;
-#ifdef EVP_PKEY_EC
+#ifdef HAVE_EVP_PKEY_EC
case EVP_PKEY_EC:
ktype = OPENSSL_KEYTYPE_EC;
break;
diff --git a/ext/openssl/php_openssl.h b/ext/openssl/php_openssl.h
index e6b064a277..e4cb7e890e 100644
--- a/ext/openssl/php_openssl.h
+++ b/ext/openssl/php_openssl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/openssl/tests/bug64802.phpt b/ext/openssl/tests/bug64802.phpt
index 9a59701494..be0b5f9b5b 100644
--- a/ext/openssl/tests/bug64802.phpt
+++ b/ext/openssl/tests/bug64802.phpt
@@ -3,6 +3,7 @@ Bug #64802: openssl_x509_parse fails to parse subject properly in some cases
--SKIPIF--
<?php
if (!extension_loaded("openssl")) die("skip");
+if (!defined(OPENSSL_KEYTYPE_EC)) die("skip no EC available);
?>
--FILE--
<?php
diff --git a/ext/openssl/tests/bug66501.phpt b/ext/openssl/tests/bug66501.phpt
new file mode 100644
index 0000000000..cd0da1f289
--- /dev/null
+++ b/ext/openssl/tests/bug66501.phpt
@@ -0,0 +1,22 @@
+--TEST--
+Bug #66501: EC private key support in openssl_sign
+--SKIPIF--
+<?php
+if (!extension_loaded("openssl")) die("skip");
+if (!defined(OPENSSL_KEYTYPE_EC)) die("skip no EC available);
+--FILE--
+<?php
+$pkey = 'ASN1 OID: prime256v1
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEILPkqoeyM7XgwYkuSj3077lrsrfWJK5LqMolv+m2oOjZoAoGCCqGSM49
+AwEHoUQDQgAEPq4hbIWHvB51rdWr8ejrjWo4qVNWVugYFtPg/xLQw0mHkIPZ4DvK
+sqOTOnMoezkbSmVVMuwz9flvnqHGmQvmug==
+-----END EC PRIVATE KEY-----';
+$key = openssl_pkey_get_private($pkey);
+$res = openssl_sign($data ='alpha', $sign, $key, 'ecdsa-with-SHA1');
+var_dump($res);
+--EXPECTF--
+bool(true)
diff --git a/ext/openssl/tests/cve-2013-6420.crt b/ext/openssl/tests/cve-2013-6420.crt
new file mode 100644
index 0000000000..454331468b
--- /dev/null
+++ b/ext/openssl/tests/cve-2013-6420.crt
@@ -0,0 +1,29 @@
+-----BEGIN CERTIFICATE-----
+MIIEpDCCA4ygAwIBAgIJAJzu8r6u6eBcMA0GCSqGSIb3DQEBBQUAMIHDMQswCQYD
+VQQGEwJERTEcMBoGA1UECAwTTm9yZHJoZWluLVdlc3RmYWxlbjEQMA4GA1UEBwwH
+S8ODwrZsbjEUMBIGA1UECgwLU2VrdGlvbkVpbnMxHzAdBgNVBAsMFk1hbGljaW91
+cyBDZXJ0IFNlY3Rpb24xITAfBgNVBAMMGG1hbGljaW91cy5zZWt0aW9uZWlucy5k
+ZTEqMCgGCSqGSIb3DQEJARYbc3RlZmFuLmVzc2VyQHNla3Rpb25laW5zLmRlMHUY
+ZDE5NzAwMTAxMDAwMDAwWgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
+AAAAAAAXDTE0MTEyODExMzkzNVowgcMxCzAJBgNVBAYTAkRFMRwwGgYDVQQIDBNO
+b3JkcmhlaW4tV2VzdGZhbGVuMRAwDgYDVQQHDAdLw4PCtmxuMRQwEgYDVQQKDAtT
+ZWt0aW9uRWluczEfMB0GA1UECwwWTWFsaWNpb3VzIENlcnQgU2VjdGlvbjEhMB8G
+A1UEAwwYbWFsaWNpb3VzLnNla3Rpb25laW5zLmRlMSowKAYJKoZIhvcNAQkBFhtz
+dGVmYW4uZXNzZXJAc2VrdGlvbmVpbnMuZGUwggEiMA0GCSqGSIb3DQEBAQUAA4IB
+DwAwggEKAoIBAQDDAf3hl7JY0XcFniyEJpSSDqn0OqBr6QP65usJPRt/8PaDoqBu
+wEYT/Na+6fsgPjC0uK9DZgWg2tHWWoanSblAMoz5PH6Z+S4SHRZ7e2dDIjPjdhjh
+0mLg2UMO5yp0V797Ggs9lNt6JRfH81MN2obXWs4NtztLMuD6egqpr8dDbr34aOs8
+pkdui5UawTZksy5pLPHq5cMhFGm06v65CLo0V2Pd9+KAokPrPcN5KLKebz7mLpk6
+SMeEXOKP4idEqxyQ7O7fBuHMedsQhu+prY3si3BUyKfQtP5CZnX2bp0wKHxX12DX
+1nfFIt9DbGvHTcyOuN+nZLPBm3vWxntyIIvVAgMBAAGjQjBAMAkGA1UdEwQCMAAw
+EQYJYIZIAYb4QgEBBAQDAgeAMAsGA1UdDwQEAwIFoDATBgNVHSUEDDAKBggrBgEF
+BQcDAjANBgkqhkiG9w0BAQUFAAOCAQEAG0fZYYCTbdj1XYc+1SnoaPR+vI8C8CaD
+8+0UYhdnyU4gga0BAcDrY9e94eEAu6ZqycF6FjLqXXdAboppWocr6T6GD1x33Ckl
+VArzG/KxQohGD2JeqkhIMlDomxHO7ka39+Oa8i2vWLVyjU8AZvWMAruHa4EENyG7
+lW2AagaFKFCr9TnXTfrdxGVEbv7KVQ6bdhg5p5SjpWH1+Mq03uR3ZXPBYdyV8319
+o0lVj1KFI2DCL/liWisJRoof+1cR35Ctd0wYBcpB6TZslMcOPl76dwKwJgeJo2Qg
+Zsfmc2vC1/qOlNuNq/0TzzkVGv8ETT3CgaU+UXe4XOVvkccebJn2dg==
+-----END CERTIFICATE-----
+
+
diff --git a/ext/openssl/tests/cve-2013-6420.phpt b/ext/openssl/tests/cve-2013-6420.phpt
new file mode 100644
index 0000000000..87c0210b2e
--- /dev/null
+++ b/ext/openssl/tests/cve-2013-6420.phpt
@@ -0,0 +1,18 @@
+--TEST--
+CVE-2013-6420
+--SKIPIF--
+<?php
+if (!extension_loaded("openssl")) die("skip");
+?>
+--FILE--
+<?php
+$crt = substr(__FILE__, 0, -4).'.crt';
+$info = openssl_x509_parse("file://$crt");
+var_dump($info['issuer']['emailAddress'], $info["validFrom_time_t"]);
+?>
+Done
+--EXPECTF--
+%s openssl_x509_parse(): illegal ASN1 data type for timestamp in %s%ecve-2013-6420.php on line 3
+string(27) "stefan.esser@sektioneins.de"
+int(-1)
+Done
diff --git a/ext/openssl/xp_ssl.c b/ext/openssl/xp_ssl.c
index a1a7ffc3f4..6f41c217d6 100644
--- a/ext/openssl/xp_ssl.c
+++ b/ext/openssl/xp_ssl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -825,7 +825,7 @@ static int php_openssl_sockop_cast(php_stream *stream, int castas, void **ret TS
case PHP_STREAM_AS_FD_FOR_SELECT:
if (ret) {
- *(int *)ret = sslsock->s.socket;
+ *(php_socket_t *)ret = sslsock->s.socket;
}
return SUCCESS;
@@ -835,7 +835,7 @@ static int php_openssl_sockop_cast(php_stream *stream, int castas, void **ret TS
return FAILURE;
}
if (ret) {
- *(int *)ret = sslsock->s.socket;
+ *(php_socket_t *)ret = sslsock->s.socket;
}
return SUCCESS;
default:
diff --git a/ext/pcntl/pcntl.c b/ext/pcntl/pcntl.c
index b66f4722e8..b7ef4c729c 100644
--- a/ext/pcntl/pcntl.c
+++ b/ext/pcntl/pcntl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcntl/php_pcntl.h b/ext/pcntl/php_pcntl.h
index 280a45bbaf..caafc10d19 100644
--- a/ext/pcntl/php_pcntl.h
+++ b/ext/pcntl/php_pcntl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcntl/php_signal.c b/ext/pcntl/php_signal.c
index 574276b7ce..9f308d793c 100644
--- a/ext/pcntl/php_signal.c
+++ b/ext/pcntl/php_signal.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcntl/php_signal.h b/ext/pcntl/php_signal.h
index 07bde634ca..5c61b10396 100644
--- a/ext/pcntl/php_signal.h
+++ b/ext/pcntl/php_signal.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcre/pcrelib/AUTHORS b/ext/pcre/pcrelib/AUTHORS
index ba4753d858..97d8c71dd6 100644
--- a/ext/pcre/pcrelib/AUTHORS
+++ b/ext/pcre/pcrelib/AUTHORS
@@ -8,7 +8,7 @@ Email domain: cam.ac.uk
University of Cambridge Computing Service,
Cambridge, England.
-Copyright (c) 1997-2012 University of Cambridge
+Copyright (c) 1997-2013 University of Cambridge
All rights reserved
@@ -19,7 +19,7 @@ Written by: Zoltan Herczeg
Email local part: hzmester
Emain domain: freemail.hu
-Copyright(c) 2010-2012 Zoltan Herczeg
+Copyright(c) 2010-2013 Zoltan Herczeg
All rights reserved.
@@ -30,7 +30,7 @@ Written by: Zoltan Herczeg
Email local part: hzmester
Emain domain: freemail.hu
-Copyright(c) 2009-2012 Zoltan Herczeg
+Copyright(c) 2009-2013 Zoltan Herczeg
All rights reserved.
diff --git a/ext/pcre/pcrelib/ChangeLog b/ext/pcre/pcrelib/ChangeLog
index ed164fed0f..1f1e860035 100644
--- a/ext/pcre/pcrelib/ChangeLog
+++ b/ext/pcre/pcrelib/ChangeLog
@@ -1,6 +1,381 @@
ChangeLog for PCRE
------------------
+Version 8.34 15-December-2013
+-----------------------------
+
+1. Add pcre[16|32]_jit_free_unused_memory to forcibly free unused JIT
+ executable memory. Patch inspired by Carsten Klein.
+
+2. ./configure --enable-coverage defined SUPPORT_GCOV in config.h, although
+ this macro is never tested and has no effect, because the work to support
+ coverage involves only compiling and linking options and special targets in
+ the Makefile. The comment in config.h implied that defining the macro would
+ enable coverage support, which is totally false. There was also support for
+ setting this macro in the CMake files (my fault, I just copied it from
+ configure). SUPPORT_GCOV has now been removed.
+
+3. Make a small performance improvement in strlen16() and strlen32() in
+ pcretest.
+
+4. Change 36 for 8.33 left some unreachable statements in pcre_exec.c,
+ detected by the Solaris compiler (gcc doesn't seem to be able to diagnose
+ these cases). There was also one in pcretest.c.
+
+5. Cleaned up a "may be uninitialized" compiler warning in pcre_exec.c.
+
+6. In UTF mode, the code for checking whether a group could match an empty
+ string (which is used for indefinitely repeated groups to allow for
+ breaking an infinite loop) was broken when the group contained a repeated
+ negated single-character class with a character that occupied more than one
+ data item and had a minimum repetition of zero (for example, [^\x{100}]* in
+ UTF-8 mode). The effect was undefined: the group might or might not be
+ deemed as matching an empty string, or the program might have crashed.
+
+7. The code for checking whether a group could match an empty string was not
+ recognizing that \h, \H, \v, \V, and \R must match a character.
+
+8. Implemented PCRE_INFO_MATCH_EMPTY, which yields 1 if the pattern can match
+ an empty string. If it can, pcretest shows this in its information output.
+
+9. Fixed two related bugs that applied to Unicode extended grapheme clusters
+ that were repeated with a maximizing qualifier (e.g. \X* or \X{2,5}) when
+ matched by pcre_exec() without using JIT:
+
+ (a) If the rest of the pattern did not match after a maximal run of
+ grapheme clusters, the code for backing up to try with fewer of them
+ did not always back up over a full grapheme when characters that do not
+ have the modifier quality were involved, e.g. Hangul syllables.
+
+ (b) If the match point in a subject started with modifier character, and
+ there was no match, the code could incorrectly back up beyond the match
+ point, and potentially beyond the first character in the subject,
+ leading to a segfault or an incorrect match result.
+
+10. A conditional group with an assertion condition could lead to PCRE
+ recording an incorrect first data item for a match if no other first data
+ item was recorded. For example, the pattern (?(?=ab)ab) recorded "a" as a
+ first data item, and therefore matched "ca" after "c" instead of at the
+ start.
+
+11. Change 40 for 8.33 (allowing pcregrep to find empty strings) showed up a
+ bug that caused the command "echo a | ./pcregrep -M '|a'" to loop.
+
+12. The source of pcregrep now includes z/OS-specific code so that it can be
+ compiled for z/OS as part of the special z/OS distribution.
+
+13. Added the -T and -TM options to pcretest.
+
+14. The code in pcre_compile.c for creating the table of named capturing groups
+ has been refactored. Instead of creating the table dynamically during the
+ actual compiling pass, the information is remembered during the pre-compile
+ pass (on the stack unless there are more than 20 named groups, in which
+ case malloc() is used) and the whole table is created before the actual
+ compile happens. This has simplified the code (it is now nearly 150 lines
+ shorter) and prepared the way for better handling of references to groups
+ with duplicate names.
+
+15. A back reference to a named subpattern when there is more than one of the
+ same name now checks them in the order in which they appear in the pattern.
+ The first one that is set is used for the reference. Previously only the
+ first one was inspected. This change makes PCRE more compatible with Perl.
+
+16. Unicode character properties were updated from Unicode 6.3.0.
+
+17. The compile-time code for auto-possessification has been refactored, based
+ on a patch by Zoltan Herczeg. It now happens after instead of during
+ compilation. The code is cleaner, and more cases are handled. The option
+ PCRE_NO_AUTO_POSSESS is added for testing purposes, and the -O and /O
+ options in pcretest are provided to set it. It can also be set by
+ (*NO_AUTO_POSSESS) at the start of a pattern.
+
+18. The character VT has been added to the default ("C" locale) set of
+ characters that match \s and are generally treated as white space,
+ following this same change in Perl 5.18. There is now no difference between
+ "Perl space" and "POSIX space". Whether VT is treated as white space in
+ other locales depends on the locale.
+
+19. The code for checking named groups as conditions, either for being set or
+ for being recursed, has been refactored (this is related to 14 and 15
+ above). Processing unduplicated named groups should now be as fast at
+ numerical groups, and processing duplicated groups should be faster than
+ before.
+
+20. Two patches to the CMake build system, by Alexander Barkov:
+
+ (1) Replace the "source" command by "." in CMakeLists.txt because
+ "source" is a bash-ism.
+
+ (2) Add missing HAVE_STDINT_H and HAVE_INTTYPES_H to config-cmake.h.in;
+ without these the CMake build does not work on Solaris.
+
+21. Perl has changed its handling of \8 and \9. If there is no previously
+ encountered capturing group of those numbers, they are treated as the
+ literal characters 8 and 9 instead of a binary zero followed by the
+ literals. PCRE now does the same.
+
+22. Following Perl, added \o{} to specify codepoints in octal, making it
+ possible to specify values greater than 0777 and also making them
+ unambiguous.
+
+23. Perl now gives an error for missing closing braces after \x{... instead of
+ treating the string as literal. PCRE now does the same.
+
+24. RunTest used to grumble if an inappropriate test was selected explicitly,
+ but just skip it when running all tests. This make it awkward to run ranges
+ of tests when one of them was inappropriate. Now it just skips any
+ inappropriate tests, as it always did when running all tests.
+
+25. If PCRE_AUTO_CALLOUT and PCRE_UCP were set for a pattern that contained
+ character types such as \d or \w, too many callouts were inserted, and the
+ data that they returned was rubbish.
+
+26. In UCP mode, \s was not matching two of the characters that Perl matches,
+ namely NEL (U+0085) and MONGOLIAN VOWEL SEPARATOR (U+180E), though they
+ were matched by \h. The code has now been refactored so that the lists of
+ the horizontal and vertical whitespace characters used for \h and \v (which
+ are defined only in one place) are now also used for \s.
+
+27. Add JIT support for the 64 bit TileGX architecture.
+ Patch by Jiong Wang (Tilera Corporation).
+
+28. Possessive quantifiers for classes (both explicit and automatically
+ generated) now use special opcodes instead of wrapping in ONCE brackets.
+
+29. Whereas an item such as A{4}+ ignored the possessivenes of the quantifier
+ (because it's meaningless), this was not happening when PCRE_CASELESS was
+ set. Not wrong, but inefficient.
+
+30. Updated perltest.pl to add /u (force Unicode mode) when /W (use Unicode
+ properties for \w, \d, etc) is present in a test regex. Otherwise if the
+ test contains no characters greater than 255, Perl doesn't realise it
+ should be using Unicode semantics.
+
+31. Upgraded the handling of the POSIX classes [:graph:], [:print:], and
+ [:punct:] when PCRE_UCP is set so as to include the same characters as Perl
+ does in Unicode mode.
+
+32. Added the "forbid" facility to pcretest so that putting tests into the
+ wrong test files can sometimes be quickly detected.
+
+33. There is now a limit (default 250) on the depth of nesting of parentheses.
+ This limit is imposed to control the amount of system stack used at compile
+ time. It can be changed at build time by --with-parens-nest-limit=xxx or
+ the equivalent in CMake.
+
+34. Character classes such as [A-\d] or [a-[:digit:]] now cause compile-time
+ errors. Perl warns for these when in warning mode, but PCRE has no facility
+ for giving warnings.
+
+35. Change 34 for 8.13 allowed quantifiers on assertions, because Perl does.
+ However, this was not working for (?!) because it is optimized to (*FAIL),
+ for which PCRE does not allow quantifiers. The optimization is now disabled
+ when a quantifier follows (?!). I can't see any use for this, but it makes
+ things uniform.
+
+36. Perl no longer allows group names to start with digits, so I have made this
+ change also in PCRE. It simplifies the code a bit.
+
+37. In extended mode, Perl ignores spaces before a + that indicates a
+ possessive quantifier. PCRE allowed a space before the quantifier, but not
+ before the possessive +. It now does.
+
+38. The use of \K (reset reported match start) within a repeated possessive
+ group such as (a\Kb)*+ was not working.
+
+40. Document that the same character tables must be used at compile time and
+ run time, and that the facility to pass tables to pcre_exec() and
+ pcre_dfa_exec() is for use only with saved/restored patterns.
+
+41. Applied Jeff Trawick's patch CMakeLists.txt, which "provides two new
+ features for Builds with MSVC:
+
+ 1. Support pcre.rc and/or pcreposix.rc (as is already done for MinGW
+ builds). The .rc files can be used to set FileDescription and many other
+ attributes.
+
+ 2. Add an option (-DINSTALL_MSVC_PDB) to enable installation of .pdb files.
+ This allows higher-level build scripts which want .pdb files to avoid
+ hard-coding the exact files needed."
+
+42. Added support for [[:<:]] and [[:>:]] as used in the BSD POSIX library to
+ mean "start of word" and "end of word", respectively, as a transition aid.
+
+43. A minimizing repeat of a class containing codepoints greater than 255 in
+ non-UTF 16-bit or 32-bit modes caused an internal error when PCRE was
+ compiled to use the heap for recursion.
+
+44. Got rid of some compiler warnings for unused variables when UTF but not UCP
+ is configured.
+
+
+Version 8.33 28-May-2013
+------------------------
+
+1. Added 'U' to some constants that are compared to unsigned integers, to
+ avoid compiler signed/unsigned warnings. Added (int) casts to unsigned
+ variables that are added to signed variables, to ensure the result is
+ signed and can be negated.
+
+2. Applied patch by Daniel Richard G for quashing MSVC warnings to the
+ CMake config files.
+
+3. Revise the creation of config.h.generic so that all boolean macros are
+ #undefined, whereas non-boolean macros are #ifndef/#endif-ed. This makes
+ overriding via -D on the command line possible.
+
+4. Changing the definition of the variable "op" in pcre_exec.c from pcre_uchar
+ to unsigned int is reported to make a quite noticeable speed difference in
+ a specific Windows environment. Testing on Linux did also appear to show
+ some benefit (and it is clearly not harmful). Also fixed the definition of
+ Xop which should be unsigned.
+
+5. Related to (4), changing the definition of the intermediate variable cc
+ in repeated character loops from pcre_uchar to pcre_uint32 also gave speed
+ improvements.
+
+6. Fix forward search in JIT when link size is 3 or greater. Also removed some
+ unnecessary spaces.
+
+7. Adjust autogen.sh and configure.ac to lose warnings given by automake 1.12
+ and later.
+
+8. Fix two buffer over read issues in 16 and 32 bit modes. Affects JIT only.
+
+9. Optimizing fast_forward_start_bits in JIT.
+
+10. Adding support for callouts in JIT, and fixing some issues revealed
+ during this work. Namely:
+
+ (a) Unoptimized capturing brackets incorrectly reset on backtrack.
+
+ (b) Minimum length was not checked before the matching is started.
+
+11. The value of capture_last that is passed to callouts was incorrect in some
+ cases when there was a capture on one path that was subsequently abandoned
+ after a backtrack. Also, the capture_last value is now reset after a
+ recursion, since all captures are also reset in this case.
+
+12. The interpreter no longer returns the "too many substrings" error in the
+ case when an overflowing capture is in a branch that is subsequently
+ abandoned after a backtrack.
+
+13. In the pathological case when an offset vector of size 2 is used, pcretest
+ now prints out the matched string after a yield of 0 or 1.
+
+14. Inlining subpatterns in recursions, when certain conditions are fulfilled.
+ Only supported by the JIT compiler at the moment.
+
+15. JIT compiler now supports 32 bit Macs thanks to Lawrence Velazquez.
+
+16. Partial matches now set offsets[2] to the "bumpalong" value, that is, the
+ offset of the starting point of the matching process, provided the offsets
+ vector is large enough.
+
+17. The \A escape now records a lookbehind value of 1, though its execution
+ does not actually inspect the previous character. This is to ensure that,
+ in partial multi-segment matching, at least one character from the old
+ segment is retained when a new segment is processed. Otherwise, if there
+ are no lookbehinds in the pattern, \A might match incorrectly at the start
+ of a new segment.
+
+18. Added some #ifdef __VMS code into pcretest.c to help VMS implementations.
+
+19. Redefined some pcre_uchar variables in pcre_exec.c as pcre_uint32; this
+ gives some modest performance improvement in 8-bit mode.
+
+20. Added the PCRE-specific property \p{Xuc} for matching characters that can
+ be expressed in certain programming languages using Universal Character
+ Names.
+
+21. Unicode validation has been updated in the light of Unicode Corrigendum #9,
+ which points out that "non characters" are not "characters that may not
+ appear in Unicode strings" but rather "characters that are reserved for
+ internal use and have only local meaning".
+
+22. When a pattern was compiled with automatic callouts (PCRE_AUTO_CALLOUT) and
+ there was a conditional group that depended on an assertion, if the
+ assertion was false, the callout that immediately followed the alternation
+ in the condition was skipped when pcre_exec() was used for matching.
+
+23. Allow an explicit callout to be inserted before an assertion that is the
+ condition for a conditional group, for compatibility with automatic
+ callouts, which always insert a callout at this point.
+
+24. In 8.31, (*COMMIT) was confined to within a recursive subpattern. Perl also
+ confines (*SKIP) and (*PRUNE) in the same way, and this has now been done.
+
+25. (*PRUNE) is now supported by the JIT compiler.
+
+26. Fix infinite loop when /(?<=(*SKIP)ac)a/ is matched against aa.
+
+27. Fix the case where there are two or more SKIPs with arguments that may be
+ ignored.
+
+28. (*SKIP) is now supported by the JIT compiler.
+
+29. (*THEN) is now supported by the JIT compiler.
+
+30. Update RunTest with additional test selector options.
+
+31. The way PCRE handles backtracking verbs has been changed in two ways.
+
+ (1) Previously, in something like (*COMMIT)(*SKIP), COMMIT would override
+ SKIP. Now, PCRE acts on whichever backtracking verb is reached first by
+ backtracking. In some cases this makes it more Perl-compatible, but Perl's
+ rather obscure rules do not always do the same thing.
+
+ (2) Previously, backtracking verbs were confined within assertions. This is
+ no longer the case for positive assertions, except for (*ACCEPT). Again,
+ this sometimes improves Perl compatibility, and sometimes does not.
+
+32. A number of tests that were in test 2 because Perl did things differently
+ have been moved to test 1, because either Perl or PCRE has changed, and
+ these tests are now compatible.
+
+32. Backtracking control verbs are now handled in the same way in JIT and
+ interpreter.
+
+33. An opening parenthesis in a MARK/PRUNE/SKIP/THEN name in a pattern that
+ contained a forward subroutine reference caused a compile error.
+
+34. Auto-detect and optimize limited repetitions in JIT.
+
+35. Implement PCRE_NEVER_UTF to lock out the use of UTF, in particular,
+ blocking (*UTF) etc.
+
+36. In the interpreter, maximizing pattern repetitions for characters and
+ character types now use tail recursion, which reduces stack usage.
+
+37. The value of the max lookbehind was not correctly preserved if a compiled
+ and saved regex was reloaded on a host of different endianness.
+
+38. Implemented (*LIMIT_MATCH) and (*LIMIT_RECURSION). As part of the extension
+ of the compiled pattern block, expand the flags field from 16 to 32 bits
+ because it was almost full.
+
+39. Try madvise first before posix_madvise.
+
+40. Change 7 for PCRE 7.9 made it impossible for pcregrep to find empty lines
+ with a pattern such as ^$. It has taken 4 years for anybody to notice! The
+ original change locked out all matches of empty strings. This has been
+ changed so that one match of an empty string per line is recognized.
+ Subsequent searches on the same line (for colouring or for --only-matching,
+ for example) do not recognize empty strings.
+
+41. Applied a user patch to fix a number of spelling mistakes in comments.
+
+42. Data lines longer than 65536 caused pcretest to crash.
+
+43. Clarified the data type for length and startoffset arguments for pcre_exec
+ and pcre_dfa_exec in the function-specific man pages, where they were
+ explicitly stated to be in bytes, never having been updated. I also added
+ some clarification to the pcreapi man page.
+
+44. A call to pcre_dfa_exec() with an output vector size less than 2 caused
+ a segmentation fault.
+
+
Version 8.32 30-November-2012
-----------------------------
@@ -1508,7 +1883,8 @@ Version 7.9 11-Apr-09
7. A pattern that could match an empty string could cause pcregrep to loop; it
doesn't make sense to accept an empty string match in pcregrep, so I have
locked it out (using PCRE's PCRE_NOTEMPTY option). By experiment, this
- seems to be how GNU grep behaves.
+ seems to be how GNU grep behaves. [But see later change 40 for release
+ 8.33.]
8. The pattern (?(?=.*b)b|^) was incorrectly compiled as "match must be at
start or after a newline", because the conditional assertion was not being
diff --git a/ext/pcre/pcrelib/HACKING b/ext/pcre/pcrelib/HACKING
index a90ddf8797..691b7a14e5 100644
--- a/ext/pcre/pcrelib/HACKING
+++ b/ext/pcre/pcrelib/HACKING
@@ -54,12 +54,12 @@ Support for 16-bit and 32-bit data strings
From release 8.30, PCRE supports 16-bit as well as 8-bit data strings; and from
release 8.32, PCRE supports 32-bit data strings. The library can be compiled
-in any combination of 8-bit, 16-bit or 32-bit modes, creating different
-libraries. In the description that follows, the word "short" is
-used for a 16-bit data quantity, and the word "unit" is used for a quantity
-that is a byte in 8-bit mode, a short in 16-bit mode and a 32-bit unsigned
-integer in 32-bit mode. However, so as not to over-complicate the text, the
-names of PCRE functions are given in 8-bit form only.
+in any combination of 8-bit, 16-bit or 32-bit modes, creating up to three
+different libraries. In the description that follows, the word "short" is used
+for a 16-bit data quantity, and the word "unit" is used for a quantity that is
+a byte in 8-bit mode, a short in 16-bit mode and a 32-bit word in 32-bit mode.
+However, so as not to over-complicate the text, the names of PCRE functions are
+given in 8-bit form only.
Computing the memory requirement: how it was
@@ -94,6 +94,11 @@ runs more slowly than before (30% or more, depending on the pattern) because it
is doing a full analysis of the pattern. My hope was that this would not be a
big issue, and in the event, nobody has commented on it.
+At release 8.34, a limit on the nesting depth of parentheses was re-introduced
+(default 250, settable at build time) so as to put a limit on the amount of
+system stack used by pcre_compile(). This is a safety feature for environments
+with small stacks where the patterns are provided by users.
+
Traditional matching function
-----------------------------
@@ -120,29 +125,30 @@ facilities are available, and those that are do not always work in quite the
same way. See the user documentation for details.
The algorithm that is used for pcre_dfa_exec() is not a traditional FSM,
-because it may have a number of states active at one time. More work would be
-needed at compile time to produce a traditional FSM where only one state is
-ever active at once. I believe some other regex matchers work this way.
+because it may have a number of states active at one time. More work would be
+needed at compile time to produce a traditional FSM where only one state is
+ever active at once. I believe some other regex matchers work this way. JIT
+support is not available for this kind of matching.
Changeable options
------------------
-The /i, /m, or /s options (PCRE_CASELESS, PCRE_MULTILINE, PCRE_DOTALL) may
-change in the middle of patterns. From PCRE 8.13, their processing is handled
-entirely at compile time by generating different opcodes for the different
-settings. The runtime functions do not need to keep track of an options state
-any more.
+The /i, /m, or /s options (PCRE_CASELESS, PCRE_MULTILINE, PCRE_DOTALL, and some
+others) may change in the middle of patterns. From PCRE 8.13, their processing
+is handled entirely at compile time by generating different opcodes for the
+different settings. The runtime functions do not need to keep track of an
+options state any more.
Format of compiled patterns
---------------------------
-The compiled form of a pattern is a vector of units (bytes in 8-bit mode, or
-shorts in 16-bit mode, 32-bit unsigned integers in 32-bit mode), containing
-items of variable length. The first unit in an item contains an opcode, and
-the length of the item is either implicit in the opcode or contained in the
-data that follows it.
+The compiled form of a pattern is a vector of unsigned units (bytes in 8-bit
+mode, shorts in 16-bit mode, 32-bit words in 32-bit mode), containing items of
+variable length. The first unit in an item contains an opcode, and the length
+of the item is either implicit in the opcode or contained in the data that
+follows it.
In many cases listed below, LINK_SIZE data values are specified for offsets
within the compiled pattern. LINK_SIZE always specifies a number of bytes. The
@@ -151,8 +157,10 @@ default value for LINK_SIZE is 2, but PCRE can be compiled to use 3-byte or
LINK_SIZE values are available only in 8-bit mode.) Specifing a LINK_SIZE
larger than 2 is necessary only when patterns whose compiled length is greater
than 64K are going to be processed. In this description, we assume the "normal"
-compilation options. Data values that are counts (e.g. for quantifiers) are
-always just two bytes long (one short in 16-bit mode).
+compilation options. Data values that are counts (e.g. quantifiers) are two
+bytes long in 8-bit mode (most significant byte first), or one unit in 16-bit
+and 32-bit modes.
+
Opcodes with no following data
------------------------------
@@ -162,7 +170,7 @@ These items are all just one unit long
OP_END end of pattern
OP_ANY match any one character other than newline
OP_ALLANY match any one character, including newline
- OP_ANYBYTE match any single byte, even in UTF-8 mode
+ OP_ANYBYTE match any single unit, even in UTF-8/16 mode
OP_SOD match start of data: \A
OP_SOM, start of match (subject + offset): \G
OP_SET_SOM, set start of match (\K)
@@ -180,28 +188,33 @@ These items are all just one unit long
OP_VSPACE \v
OP_NOT_WORDCHAR \W
OP_WORDCHAR \w
- OP_EODN match end of data or \n at end: \Z
+ OP_EODN match end of data or newline at end: \Z
OP_EOD match end of data: \z
OP_DOLL $ (end of data, or before final newline)
OP_DOLLM $ multiline mode (end of data or before newline)
- OP_EXTUNI match an extended Unicode character
+ OP_EXTUNI match an extended Unicode grapheme cluster
OP_ANYNL match any Unicode newline sequence
+ OP_ASSERT_ACCEPT )
OP_ACCEPT ) These are Perl 5.10's "backtracking control
OP_COMMIT ) verbs". If OP_ACCEPT is inside capturing
OP_FAIL ) parentheses, it may be preceded by one or more
- OP_PRUNE ) OP_CLOSE, followed by a 2-byte number,
- OP_SKIP ) indicating which parentheses must be closed.
+ OP_PRUNE ) OP_CLOSE, each followed by a count that
+ OP_SKIP ) indicates which parentheses must be closed.
+ OP_THEN )
+
+OP_ASSERT_ACCEPT is used when (*ACCEPT) is encountered within an assertion.
+This ends the assertion, not the entire pattern match.
-Backtracking control verbs with (optional) data
------------------------------------------------
+Backtracking control verbs with optional data
+---------------------------------------------
(*THEN) without an argument generates the opcode OP_THEN and no following data.
OP_MARK is followed by the mark name, preceded by a one-unit length, and
followed by a binary zero. For (*PRUNE), (*SKIP), and (*THEN) with arguments,
the opcodes OP_PRUNE_ARG, OP_SKIP_ARG, and OP_THEN_ARG are used, with the name
-following in the same format.
+following in the same format as OP_MARK.
Matching literal characters
@@ -212,6 +225,10 @@ casefully. For caseless matching, OP_CHARI is used. In UTF-8 or UTF-16 modes,
the character may be more than one unit long. In UTF-32 mode, characters
are always exactly one unit long.
+If there is only one character in a character class, OP_CHAR or OP_CHARI is
+used for a positive class, and OP_NOT or OP_NOTI for a negative one (that is,
+for something like [^a]).
+
Repeating single characters
---------------------------
@@ -232,10 +249,9 @@ following opcodes, which come in caseful and caseless versions:
Each opcode is followed by the character that is to be repeated. In ASCII mode,
these are two-unit items; in UTF-8 or UTF-16 modes, the length is variable; in
-UTF-32 mode these are one-unit items.
-Those with "MIN" in their names are the minimizing versions. Those with "POS"
-in their names are possessive versions. Other repeats make use of these
-opcodes:
+UTF-32 mode these are one-unit items. Those with "MIN" in their names are the
+minimizing versions. Those with "POS" in their names are possessive versions.
+Other repeats make use of these opcodes:
Caseful Caseless
OP_UPTO OP_UPTOI
@@ -243,10 +259,15 @@ opcodes:
OP_POSUPTO OP_POSUPTOI
OP_EXACT OP_EXACTI
-Each of these is followed by a two-byte (one short) count (most significant
-byte first in 8-bit mode) and then the repeated character. OP_UPTO matches from
-0 to the given number. A repeat with a non-zero minimum and a fixed maximum is
-coded as an OP_EXACT followed by an OP_UPTO (or OP_MINUPTO or OPT_POSUPTO).
+Each of these is followed by a count and then the repeated character. OP_UPTO
+matches from 0 to the given number. A repeat with a non-zero minimum and a
+fixed maximum is coded as an OP_EXACT followed by an OP_UPTO (or OP_MINUPTO or
+OPT_POSUPTO).
+
+Another set of matching repeating opcodes (called OP_NOTSTAR, OP_NOTSTARI,
+etc.) are used for repeated, negated, single-character classes such as [^a]*.
+The normal single-character opcodes (OP_STAR, etc.) are used for repeated
+positive single-character classes.
Repeating character types
@@ -277,7 +298,10 @@ Match by Unicode property
OP_PROP and OP_NOTPROP are used for positive and negative matches of a
character by testing its Unicode property (the \p and \P escape sequences).
Each is followed by two units that encode the desired property as a type and a
-value.
+value. The types are a set of #defines of the form PT_xxx, and the values are
+enumerations of the form ucp_xx, defined in the ucp.h source file. The value is
+relevant only for PT_GC (General Category), PT_PC (Particular Category), and
+PT_SC (Script).
Repeats of these items use the OP_TYPESTAR etc. set of opcodes, followed by
three units: OP_PROP or OP_NOTPROP, and then the desired property type and
@@ -287,67 +311,88 @@ value.
Character classes
-----------------
-If there is only one character in the class, OP_CHAR or OP_CHARI is used for a
+If there is only one character in a class, OP_CHAR or OP_CHARI is used for a
positive class, and OP_NOT or OP_NOTI for a negative one (that is, for
something like [^a]).
-Another set of 13 repeating opcodes (called OP_NOTSTAR etc.) are used for
-repeated, negated, single-character classes. The normal single-character
-opcodes (OP_STAR, etc.) are used for repeated positive single-character
-classes.
+A set of repeating opcodes (called OP_NOTSTAR etc.) are used for repeated,
+negated, single-character classes. The normal single-character opcodes
+(OP_STAR, etc.) are used for repeated positive single-character classes.
-When there is more than one character in a class and all the characters are
+When there is more than one character in a class, and all the code points are
less than 256, OP_CLASS is used for a positive class, and OP_NCLASS for a
-negative one. In either case, the opcode is followed by a 32-byte (16-short)
-bit map containing a 1 bit for every character that is acceptable. The bits are
-counted from the least significant end of each unit. In caseless mode, bits for
-both cases are set.
+negative one. In either case, the opcode is followed by a 32-byte (16-short,
+8-word) bit map containing a 1 bit for every character that is acceptable. The
+bits are counted from the least significant end of each unit. In caseless mode,
+bits for both cases are set.
+
+The reason for having both OP_CLASS and OP_NCLASS is so that, in UTF-8/16/32
+mode, subject characters with values greater than 255 can be handled correctly.
+For OP_CLASS they do not match, whereas for OP_NCLASS they do.
+
+For classes containing characters with values greater than 255 or that contain
+\p or \P, OP_XCLASS is used. It optionally uses a bit map if any code points
+are less than 256, followed by a list of pairs (for a range) and single
+characters. In caseless mode, both cases are explicitly listed.
-The reason for having both OP_CLASS and OP_NCLASS is so that, in UTF-8/16/32 mode,
-subject characters with values greater than 255 can be handled correctly. For
-OP_CLASS they do not match, whereas for OP_NCLASS they do.
+OP_XCLASS is followed by a unit containing flag bits: XCL_NOT indicates that
+this is a negative class, and XCL_MAP indicates that a bit map is present.
+There follows the bit map, if XCL_MAP is set, and then a sequence of items
+coded as follows:
-For classes containing characters with values greater than 255, OP_XCLASS is
-used. It optionally uses a bit map (if any characters lie within it), followed
-by a list of pairs (for a range) and single characters. In caseless mode, both
-cases are explicitly listed. There is a flag character than indicates whether
-it is a positive or a negative class.
+ XCL_END marks the end of the list
+ XCL_SINGLE one character follows
+ XCL_RANGE two characters follow
+ XCL_PROP a Unicode property (type, value) follows
+ XCL_NOTPROP a Unicode property (type, value) follows
+
+If a range starts with a code point less than 256 and ends with one greater
+than 256, an XCL_RANGE item is used, without setting any bits in the bit map.
+This means that if no other items in the class set bits in the map, a map is
+not needed.
Back references
---------------
-OP_REF (caseful) or OP_REFI (caseless) is followed by two bytes (one short)
-containing the reference number.
+OP_REF (caseful) or OP_REFI (caseless) is followed by a count containing the
+reference number if the reference is to a unique capturing group (either by
+number or by name). When named groups are used, there may be more than one
+group with the same name. In this case, a reference by name generates OP_DNREF
+or OP_DNREFI. These are followed by two counts: the index (not the byte offset)
+in the group name table of the first entry for the requred name, followed by
+the number of groups with the same name.
Repeating character classes and back references
-----------------------------------------------
Single-character classes are handled specially (see above). This section
-applies to OP_CLASS and OP_REF[I]. In both cases, the repeat information
-follows the base item. The matching code looks at the following opcode to see
-if it is one of
+applies to other classes and also to back references. In both cases, the repeat
+information follows the base item. The matching code looks at the following
+opcode to see if it is one of
OP_CRSTAR
OP_CRMINSTAR
+ OP_CRPOSSTAR
OP_CRPLUS
OP_CRMINPLUS
+ OP_CRPOSPLUS
OP_CRQUERY
OP_CRMINQUERY
+ OP_CRPOSQUERY
OP_CRRANGE
OP_CRMINRANGE
+ OP_CRPOSRANGE
-All but the last two are just single-unit items. The others are followed by
-four bytes (two shorts) of data, comprising the minimum and maximum repeat
-counts. There are no special possessive opcodes for these repeats; a possessive
-repeat is compiled into an atomic group.
+All but the last three are single-unit items, with no data. The others are
+followed by the minimum and maximum repeat counts.
Brackets and alternation
------------------------
-A pair of non-capturing (round) brackets is wrapped round each expression at
+A pair of non-capturing round brackets is wrapped round each expression at
compile time, so alternation always happens in the context of brackets.
[Note for North Americans: "bracket" to some English speakers, including
@@ -364,20 +409,20 @@ A bracket opcode is followed by LINK_SIZE bytes which give the offset to the
next alternative OP_ALT or, if there aren't any branches, to the matching
OP_KET opcode. Each OP_ALT is followed by LINK_SIZE bytes giving the offset to
the next one, or to the OP_KET opcode. For capturing brackets, the bracket
-number immediately follows the offset, always as a 2-byte (one short) item.
+number is a count that immediately follows the offset.
-OP_KET is used for subpatterns that do not repeat indefinitely, and
-OP_KETRMIN and OP_KETRMAX are used for indefinite repetitions, minimally or
-maximally respectively (see below for possessive repetitions). All three are
-followed by LINK_SIZE bytes giving (as a positive number) the offset back to
-the matching bracket opcode.
+OP_KET is used for subpatterns that do not repeat indefinitely, and OP_KETRMIN
+and OP_KETRMAX are used for indefinite repetitions, minimally or maximally
+respectively (see below for possessive repetitions). All three are followed by
+LINK_SIZE bytes giving (as a positive number) the offset back to the matching
+bracket opcode.
If a subpattern is quantified such that it is permitted to match zero times, it
is preceded by one of OP_BRAZERO, OP_BRAMINZERO, or OP_SKIPZERO. These are
single-unit opcodes that tell the matcher that skipping the following
subpattern entirely is a valid branch. In the case of the first two, not
skipping the pattern is also valid (greedy and non-greedy). The third is used
-when a pattern has the quantifier {0,0}. It cannot be entirely discarded,
+when a pattern has the quantifier {0,0}. It cannot be entirely discarded,
because it may be called as a subroutine from elsewhere in the regex.
A subpattern with an indefinite maximum repetition is replicated in the
@@ -397,6 +442,7 @@ final replication is changed to OP_SBRA or OP_SCBRA. This tells the matcher
that it needs to check for matching an empty string when it hits OP_KETRMIN or
OP_KETRMAX, and if so, to break the loop.
+
Possessive brackets
-------------------
@@ -407,26 +453,34 @@ of OP_SCBRA. The end of such a group is marked by OP_KETRPOS. If the minimum
repetition is zero, the group is preceded by OP_BRAPOSZERO.
-Assertions
-----------
+Once-only (atomic) groups
+-------------------------
-Forward assertions are just like other subpatterns, but starting with one of
-the opcodes OP_ASSERT or OP_ASSERT_NOT. Backward assertions use the opcodes
-OP_ASSERTBACK and OP_ASSERTBACK_NOT, and the first opcode inside the assertion
-is OP_REVERSE, followed by a two byte (one short) count of the number of
-characters to move back the pointer in the subject string. In ASCII mode, the
-count is a number of units, but in UTF-8/16 mode each character may occupy more
-than one unit; in UTF-32 mode each character occupies exactly one unit.
-A separate count is present in each alternative of a lookbehind
-assertion, allowing them to have different fixed lengths.
+These are just like other subpatterns, but they start with the opcode
+OP_ONCE or OP_ONCE_NC. The former is used when there are no capturing brackets
+within the atomic group; the latter when there are. The distinction is needed
+for when there is a backtrack to before the group - any captures within the
+group must be reset, so it is necessary to retain backtracking points inside
+the group even after it is complete in order to do this. When there are no
+captures in an atomic group, all the backtracking can be discarded when it is
+complete. This is more efficient, and also uses less stack.
+The check for matching an empty string in an unbounded repeat is handled
+entirely at runtime, so there are just these two opcodes for atomic groups.
-Once-only (atomic) subpatterns
-------------------------------
-These are also just like other subpatterns, but they start with the opcode
-OP_ONCE. The check for matching an empty string in an unbounded repeat is
-handled entirely at runtime, so there is just this one opcode.
+Assertions
+----------
+
+Forward assertions are also just like other subpatterns, but starting with one
+of the opcodes OP_ASSERT or OP_ASSERT_NOT. Backward assertions use the opcodes
+OP_ASSERTBACK and OP_ASSERTBACK_NOT, and the first opcode inside the assertion
+is OP_REVERSE, followed by a count of the number of characters to move back the
+pointer in the subject string. In ASCII mode, the count is a number of units,
+but in UTF-8/16 mode each character may occupy more than one unit; in UTF-32
+mode each character occupies exactly one unit. A separate count is present in
+each alternative of a lookbehind assertion, allowing them to have different
+fixed lengths.
Conditional subpatterns
@@ -435,28 +489,29 @@ Conditional subpatterns
These are like other subpatterns, but they start with the opcode OP_COND, or
OP_SCOND for one that might match an empty string in an unbounded repeat. If
the condition is a back reference, this is stored at the start of the
-subpattern using the opcode OP_CREF followed by two bytes (one short)
-containing the reference number. OP_NCREF is used instead if the reference was
-generated by name (so that the runtime code knows to check for duplicate
-names).
+subpattern using the opcode OP_CREF followed by a count containing the
+reference number, provided that the reference is to a unique capturing group.
+If the reference was by name and there is more than one group with that name,
+OP_DNCREF is used instead. It is followed by two counts: the index in the group
+names table, and the number of groups with the same name.
If the condition is "in recursion" (coded as "(?(R)"), or "in recursion of
group x" (coded as "(?(Rx)"), the group number is stored at the start of the
-subpattern using the opcode OP_RREF or OP_NRREF (cf OP_NCREF), and a value of
-zero for "the whole pattern". For a DEFINE condition, just the single unit
-OP_DEF is used (it has no associated data). Otherwise, a conditional subpattern
-always starts with one of the assertions.
+subpattern using the opcode OP_RREF (with a value of zero for "the whole
+pattern") or OP_DNRREF (with data as for OP_DNCREF). For a DEFINE condition,
+just the single unit OP_DEF is used (it has no associated data). Otherwise, a
+conditional subpattern always starts with one of the assertions.
Recursion
---------
Recursion either matches the current regex, or some subexpression. The opcode
-OP_RECURSE is followed by an value which is the offset to the starting bracket
-from the start of the whole pattern. From release 6.5, OP_RECURSE is
-automatically wrapped inside OP_ONCE brackets (because otherwise some patterns
-broke it). OP_RECURSE is also used for "subroutine" calls, even though they
-are not strictly a recursion.
+OP_RECURSE is followed by aLINK_SIZE value that is the offset to the starting
+bracket from the start of the whole pattern. From release 6.5, OP_RECURSE is
+automatically wrapped inside OP_ONCE brackets, because otherwise some patterns
+broke it. OP_RECURSE is also used for "subroutine" calls, even though they are
+not strictly a recursion.
Callout
@@ -464,10 +519,10 @@ Callout
OP_CALLOUT is followed by one unit of data that holds a callout number in the
range 0 to 254 for manual callouts, or 255 for an automatic callout. In both
-cases there follows a two-byte (one short) value giving the offset in the
-pattern to the start of the following item, and another two-byte (one short)
-item giving the length of the next item.
-
+cases there follows a count giving the offset in the pattern string to the
+start of the following item, and another count giving the length of this item.
+These values make is possible for pcretest to output useful tracing information
+using automatic callouts.
Philip Hazel
-February 2012
+November 2013
diff --git a/ext/pcre/pcrelib/LICENCE b/ext/pcre/pcrelib/LICENCE
index 5ce31a828d..3aff6a62c0 100644
--- a/ext/pcre/pcrelib/LICENCE
+++ b/ext/pcre/pcrelib/LICENCE
@@ -24,7 +24,7 @@ Email domain: cam.ac.uk
University of Cambridge Computing Service,
Cambridge, England.
-Copyright (c) 1997-2012 University of Cambridge
+Copyright (c) 1997-2013 University of Cambridge
All rights reserved.
@@ -35,7 +35,7 @@ Written by: Zoltan Herczeg
Email local part: hzmester
Emain domain: freemail.hu
-Copyright(c) 2010-2012 Zoltan Herczeg
+Copyright(c) 2010-2013 Zoltan Herczeg
All rights reserved.
@@ -46,7 +46,7 @@ Written by: Zoltan Herczeg
Email local part: hzmester
Emain domain: freemail.hu
-Copyright(c) 2009-2012 Zoltan Herczeg
+Copyright(c) 2009-2013 Zoltan Herczeg
All rights reserved.
diff --git a/ext/pcre/pcrelib/NEWS b/ext/pcre/pcrelib/NEWS
index 082139f222..5f52f15346 100644
--- a/ext/pcre/pcrelib/NEWS
+++ b/ext/pcre/pcrelib/NEWS
@@ -1,6 +1,77 @@
News about PCRE releases
------------------------
+Release 8.34 15-December-2013
+-----------------------------
+
+As well as fixing the inevitable bugs, performance has been improved by
+refactoring and extending the amount of "auto-possessification" that PCRE does.
+Other notable changes:
+
+. Implemented PCRE_INFO_MATCH_EMPTY, which yields 1 if the pattern can match
+ an empty string. If it can, pcretest shows this in its information output.
+
+. A back reference to a named subpattern when there is more than one of the
+ same name now checks them in the order in which they appear in the pattern.
+ The first one that is set is used for the reference. Previously only the
+ first one was inspected. This change makes PCRE more compatible with Perl.
+
+. Unicode character properties were updated from Unicode 6.3.0.
+
+. The character VT has been added to the set of characters that match \s and
+ are generally treated as white space, following this same change in Perl
+ 5.18. There is now no difference between "Perl space" and "POSIX space".
+
+. Perl has changed its handling of \8 and \9. If there is no previously
+ encountered capturing group of those numbers, they are treated as the
+ literal characters 8 and 9 instead of a binary zero followed by the
+ literals. PCRE now does the same.
+
+. Following Perl, added \o{} to specify codepoints in octal, making it
+ possible to specify values greater than 0777 and also making them
+ unambiguous.
+
+. In UCP mode, \s was not matching two of the characters that Perl matches,
+ namely NEL (U+0085) and MONGOLIAN VOWEL SEPARATOR (U+180E), though they
+ were matched by \h.
+
+. Add JIT support for the 64 bit TileGX architecture.
+
+. Upgraded the handling of the POSIX classes [:graph:], [:print:], and
+ [:punct:] when PCRE_UCP is set so as to include the same characters as Perl
+ does in Unicode mode.
+
+. Perl no longer allows group names to start with digits, so I have made this
+ change also in PCRE.
+
+. Added support for [[:<:]] and [[:>:]] as used in the BSD POSIX library to
+ mean "start of word" and "end of word", respectively, as a transition aid.
+
+
+Release 8.33 28-May-2013
+--------------------------
+
+A number of bugs are fixed, and some performance improvements have been made.
+There are also some new features, of which these are the most important:
+
+. The behaviour of the backtracking verbs has been rationalized and
+ documented in more detail.
+
+. JIT now supports callouts and all of the backtracking verbs.
+
+. Unicode validation has been updated in the light of Unicode Corrigendum #9,
+ which points out that "non characters" are not "characters that may not
+ appear in Unicode strings" but rather "characters that are reserved for
+ internal use and have only local meaning".
+
+. (*LIMIT_MATCH=d) and (*LIMIT_RECURSION=d) have been added so that the
+ creator of a pattern can specify lower (but not higher) limits for the
+ matching process.
+
+. The PCRE_NEVER_UTF option is available to prevent pattern-writers from using
+ the (*UTF) feature, as this could be a security issue.
+
+
Release 8.32 30-November-2012
-----------------------------
diff --git a/ext/pcre/pcrelib/README b/ext/pcre/pcrelib/README
index a2c3d9b31c..51197df721 100644
--- a/ext/pcre/pcrelib/README
+++ b/ext/pcre/pcrelib/README
@@ -9,8 +9,10 @@ from:
ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/pcre-xxx.zip
There is a mailing list for discussion about the development of PCRE at
+pcre-dev@exim.org. You can access the archives and subscribe or manage your
+subscription here:
- pcre-dev@exim.org
+ https://lists.exim.org/mailman/listinfo/pcre-dev
Please read the NEWS file if you are upgrading from a previous release.
The contents of this README file are:
@@ -25,6 +27,8 @@ The contents of this README file are:
Shared libraries
Cross-compiling using autotools
Using HP's ANSI C++ compiler (aCC)
+ Compiling in Tru64 using native compilers
+ Using Sun's compilers for Solaris
Using PCRE from MySQL
Making new tarballs
Testing PCRE
@@ -35,10 +39,10 @@ The contents of this README file are:
The PCRE APIs
-------------
-PCRE is written in C, and it has its own API. There are three sets of functions,
-one for the 8-bit library, which processes strings of bytes, one for the
-16-bit library, which processes strings of 16-bit values, and one for the 32-bit
-library, which processes strings of 32-bit values. The distribution also
+PCRE is written in C, and it has its own API. There are three sets of
+functions, one for the 8-bit library, which processes strings of bytes, one for
+the 16-bit library, which processes strings of 16-bit values, and one for the
+32-bit library, which processes strings of 32-bit values. The distribution also
includes a set of C++ wrapper functions (see the pcrecpp man page for details),
courtesy of Google Inc., which can be used to call the 8-bit PCRE library from
C++.
@@ -110,6 +114,11 @@ contributions provided support for compiling PCRE on various flavours of
Windows (I myself do not use Windows). Nowadays there is more Windows support
in the standard distribution, so these contibutions have been archived.
+A PCRE user maintains downloadable Windows binaries of the pcregrep and
+pcretest programs here:
+
+ http://www.rexegg.com/pcregrep-pcretest.html
+
Building PCRE on non-Unix-like systems
--------------------------------------
@@ -260,9 +269,17 @@ library. They are also documented in the pcrebuild man page.
on the "configure" command.
-. PCRE has a counter that can be set to limit the amount of resources it uses.
- If the limit is exceeded during a match, the match fails. The default is ten
- million. You can change the default by setting, for example,
+. PCRE has a counter that limits the depth of nesting of parentheses in a
+ pattern. This limits the amount of system stack that a pattern uses when it
+ is compiled. The default is 250, but you can change it by setting, for
+ example,
+
+ --with-parens-nest-limit=500
+
+. PCRE has a counter that can be set to limit the amount of resources it uses
+ when matching a pattern. If the limit is exceeded during a match, the match
+ fails. The default is ten million. You can change the default by setting, for
+ example,
--with-match-limit=500000
@@ -342,7 +359,8 @@ library. They are also documented in the pcrebuild man page.
report is generated by running "make coverage". If ccache is installed on
your system, it must be disabled when building PCRE for coverage reporting.
You can do this by setting the environment variable CCACHE_DISABLE=1 before
- running "make" to build PCRE.
+ running "make" to build PCRE. There is more information about coverage
+ reporting in the "pcrebuild" documentation.
. The pcregrep program currently supports only 8-bit data files, and so
requires the 8-bit PCRE library. It is possible to compile pcregrep to use
@@ -575,6 +593,27 @@ running the "configure" script:
CXXLDFLAGS="-lstd_v2 -lCsup_v2"
+Compiling in Tru64 using native compilers
+-----------------------------------------
+
+The following error may occur when compiling with native compilers in the Tru64
+operating system:
+
+ CXX libpcrecpp_la-pcrecpp.lo
+cxx: Error: /usr/lib/cmplrs/cxx/V7.1-006/include/cxx/iosfwd, line 58: #error
+ directive: "cannot include iosfwd -- define __USE_STD_IOSTREAM to
+ override default - see section 7.1.2 of the C++ Using Guide"
+#error "cannot include iosfwd -- define __USE_STD_IOSTREAM to override default
+- see section 7.1.2 of the C++ Using Guide"
+
+This may be followed by other errors, complaining that 'namespace "std" has no
+member'. The solution to this is to add the line
+
+#define __USE_STD_IOSTREAM 1
+
+to the config.h file.
+
+
Using Sun's compilers for Solaris
---------------------------------
@@ -624,27 +663,40 @@ NON-AUTOTOOLS-BUILD.
The RunTest script runs the pcretest test program (which is documented in its
own man page) on each of the relevant testinput files in the testdata
directory, and compares the output with the contents of the corresponding
-testoutput files. Some tests are relevant only when certain build-time options
-were selected. For example, the tests for UTF-8/16/32 support are run only if
---enable-utf was used. RunTest outputs a comment when it skips a test.
+testoutput files. RunTest uses a file called testtry to hold the main output
+from pcretest. Other files whose names begin with "test" are used as working
+files in some tests.
+
+Some tests are relevant only when certain build-time options were selected. For
+example, the tests for UTF-8/16/32 support are run only if --enable-utf was
+used. RunTest outputs a comment when it skips a test.
Many of the tests that are not skipped are run up to three times. The second
run forces pcre_study() to be called for all patterns except for a few in some
tests that are marked "never study" (see the pcretest program for how this is
done). If JIT support is available, the non-DFA tests are run a third time,
this time with a forced pcre_study() with the PCRE_STUDY_JIT_COMPILE option.
+This testing can be suppressed by putting "nojit" on the RunTest command line.
The entire set of tests is run once for each of the 8-bit, 16-bit and 32-bit
libraries that are enabled. If you want to run just one set of tests, call
RunTest with either the -8, -16 or -32 option.
-RunTest uses a file called testtry to hold the main output from pcretest.
-Other files whose names begin with "test" are used as working files in some
-tests. To run pcretest on just one or more specific test files, give their
-numbers as arguments to RunTest, for example:
+If valgrind is installed, you can run the tests under it by putting "valgrind"
+on the RunTest command line. To run pcretest on just one or more specific test
+files, give their numbers as arguments to RunTest, for example:
RunTest 2 7 11
+You can also specify ranges of tests such as 3-6 or 3- (meaning 3 to the
+end), or a number preceded by ~ to exclude a test. For example:
+
+ Runtest 3-15 ~10
+
+This runs tests 3 to 15, excluding test 10, and just ~13 runs all the tests
+except test 13. Whatever order the arguments are in, the tests are always run
+in numerical order.
+
You can also call RunTest with the single argument "list" to cause it to output
a list of tests.
@@ -704,21 +756,24 @@ test is run only when JIT support is not available. They test some JIT-specific
features such as information output from pcretest about JIT compilation.
The fourteenth, fifteenth, and sixteenth tests are run only in 8-bit mode, and
-the seventeenth, eighteenth, and nineteenth tests are run only in 16/32-bit mode.
-These are tests that generate different output in the two modes. They are for
-general cases, UTF-8/16/32 support, and Unicode property support, respectively.
+the seventeenth, eighteenth, and nineteenth tests are run only in 16/32-bit
+mode. These are tests that generate different output in the two modes. They are
+for general cases, UTF-8/16/32 support, and Unicode property support,
+respectively.
The twentieth test is run only in 16/32-bit mode. It tests some specific
16/32-bit features of the DFA matching engine.
-The twenty-first and twenty-second tests are run only in 16/32-bit mode, when the
-link size is set to 2 for the 16-bit library. They test reloading pre-compiled patterns.
+The twenty-first and twenty-second tests are run only in 16/32-bit mode, when
+the link size is set to 2 for the 16-bit library. They test reloading
+pre-compiled patterns.
+
+The twenty-third and twenty-fourth tests are run only in 16-bit mode. They are
+for general cases, and UTF-16 support, respectively.
-The twenty-third and twenty-fourth tests are run only in 16-bit mode. They are for
-general cases, and UTF-16 support, respectively.
+The twenty-fifth and twenty-sixth tests are run only in 32-bit mode. They are
+for general cases, and UTF-32 support, respectively.
-The twenty-fifth and twenty-sixth tests are run only in 32-bit mode. They are for
-general cases, and UTF-32 support, respectively.
Character tables
----------------
@@ -784,11 +839,11 @@ pcre_xxx, one with the name pcre16_xx, and a third with the name pcre32_xxx.
(A) Source files of the PCRE library functions and their headers:
dftables.c auxiliary program for building pcre_chartables.c
- when --enable-rebuild-chartables is specified
+ when --enable-rebuild-chartables is specified
pcre_chartables.c.dist a default set of character tables that assume ASCII
- coding; used, unless --enable-rebuild-chartables is
- specified, by copying to pcre[16]_chartables.c
+ coding; used, unless --enable-rebuild-chartables is
+ specified, by copying to pcre[16]_chartables.c
pcreposix.c )
pcre[16|32]_byte_order.c )
@@ -932,4 +987,4 @@ pcre_xxx, one with the name pcre16_xx, and a third with the name pcre32_xxx.
Philip Hazel
Email local part: ph10
Email domain: cam.ac.uk
-Last updated: 27 October 2012
+Last updated: 05 November 2013
diff --git a/ext/pcre/pcrelib/config.h b/ext/pcre/pcrelib/config.h
index bd18f535a7..a3b1b5dd38 100644
--- a/ext/pcre/pcrelib/config.h
+++ b/ext/pcre/pcrelib/config.h
@@ -302,6 +302,8 @@ them both to 0; an emulation function will be used. */
*/
/* #undef NO_RECURSE */
+#define PARENS_NEST_LIMIT 250
+
/* Name of package */
#define PACKAGE "pcre"
@@ -430,7 +432,7 @@ them both to 0; an emulation function will be used. */
/* Version number of package */
#ifndef VERSION
-#define VERSION "8.32"
+#define VERSION "8.34"
#endif
/* Define to empty if `const' does not conform to ANSI C. */
diff --git a/ext/pcre/pcrelib/doc/pcre.txt b/ext/pcre/pcrelib/doc/pcre.txt
index 2a2a82c7f1..9d69515c3b 100644
--- a/ext/pcre/pcrelib/doc/pcre.txt
+++ b/ext/pcre/pcrelib/doc/pcre.txt
@@ -8,13 +8,13 @@ pcretest commands.
-----------------------------------------------------------------------------
-PCRE(3) PCRE(3)
+PCRE(3) Library Functions Manual PCRE(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
INTRODUCTION
The PCRE library is a set of functions that implement regular expres-
@@ -33,110 +33,113 @@ INTRODUCTION
possible was done by Zoltan Herczeg.
Starting with release 8.32 it is possible to compile a third separate
- PCRE library, which supports 32-bit character strings (including UTF-32
- strings). The build process allows any set of the 8-, 16- and 32-bit
- libraries. The work to make this possible was done by Christian Persch.
-
- The three libraries contain identical sets of functions, except that
- the names in the 16-bit library start with pcre16_ instead of pcre_,
- and the names in the 32-bit library start with pcre32_ instead of
- pcre_. To avoid over-complication and reduce the documentation mainte-
+ PCRE library that supports 32-bit character strings (including UTF-32
+ strings). The build process allows any combination of the 8-, 16- and
+ 32-bit libraries. The work to make this possible was done by Christian
+ Persch.
+
+ The three libraries contain identical sets of functions, except that
+ the names in the 16-bit library start with pcre16_ instead of pcre_,
+ and the names in the 32-bit library start with pcre32_ instead of
+ pcre_. To avoid over-complication and reduce the documentation mainte-
nance load, most of the documentation describes the 8-bit library, with
- the differences for the 16-bit and 32-bit libraries described sepa-
- rately in the pcre16 and pcre32 pages. References to functions or
- structures of the form pcre[16|32]_xxx should be read as meaning
- "pcre_xxx when using the 8-bit library, pcre16_xxx when using the
+ the differences for the 16-bit and 32-bit libraries described sepa-
+ rately in the pcre16 and pcre32 pages. References to functions or
+ structures of the form pcre[16|32]_xxx should be read as meaning
+ "pcre_xxx when using the 8-bit library, pcre16_xxx when using the
16-bit library, or pcre32_xxx when using the 32-bit library".
- The current implementation of PCRE corresponds approximately with Perl
- 5.12, including support for UTF-8/16/32 encoded strings and Unicode
- general category properties. However, UTF-8/16/32 and Unicode support
+ The current implementation of PCRE corresponds approximately with Perl
+ 5.12, including support for UTF-8/16/32 encoded strings and Unicode
+ general category properties. However, UTF-8/16/32 and Unicode support
has to be explicitly enabled; it is not the default. The Unicode tables
- correspond to Unicode release 6.2.0.
+ correspond to Unicode release 6.3.0.
- In addition to the Perl-compatible matching function, PCRE contains an
- alternative function that matches the same compiled patterns in a dif-
+ In addition to the Perl-compatible matching function, PCRE contains an
+ alternative function that matches the same compiled patterns in a dif-
ferent way. In certain circumstances, the alternative function has some
- advantages. For a discussion of the two matching algorithms, see the
+ advantages. For a discussion of the two matching algorithms, see the
pcrematching page.
- PCRE is written in C and released as a C library. A number of people
- have written wrappers and interfaces of various kinds. In particular,
- Google Inc. have provided a comprehensive C++ wrapper for the 8-bit
- library. This is now included as part of the PCRE distribution. The
- pcrecpp page has details of this interface. Other people's contribu-
- tions can be found in the Contrib directory at the primary FTP site,
+ PCRE is written in C and released as a C library. A number of people
+ have written wrappers and interfaces of various kinds. In particular,
+ Google Inc. have provided a comprehensive C++ wrapper for the 8-bit
+ library. This is now included as part of the PCRE distribution. The
+ pcrecpp page has details of this interface. Other people's contribu-
+ tions can be found in the Contrib directory at the primary FTP site,
which is:
ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre
- Details of exactly which Perl regular expression features are and are
+ Details of exactly which Perl regular expression features are and are
not supported by PCRE are given in separate documents. See the pcrepat-
- tern and pcrecompat pages. There is a syntax summary in the pcresyntax
+ tern and pcrecompat pages. There is a syntax summary in the pcresyntax
page.
- Some features of PCRE can be included, excluded, or changed when the
- library is built. The pcre_config() function makes it possible for a
- client to discover which features are available. The features them-
- selves are described in the pcrebuild page. Documentation about build-
- ing PCRE for various operating systems can be found in the README and
+ Some features of PCRE can be included, excluded, or changed when the
+ library is built. The pcre_config() function makes it possible for a
+ client to discover which features are available. The features them-
+ selves are described in the pcrebuild page. Documentation about build-
+ ing PCRE for various operating systems can be found in the README and
NON-AUTOTOOLS_BUILD files in the source distribution.
- The libraries contains a number of undocumented internal functions and
- data tables that are used by more than one of the exported external
- functions, but which are not intended for use by external callers.
- Their names all begin with "_pcre_" or "_pcre16_" or "_pcre32_", which
- hopefully will not provoke any name clashes. In some environments, it
- is possible to control which external symbols are exported when a
- shared library is built, and in these cases the undocumented symbols
+ The libraries contains a number of undocumented internal functions and
+ data tables that are used by more than one of the exported external
+ functions, but which are not intended for use by external callers.
+ Their names all begin with "_pcre_" or "_pcre16_" or "_pcre32_", which
+ hopefully will not provoke any name clashes. In some environments, it
+ is possible to control which external symbols are exported when a
+ shared library is built, and in these cases the undocumented symbols
are not exported.
SECURITY CONSIDERATIONS
- If you are using PCRE in a non-UTF application that permits users to
- supply arbitrary patterns for compilation, you should be aware of a
+ If you are using PCRE in a non-UTF application that permits users to
+ supply arbitrary patterns for compilation, you should be aware of a
feature that allows users to turn on UTF support from within a pattern,
- provided that PCRE was built with UTF support. For example, an 8-bit
- pattern that begins with "(*UTF8)" or "(*UTF)" turns on UTF-8 mode,
- which interprets patterns and subjects as strings of UTF-8 characters
- instead of individual 8-bit characters. This causes both the pattern
+ provided that PCRE was built with UTF support. For example, an 8-bit
+ pattern that begins with "(*UTF8)" or "(*UTF)" turns on UTF-8 mode,
+ which interprets patterns and subjects as strings of UTF-8 characters
+ instead of individual 8-bit characters. This causes both the pattern
and any data against which it is matched to be checked for UTF-8 valid-
- ity. If the data string is very long, such a check might use suffi-
- ciently many resources as to cause your application to lose perfor-
+ ity. If the data string is very long, such a check might use suffi-
+ ciently many resources as to cause your application to lose perfor-
mance.
- The best way of guarding against this possibility is to use the
- pcre_fullinfo() function to check the compiled pattern's options for
- UTF.
+ One way of guarding against this possibility is to use the
+ pcre_fullinfo() function to check the compiled pattern's options for
+ UTF. Alternatively, from release 8.33, you can set the PCRE_NEVER_UTF
+ option at compile time. This causes an compile time error if a pattern
+ contains a UTF-setting sequence.
- If your application is one that supports UTF, be aware that validity
- checking can take time. If the same data string is to be matched many
+ If your application is one that supports UTF, be aware that validity
+ checking can take time. If the same data string is to be matched many
times, you can use the PCRE_NO_UTF[8|16|32]_CHECK option for the second
and subsequent matches to save redundant checks.
- Another way that performance can be hit is by running a pattern that
- has a very large search tree against a string that will never match.
- Nested unlimited repeats in a pattern are a common example. PCRE pro-
+ Another way that performance can be hit is by running a pattern that
+ has a very large search tree against a string that will never match.
+ Nested unlimited repeats in a pattern are a common example. PCRE pro-
vides some protection against this: see the PCRE_EXTRA_MATCH_LIMIT fea-
ture in the pcreapi page.
USER DOCUMENTATION
- The user documentation for PCRE comprises a number of different sec-
- tions. In the "man" format, each of these is a separate "man page". In
- the HTML format, each is a separate page, linked from the index page.
- In the plain text format, all the sections, except the pcredemo sec-
+ The user documentation for PCRE comprises a number of different sec-
+ tions. In the "man" format, each of these is a separate "man page". In
+ the HTML format, each is a separate page, linked from the index page.
+ In the plain text format, all the sections, except the pcredemo sec-
tion, are concatenated, for ease of searching. The sections are as fol-
lows:
pcre this document
+ pcre-config show PCRE installation configuration information
pcre16 details of the 16-bit library
pcre32 details of the 32-bit library
- pcre-config show PCRE installation configuration information
pcreapi details of PCRE's native C API
- pcrebuild options for building PCRE
+ pcrebuild building PCRE
pcrecallout details of the callout feature
pcrecompat discussion of Perl compatibility
pcrecpp details of the C++ wrapper for the 8-bit library
@@ -157,7 +160,7 @@ USER DOCUMENTATION
pcretest description of the pcretest testing command
pcreunicode discussion of Unicode and UTF-8/16/32 support
- In addition, in the "man" and HTML formats, there is a short page for
+ In addition, in the "man" and HTML formats, there is a short page for
each C library function, listing its arguments and results.
@@ -167,19 +170,20 @@ AUTHOR
University Computing Service
Cambridge CB2 3QH, England.
- Putting an actual email address here seems to have been a spam magnet,
- so I've taken it away. If you want to email me, use my two initials,
+ Putting an actual email address here seems to have been a spam magnet,
+ so I've taken it away. If you want to email me, use my two initials,
followed by the two digits 10, at the domain cam.ac.uk.
REVISION
- Last updated: 11 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 13 May 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRE(3) PCRE(3)
+PCRE(3) Library Functions Manual PCRE(3)
+
NAME
@@ -389,8 +393,10 @@ STRUCTURE TYPES
SUBJECT STRING OFFSETS
- The offsets within subject strings that are returned by the matching
- functions are in 16-bit units rather than bytes.
+ The lengths and starting offsets of subject strings must be specified
+ in 16-bit data units, and the offsets within subject strings that are
+ returned by the matching functions are in also 16-bit units rather than
+ bytes.
NAMED SUBPATTERNS
@@ -503,12 +509,13 @@ AUTHOR
REVISION
- Last updated: 08 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 May 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRE(3) PCRE(3)
+PCRE(3) Library Functions Manual PCRE(3)
+
NAME
@@ -525,7 +532,6 @@ PCRE 32-BIT API BASIC FUNCTIONS
pcre32 *pcre32_compile2(PCRE_SPTR32 pattern, int options,
int *errorcodeptr,
- const char **errptr, int *erroffset,
const unsigned char *tableptr);
pcre32_extra *pcre32_study(const pcre32 *code, int options,
@@ -718,8 +724,10 @@ STRUCTURE TYPES
SUBJECT STRING OFFSETS
- The offsets within subject strings that are returned by the matching
- functions are in 32-bit units rather than bytes.
+ The lengths and starting offsets of subject strings must be specified
+ in 32-bit data units, and the offsets within subject strings that are
+ returned by the matching functions are in also 32-bit units rather than
+ bytes.
NAMED SUBPATTERNS
@@ -829,33 +837,46 @@ AUTHOR
REVISION
- Last updated: 08 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 May 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREBUILD(3) PCREBUILD(3)
+PCREBUILD(3) Library Functions Manual PCREBUILD(3)
+
NAME
PCRE - Perl-compatible regular expressions
+BUILDING PCRE
+
+ PCRE is distributed with a configure script that can be used to build
+ the library in Unix-like environments using the applications known as
+ Autotools. Also in the distribution are files to support building
+ using CMake instead of configure. The text file README contains general
+ information about building with Autotools (some of which is repeated
+ below), and also has some comments about building on various operating
+ systems. There is a lot more information about building PCRE without
+ using Autotools (including information about using CMake and building
+ "by hand") in the text file called NON-AUTOTOOLS-BUILD. You should
+ consult this file as well as the README file if you are building in a
+ non-Unix-like environment.
+
PCRE BUILD-TIME OPTIONS
- This document describes the optional features of PCRE that can be
- selected when the library is compiled. It assumes use of the configure
- script, where the optional features are selected or deselected by pro-
- viding options to configure before running the make command. However,
- the same options can be selected in both Unix-like and non-Unix-like
- environments using the GUI facility of cmake-gui if you are using CMake
- instead of configure to build PCRE.
+ The rest of this document describes the optional features of PCRE that
+ can be selected when the library is compiled. It assumes use of the
+ configure script, where the optional features are selected or dese-
+ lected by providing options to configure before running the make com-
+ mand. However, the same options can be selected in both Unix-like and
+ non-Unix-like environments using the GUI facility of cmake-gui if you
+ are using CMake instead of configure to build PCRE.
- There is a lot more information about building PCRE without using con-
- figure (including information about using CMake or building "by hand")
- in the file called NON-AUTOTOOLS-BUILD, which is part of the PCRE dis-
- tribution. You should consult this file as well as the README file if
- you are building in a non-Unix-like environment.
+ If you are not using Autotools or CMake, option selection can be done
+ by editing the config.h file, or by passing parameter settings to the
+ compiler, as described in NON-AUTOTOOLS-BUILD.
The complete list of options for configure (which includes the standard
ones such as the selection of the installation directory) can be
@@ -882,10 +903,10 @@ BUILDING 8-BIT, 16-BIT AND 32-BIT LIBRARIES
--enable-pcre16
- to the configure command. You can also build a separate library, called
- libpcre32, in which strings are contained in vectors of 32-bit data
- units and interpreted either as single-unit characters or UTF-32
- strings, by adding
+ to the configure command. You can also build yet another separate
+ library, called libpcre32, in which strings are contained in vectors of
+ 32-bit data units and interpreted either as single-unit characters or
+ UTF-32 strings, by adding
--enable-pcre32
@@ -901,9 +922,9 @@ BUILDING 8-BIT, 16-BIT AND 32-BIT LIBRARIES
BUILDING SHARED AND STATIC LIBRARIES
- The PCRE building process uses libtool to build both shared and static
- Unix libraries by default. You can suppress one of these by adding one
- of
+ The Autotools PCRE building process uses libtool to build both shared
+ and static libraries by default. You can suppress one of these by
+ adding one of
--disable-shared
--disable-static
@@ -1319,18 +1340,18 @@ AUTHOR
REVISION
- Last updated: 30 October 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 May 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREMATCHING(3) PCREMATCHING(3)
+PCREMATCHING(3) Library Functions Manual PCREMATCHING(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE MATCHING ALGORITHMS
This document describes the two different algorithms that are available
@@ -1436,72 +1457,81 @@ THE ALTERNATIVE MATCHING ALGORITHM
at the fifth character of the subject. The algorithm does not automati-
cally move on to find matches that start at later positions.
+ PCRE's "auto-possessification" optimization usually applies to charac-
+ ter repeats at the end of a pattern (as well as internally). For exam-
+ ple, the pattern "a\d+" is compiled as if it were "a\d++" because there
+ is no point even considering the possibility of backtracking into the
+ repeated digits. For DFA matching, this means that only one possible
+ match is found. If you really do want multiple matches in such cases,
+ either use an ungreedy repeat ("a\d+?") or set the PCRE_NO_AUTO_POSSESS
+ option when compiling.
+
There are a number of features of PCRE regular expressions that are not
supported by the alternative matching algorithm. They are as follows:
- 1. Because the algorithm finds all possible matches, the greedy or
- ungreedy nature of repetition quantifiers is not relevant. Greedy and
+ 1. Because the algorithm finds all possible matches, the greedy or
+ ungreedy nature of repetition quantifiers is not relevant. Greedy and
ungreedy quantifiers are treated in exactly the same way. However, pos-
- sessive quantifiers can make a difference when what follows could also
+ sessive quantifiers can make a difference when what follows could also
match what is quantified, for example in a pattern like this:
^a++\w!
- This pattern matches "aaab!" but not "aaa!", which would be matched by
- a non-possessive quantifier. Similarly, if an atomic group is present,
- it is matched as if it were a standalone pattern at the current point,
- and the longest match is then "locked in" for the rest of the overall
+ This pattern matches "aaab!" but not "aaa!", which would be matched by
+ a non-possessive quantifier. Similarly, if an atomic group is present,
+ it is matched as if it were a standalone pattern at the current point,
+ and the longest match is then "locked in" for the rest of the overall
pattern.
2. When dealing with multiple paths through the tree simultaneously, it
- is not straightforward to keep track of captured substrings for the
- different matching possibilities, and PCRE's implementation of this
+ is not straightforward to keep track of captured substrings for the
+ different matching possibilities, and PCRE's implementation of this
algorithm does not attempt to do this. This means that no captured sub-
strings are available.
- 3. Because no substrings are captured, back references within the pat-
+ 3. Because no substrings are captured, back references within the pat-
tern are not supported, and cause errors if encountered.
- 4. For the same reason, conditional expressions that use a backrefer-
- ence as the condition or test for a specific group recursion are not
+ 4. For the same reason, conditional expressions that use a backrefer-
+ ence as the condition or test for a specific group recursion are not
supported.
- 5. Because many paths through the tree may be active, the \K escape
+ 5. Because many paths through the tree may be active, the \K escape
sequence, which resets the start of the match when encountered (but may
- be on some paths and not on others), is not supported. It causes an
+ be on some paths and not on others), is not supported. It causes an
error if encountered.
- 6. Callouts are supported, but the value of the capture_top field is
+ 6. Callouts are supported, but the value of the capture_top field is
always 1, and the value of the capture_last field is always -1.
- 7. The \C escape sequence, which (in the standard algorithm) always
- matches a single data unit, even in UTF-8, UTF-16 or UTF-32 modes, is
- not supported in these modes, because the alternative algorithm moves
+ 7. The \C escape sequence, which (in the standard algorithm) always
+ matches a single data unit, even in UTF-8, UTF-16 or UTF-32 modes, is
+ not supported in these modes, because the alternative algorithm moves
through the subject string one character (not data unit) at a time, for
all active paths through the tree.
- 8. Except for (*FAIL), the backtracking control verbs such as (*PRUNE)
- are not supported. (*FAIL) is supported, and behaves like a failing
+ 8. Except for (*FAIL), the backtracking control verbs such as (*PRUNE)
+ are not supported. (*FAIL) is supported, and behaves like a failing
negative assertion.
ADVANTAGES OF THE ALTERNATIVE ALGORITHM
- Using the alternative matching algorithm provides the following advan-
+ Using the alternative matching algorithm provides the following advan-
tages:
1. All possible matches (at a single point in the subject) are automat-
- ically found, and in particular, the longest match is found. To find
+ ically found, and in particular, the longest match is found. To find
more than one match using the standard algorithm, you have to do kludgy
things with callouts.
- 2. Because the alternative algorithm scans the subject string just
+ 2. Because the alternative algorithm scans the subject string just
once, and never needs to backtrack (except for lookbehinds), it is pos-
- sible to pass very long subject strings to the matching function in
+ sible to pass very long subject strings to the matching function in
several pieces, checking for partial matching each time. Although it is
- possible to do multi-segment matching using the standard algorithm by
- retaining partially matched substrings, it is more complicated. The
- pcrepartial documentation gives details of partial matching and dis-
+ possible to do multi-segment matching using the standard algorithm by
+ retaining partially matched substrings, it is more complicated. The
+ pcrepartial documentation gives details of partial matching and dis-
cusses multi-segment matching.
@@ -1509,8 +1539,8 @@ DISADVANTAGES OF THE ALTERNATIVE ALGORITHM
The alternative algorithm suffers from a number of disadvantages:
- 1. It is substantially slower than the standard algorithm. This is
- partly because it has to search for all possible matches, but is also
+ 1. It is substantially slower than the standard algorithm. This is
+ partly because it has to search for all possible matches, but is also
because it is less susceptible to optimization.
2. Capturing parentheses and back references are not supported.
@@ -1528,12 +1558,13 @@ AUTHOR
REVISION
- Last updated: 08 January 2012
+ Last updated: 12 November 2013
Copyright (c) 1997-2012 University of Cambridge.
------------------------------------------------------------------------------
-PCREAPI(3) PCREAPI(3)
+PCREAPI(3) Library Functions Manual PCREAPI(3)
+
NAME
@@ -1663,68 +1694,67 @@ PCRE 8-BIT, 16-BIT, AND 32-BIT LIBRARIES
ues.
References to bytes and UTF-8 in this document should be read as refer-
- ences to 16-bit data quantities and UTF-16 when using the 16-bit
- library, or 32-bit data quantities and UTF-32 when using the 32-bit
- library, unless specified otherwise. More details of the specific dif-
- ferences for the 16-bit and 32-bit libraries are given in the pcre16
- and pcre32 pages.
+ ences to 16-bit data units and UTF-16 when using the 16-bit library, or
+ 32-bit data units and UTF-32 when using the 32-bit library, unless
+ specified otherwise. More details of the specific differences for the
+ 16-bit and 32-bit libraries are given in the pcre16 and pcre32 pages.
PCRE API OVERVIEW
PCRE has its own native API, which is described in this document. There
- are also some wrapper functions (for the 8-bit library only) that cor-
- respond to the POSIX regular expression API, but they do not give
- access to all the functionality. They are described in the pcreposix
- documentation. Both of these APIs define a set of C function calls. A
+ are also some wrapper functions (for the 8-bit library only) that cor-
+ respond to the POSIX regular expression API, but they do not give
+ access to all the functionality. They are described in the pcreposix
+ documentation. Both of these APIs define a set of C function calls. A
C++ wrapper (again for the 8-bit library only) is also distributed with
PCRE. It is documented in the pcrecpp page.
- The native API C function prototypes are defined in the header file
- pcre.h, and on Unix-like systems the (8-bit) library itself is called
- libpcre. It can normally be accessed by adding -lpcre to the command
- for linking an application that uses PCRE. The header file defines the
+ The native API C function prototypes are defined in the header file
+ pcre.h, and on Unix-like systems the (8-bit) library itself is called
+ libpcre. It can normally be accessed by adding -lpcre to the command
+ for linking an application that uses PCRE. The header file defines the
macros PCRE_MAJOR and PCRE_MINOR to contain the major and minor release
- numbers for the library. Applications can use these to include support
+ numbers for the library. Applications can use these to include support
for different releases of PCRE.
In a Windows environment, if you want to statically link an application
- program against a non-dll pcre.a file, you must define PCRE_STATIC
- before including pcre.h or pcrecpp.h, because otherwise the pcre_mal-
+ program against a non-dll pcre.a file, you must define PCRE_STATIC
+ before including pcre.h or pcrecpp.h, because otherwise the pcre_mal-
loc() and pcre_free() exported functions will be declared
__declspec(dllimport), with unwanted results.
- The functions pcre_compile(), pcre_compile2(), pcre_study(), and
- pcre_exec() are used for compiling and matching regular expressions in
- a Perl-compatible manner. A sample program that demonstrates the sim-
- plest way of using them is provided in the file called pcredemo.c in
+ The functions pcre_compile(), pcre_compile2(), pcre_study(), and
+ pcre_exec() are used for compiling and matching regular expressions in
+ a Perl-compatible manner. A sample program that demonstrates the sim-
+ plest way of using them is provided in the file called pcredemo.c in
the PCRE source distribution. A listing of this program is given in the
- pcredemo documentation, and the pcresample documentation describes how
+ pcredemo documentation, and the pcresample documentation describes how
to compile and run it.
- Just-in-time compiler support is an optional feature of PCRE that can
+ Just-in-time compiler support is an optional feature of PCRE that can
be built in appropriate hardware environments. It greatly speeds up the
- matching performance of many patterns. Simple programs can easily
- request that it be used if available, by setting an option that is
- ignored when it is not relevant. More complicated programs might need
- to make use of the functions pcre_jit_stack_alloc(),
- pcre_jit_stack_free(), and pcre_assign_jit_stack() in order to control
+ matching performance of many patterns. Simple programs can easily
+ request that it be used if available, by setting an option that is
+ ignored when it is not relevant. More complicated programs might need
+ to make use of the functions pcre_jit_stack_alloc(),
+ pcre_jit_stack_free(), and pcre_assign_jit_stack() in order to control
the JIT code's memory usage.
- From release 8.32 there is also a direct interface for JIT execution,
- which gives improved performance. The JIT-specific functions are dis-
+ From release 8.32 there is also a direct interface for JIT execution,
+ which gives improved performance. The JIT-specific functions are dis-
cussed in the pcrejit documentation.
A second matching function, pcre_dfa_exec(), which is not Perl-compati-
- ble, is also provided. This uses a different algorithm for the match-
- ing. The alternative algorithm finds all possible matches (at a given
- point in the subject), and scans the subject just once (unless there
- are lookbehind assertions). However, this algorithm does not return
- captured substrings. A description of the two matching algorithms and
- their advantages and disadvantages is given in the pcrematching docu-
+ ble, is also provided. This uses a different algorithm for the match-
+ ing. The alternative algorithm finds all possible matches (at a given
+ point in the subject), and scans the subject just once (unless there
+ are lookbehind assertions). However, this algorithm does not return
+ captured substrings. A description of the two matching algorithms and
+ their advantages and disadvantages is given in the pcrematching docu-
mentation.
- In addition to the main compiling and matching functions, there are
+ In addition to the main compiling and matching functions, there are
convenience functions for extracting captured substrings from a subject
string that is matched by pcre_exec(). They are:
@@ -1739,105 +1769,105 @@ PCRE API OVERVIEW
pcre_free_substring() and pcre_free_substring_list() are also provided,
to free the memory used for extracted strings.
- The function pcre_maketables() is used to build a set of character
- tables in the current locale for passing to pcre_compile(),
- pcre_exec(), or pcre_dfa_exec(). This is an optional facility that is
- provided for specialist use. Most commonly, no special tables are
- passed, in which case internal tables that are generated when PCRE is
+ The function pcre_maketables() is used to build a set of character
+ tables in the current locale for passing to pcre_compile(),
+ pcre_exec(), or pcre_dfa_exec(). This is an optional facility that is
+ provided for specialist use. Most commonly, no special tables are
+ passed, in which case internal tables that are generated when PCRE is
built are used.
- The function pcre_fullinfo() is used to find out information about a
- compiled pattern. The function pcre_version() returns a pointer to a
+ The function pcre_fullinfo() is used to find out information about a
+ compiled pattern. The function pcre_version() returns a pointer to a
string containing the version of PCRE and its date of release.
- The function pcre_refcount() maintains a reference count in a data
- block containing a compiled pattern. This is provided for the benefit
+ The function pcre_refcount() maintains a reference count in a data
+ block containing a compiled pattern. This is provided for the benefit
of object-oriented applications.
- The global variables pcre_malloc and pcre_free initially contain the
- entry points of the standard malloc() and free() functions, respec-
+ The global variables pcre_malloc and pcre_free initially contain the
+ entry points of the standard malloc() and free() functions, respec-
tively. PCRE calls the memory management functions via these variables,
- so a calling program can replace them if it wishes to intercept the
+ so a calling program can replace them if it wishes to intercept the
calls. This should be done before calling any PCRE functions.
- The global variables pcre_stack_malloc and pcre_stack_free are also
- indirections to memory management functions. These special functions
- are used only when PCRE is compiled to use the heap for remembering
+ The global variables pcre_stack_malloc and pcre_stack_free are also
+ indirections to memory management functions. These special functions
+ are used only when PCRE is compiled to use the heap for remembering
data, instead of recursive function calls, when running the pcre_exec()
- function. See the pcrebuild documentation for details of how to do
- this. It is a non-standard way of building PCRE, for use in environ-
- ments that have limited stacks. Because of the greater use of memory
- management, it runs more slowly. Separate functions are provided so
- that special-purpose external code can be used for this case. When
- used, these functions are always called in a stack-like manner (last
- obtained, first freed), and always for memory blocks of the same size.
- There is a discussion about PCRE's stack usage in the pcrestack docu-
+ function. See the pcrebuild documentation for details of how to do
+ this. It is a non-standard way of building PCRE, for use in environ-
+ ments that have limited stacks. Because of the greater use of memory
+ management, it runs more slowly. Separate functions are provided so
+ that special-purpose external code can be used for this case. When
+ used, these functions are always called in a stack-like manner (last
+ obtained, first freed), and always for memory blocks of the same size.
+ There is a discussion about PCRE's stack usage in the pcrestack docu-
mentation.
The global variable pcre_callout initially contains NULL. It can be set
- by the caller to a "callout" function, which PCRE will then call at
- specified points during a matching operation. Details are given in the
+ by the caller to a "callout" function, which PCRE will then call at
+ specified points during a matching operation. Details are given in the
pcrecallout documentation.
NEWLINES
- PCRE supports five different conventions for indicating line breaks in
- strings: a single CR (carriage return) character, a single LF (line-
+ PCRE supports five different conventions for indicating line breaks in
+ strings: a single CR (carriage return) character, a single LF (line-
feed) character, the two-character sequence CRLF, any of the three pre-
- ceding, or any Unicode newline sequence. The Unicode newline sequences
- are the three just mentioned, plus the single characters VT (vertical
+ ceding, or any Unicode newline sequence. The Unicode newline sequences
+ are the three just mentioned, plus the single characters VT (vertical
tab, U+000B), FF (form feed, U+000C), NEL (next line, U+0085), LS (line
separator, U+2028), and PS (paragraph separator, U+2029).
- Each of the first three conventions is used by at least one operating
- system as its standard newline sequence. When PCRE is built, a default
- can be specified. The default default is LF, which is the Unix stan-
- dard. When PCRE is run, the default can be overridden, either when a
+ Each of the first three conventions is used by at least one operating
+ system as its standard newline sequence. When PCRE is built, a default
+ can be specified. The default default is LF, which is the Unix stan-
+ dard. When PCRE is run, the default can be overridden, either when a
pattern is compiled, or when it is matched.
At compile time, the newline convention can be specified by the options
- argument of pcre_compile(), or it can be specified by special text at
+ argument of pcre_compile(), or it can be specified by special text at
the start of the pattern itself; this overrides any other settings. See
the pcrepattern page for details of the special character sequences.
In the PCRE documentation the word "newline" is used to mean "the char-
- acter or pair of characters that indicate a line break". The choice of
- newline convention affects the handling of the dot, circumflex, and
+ acter or pair of characters that indicate a line break". The choice of
+ newline convention affects the handling of the dot, circumflex, and
dollar metacharacters, the handling of #-comments in /x mode, and, when
- CRLF is a recognized line ending sequence, the match position advance-
+ CRLF is a recognized line ending sequence, the match position advance-
ment for a non-anchored pattern. There is more detail about this in the
section on pcre_exec() options below.
- The choice of newline convention does not affect the interpretation of
- the \n or \r escape sequences, nor does it affect what \R matches,
+ The choice of newline convention does not affect the interpretation of
+ the \n or \r escape sequences, nor does it affect what \R matches,
which is controlled in a similar way, but by separate options.
MULTITHREADING
- The PCRE functions can be used in multi-threading applications, with
+ The PCRE functions can be used in multi-threading applications, with
the proviso that the memory management functions pointed to by
pcre_malloc, pcre_free, pcre_stack_malloc, and pcre_stack_free, and the
callout function pointed to by pcre_callout, are shared by all threads.
- The compiled form of a regular expression is not altered during match-
+ The compiled form of a regular expression is not altered during match-
ing, so the same compiled pattern can safely be used by several threads
at once.
- If the just-in-time optimization feature is being used, it needs sepa-
- rate memory stack areas for each thread. See the pcrejit documentation
+ If the just-in-time optimization feature is being used, it needs sepa-
+ rate memory stack areas for each thread. See the pcrejit documentation
for more details.
SAVING PRECOMPILED PATTERNS FOR LATER USE
The compiled form of a regular expression can be saved and re-used at a
- later time, possibly by a different program, and even on a host other
- than the one on which it was compiled. Details are given in the
- pcreprecompile documentation, which includes a description of the
- pcre_pattern_to_host_byte_order() function. However, compiling a regu-
- lar expression with one version of PCRE for use with a different ver-
+ later time, possibly by a different program, and even on a host other
+ than the one on which it was compiled. Details are given in the
+ pcreprecompile documentation, which includes a description of the
+ pcre_pattern_to_host_byte_order() function. However, compiling a regu-
+ lar expression with one version of PCRE for use with a different ver-
sion is not guaranteed to work and may cause crashes.
@@ -1845,45 +1875,45 @@ CHECKING BUILD-TIME OPTIONS
int pcre_config(int what, void *where);
- The function pcre_config() makes it possible for a PCRE client to dis-
+ The function pcre_config() makes it possible for a PCRE client to dis-
cover which optional features have been compiled into the PCRE library.
- The pcrebuild documentation has more details about these optional fea-
+ The pcrebuild documentation has more details about these optional fea-
tures.
- The first argument for pcre_config() is an integer, specifying which
+ The first argument for pcre_config() is an integer, specifying which
information is required; the second argument is a pointer to a variable
- into which the information is placed. The returned value is zero on
- success, or the negative error code PCRE_ERROR_BADOPTION if the value
- in the first argument is not recognized. The following information is
+ into which the information is placed. The returned value is zero on
+ success, or the negative error code PCRE_ERROR_BADOPTION if the value
+ in the first argument is not recognized. The following information is
available:
PCRE_CONFIG_UTF8
- The output is an integer that is set to one if UTF-8 support is avail-
- able; otherwise it is set to zero. This value should normally be given
+ The output is an integer that is set to one if UTF-8 support is avail-
+ able; otherwise it is set to zero. This value should normally be given
to the 8-bit version of this function, pcre_config(). If it is given to
- the 16-bit or 32-bit version of this function, the result is
+ the 16-bit or 32-bit version of this function, the result is
PCRE_ERROR_BADOPTION.
PCRE_CONFIG_UTF16
The output is an integer that is set to one if UTF-16 support is avail-
- able; otherwise it is set to zero. This value should normally be given
+ able; otherwise it is set to zero. This value should normally be given
to the 16-bit version of this function, pcre16_config(). If it is given
- to the 8-bit or 32-bit version of this function, the result is
+ to the 8-bit or 32-bit version of this function, the result is
PCRE_ERROR_BADOPTION.
PCRE_CONFIG_UTF32
The output is an integer that is set to one if UTF-32 support is avail-
- able; otherwise it is set to zero. This value should normally be given
+ able; otherwise it is set to zero. This value should normally be given
to the 32-bit version of this function, pcre32_config(). If it is given
- to the 8-bit or 16-bit version of this function, the result is
+ to the 8-bit or 16-bit version of this function, the result is
PCRE_ERROR_BADOPTION.
PCRE_CONFIG_UNICODE_PROPERTIES
- The output is an integer that is set to one if support for Unicode
+ The output is an integer that is set to one if support for Unicode
character properties is available; otherwise it is set to zero.
PCRE_CONFIG_JIT
@@ -1893,49 +1923,56 @@ CHECKING BUILD-TIME OPTIONS
PCRE_CONFIG_JITTARGET
- The output is a pointer to a zero-terminated "const char *" string. If
+ The output is a pointer to a zero-terminated "const char *" string. If
JIT support is available, the string contains the name of the architec-
- ture for which the JIT compiler is configured, for example "x86 32bit
- (little endian + unaligned)". If JIT support is not available, the
+ ture for which the JIT compiler is configured, for example "x86 32bit
+ (little endian + unaligned)". If JIT support is not available, the
result is NULL.
PCRE_CONFIG_NEWLINE
- The output is an integer whose value specifies the default character
- sequence that is recognized as meaning "newline". The values that are
+ The output is an integer whose value specifies the default character
+ sequence that is recognized as meaning "newline". The values that are
supported in ASCII/Unicode environments are: 10 for LF, 13 for CR, 3338
- for CRLF, -2 for ANYCRLF, and -1 for ANY. In EBCDIC environments, CR,
- ANYCRLF, and ANY yield the same values. However, the value for LF is
- normally 21, though some EBCDIC environments use 37. The corresponding
- values for CRLF are 3349 and 3365. The default should normally corre-
+ for CRLF, -2 for ANYCRLF, and -1 for ANY. In EBCDIC environments, CR,
+ ANYCRLF, and ANY yield the same values. However, the value for LF is
+ normally 21, though some EBCDIC environments use 37. The corresponding
+ values for CRLF are 3349 and 3365. The default should normally corre-
spond to the standard sequence for your operating system.
PCRE_CONFIG_BSR
The output is an integer whose value indicates what character sequences
- the \R escape sequence matches by default. A value of 0 means that \R
- matches any Unicode line ending sequence; a value of 1 means that \R
+ the \R escape sequence matches by default. A value of 0 means that \R
+ matches any Unicode line ending sequence; a value of 1 means that \R
matches only CR, LF, or CRLF. The default can be overridden when a pat-
tern is compiled or matched.
PCRE_CONFIG_LINK_SIZE
- The output is an integer that contains the number of bytes used for
+ The output is an integer that contains the number of bytes used for
internal linkage in compiled regular expressions. For the 8-bit
library, the value can be 2, 3, or 4. For the 16-bit library, the value
- is either 2 or 4 and is still a number of bytes. For the 32-bit
+ is either 2 or 4 and is still a number of bytes. For the 32-bit
library, the value is either 2 or 4 and is still a number of bytes. The
default value of 2 is sufficient for all but the most massive patterns,
- since it allows the compiled pattern to be up to 64K in size. Larger
- values allow larger regular expressions to be compiled, at the expense
+ since it allows the compiled pattern to be up to 64K in size. Larger
+ values allow larger regular expressions to be compiled, at the expense
of slower matching.
PCRE_CONFIG_POSIX_MALLOC_THRESHOLD
- The output is an integer that contains the threshold above which the
- POSIX interface uses malloc() for output vectors. Further details are
+ The output is an integer that contains the threshold above which the
+ POSIX interface uses malloc() for output vectors. Further details are
given in the pcreposix documentation.
+ PCRE_CONFIG_PARENS_LIMIT
+
+ The output is a long integer that gives the maximum depth of nesting of
+ parentheses (of any kind) in a pattern. This limit is imposed to cap
+ the amount of system stack used when a pattern is compiled. It is spec-
+ ified when PCRE is built; the default is 250.
+
PCRE_CONFIG_MATCH_LIMIT
The output is a long integer that gives the default limit for the num-
@@ -2008,15 +2045,17 @@ COMPILING A PATTERN
sets the variable pointed to by errptr to point to a textual error mes-
sage. This is a static string that is part of the library. You must not
try to free it. Normally, the offset from the start of the pattern to
- the byte that was being processed when the error was discovered is
+ the data unit that was being processed when the error was discovered is
placed in the variable pointed to by erroffset, which must not be NULL
(if it is, an immediate error is given). However, for an invalid UTF-8
- string, the offset is that of the first byte of the failing character.
+ or UTF-16 string, the offset is that of the first data unit of the
+ failing character.
- Some errors are not detected until the whole pattern has been scanned;
- in these cases, the offset passed back is the length of the pattern.
- Note that the offset is in bytes, not characters, even in UTF-8 mode.
- It may sometimes point into the middle of a UTF-8 character.
+ Some errors are not detected until the whole pattern has been scanned;
+ in these cases, the offset passed back is the length of the pattern.
+ Note that the offset is in data units, not characters, even in a UTF
+ mode. It may sometimes point into the middle of a UTF-8 or UTF-16 char-
+ acter.
If pcre_compile2() is used instead of pcre_compile(), and the error-
codeptr argument is not NULL, a non-zero error code number is returned
@@ -2027,9 +2066,9 @@ COMPILING A PATTERN
character tables that are built when PCRE is compiled, using the
default C locale. Otherwise, tableptr must be an address that is the
result of a call to pcre_maketables(). This value is stored with the
- compiled pattern, and used again by pcre_exec(), unless another table
- pointer is passed to it. For more discussion, see the section on locale
- support below.
+ compiled pattern, and used again by pcre_exec() and pcre_dfa_exec()
+ when the pattern is matched. For more discussion, see the section on
+ locale support below.
This code fragment shows a typical straightforward call to pcre_com-
pile():
@@ -2113,13 +2152,23 @@ COMPILING A PATTERN
PCRE_EXTENDED
- If this bit is set, white space data characters in the pattern are
- totally ignored except when escaped or inside a character class. White
- space does not include the VT character (code 11). In addition, charac-
- ters between an unescaped # outside a character class and the next new-
- line, inclusive, are also ignored. This is equivalent to Perl's /x
- option, and it can be changed within a pattern by a (?x) option set-
- ting.
+ If this bit is set, most white space characters in the pattern are
+ totally ignored except when escaped or inside a character class. How-
+ ever, white space is not allowed within sequences such as (?> that
+ introduce various parenthesized subpatterns, nor within a numerical
+ quantifier such as {1,3}. However, ignorable white space is permitted
+ between an item and a following quantifier and between a quantifier and
+ a following + that indicates possessiveness.
+
+ White space did not used to include the VT character (code 11), because
+ Perl did not treat this character as white space. However, Perl changed
+ at release 5.18, so PCRE followed at release 8.34, and VT is now
+ treated as white space.
+
+ PCRE_EXTENDED also causes characters between an unescaped # outside a
+ character class and the next newline, inclusive, to be ignored.
+ PCRE_EXTENDED is equivalent to Perl's /x option, and it can be changed
+ within a pattern by a (?x) option setting.
Which characters are interpreted as newlines is controlled by the
options passed to pcre_compile() or by a special sequence at the start
@@ -2186,21 +2235,33 @@ COMPILING A PATTERN
PCRE_MULTILINE
- By default, PCRE treats the subject string as consisting of a single
- line of characters (even if it actually contains newlines). The "start
- of line" metacharacter (^) matches only at the start of the string,
- while the "end of line" metacharacter ($) matches only at the end of
- the string, or before a terminating newline (unless PCRE_DOLLAR_ENDONLY
- is set). This is the same as Perl.
-
- When PCRE_MULTILINE it is set, the "start of line" and "end of line"
- constructs match immediately following or immediately before internal
- newlines in the subject string, respectively, as well as at the very
- start and end. This is equivalent to Perl's /m option, and it can be
+ By default, for the purposes of matching "start of line" and "end of
+ line", PCRE treats the subject string as consisting of a single line of
+ characters, even if it actually contains newlines. The "start of line"
+ metacharacter (^) matches only at the start of the string, and the "end
+ of line" metacharacter ($) matches only at the end of the string, or
+ before a terminating newline (except when PCRE_DOLLAR_ENDONLY is set).
+ Note, however, that unless PCRE_DOTALL is set, the "any character"
+ metacharacter (.) does not match at a newline. This behaviour (for ^,
+ $, and dot) is the same as Perl.
+
+ When PCRE_MULTILINE it is set, the "start of line" and "end of line"
+ constructs match immediately following or immediately before internal
+ newlines in the subject string, respectively, as well as at the very
+ start and end. This is equivalent to Perl's /m option, and it can be
changed within a pattern by a (?m) option setting. If there are no new-
- lines in a subject string, or no occurrences of ^ or $ in a pattern,
+ lines in a subject string, or no occurrences of ^ or $ in a pattern,
setting PCRE_MULTILINE has no effect.
+ PCRE_NEVER_UTF
+
+ This option locks out interpretation of the pattern as UTF-8 (or UTF-16
+ or UTF-32 in the 16-bit and 32-bit libraries). In particular, it pre-
+ vents the creator of the pattern from switching to UTF interpretation
+ by starting the pattern with (*UTF). This may be useful in applications
+ that process patterns from external sources. The combination of
+ PCRE_UTF8 and PCRE_NEVER_UTF also causes an error.
+
PCRE_NEWLINE_CR
PCRE_NEWLINE_LF
PCRE_NEWLINE_CRLF
@@ -2255,63 +2316,74 @@ COMPILING A PATTERN
be used for capturing (and they acquire numbers in the usual way).
There is no equivalent of this option in Perl.
- NO_START_OPTIMIZE
+ PCRE_NO_AUTO_POSSESS
+
+ If this option is set, it disables "auto-possessification". This is an
+ optimization that, for example, turns a+b into a++b in order to avoid
+ backtracks into a+ that can never be successful. However, if callouts
+ are in use, auto-possessification means that some of them are never
+ taken. You can set this option if you want the matching functions to do
+ a full unoptimized search and run all the callouts, but it is mainly
+ provided for testing purposes.
+
+ PCRE_NO_START_OPTIMIZE
This is an option that acts at matching time; that is, it is really an
option for pcre_exec() or pcre_dfa_exec(). If it is set at compile
time, it is remembered with the compiled pattern and assumed at match-
- ing time. For details see the discussion of PCRE_NO_START_OPTIMIZE
- below.
+ ing time. This is necessary if you want to use JIT execution, because
+ the JIT compiler needs to know whether or not this option is set. For
+ details see the discussion of PCRE_NO_START_OPTIMIZE below.
PCRE_UCP
- This option changes the way PCRE processes \B, \b, \D, \d, \S, \s, \W,
- \w, and some of the POSIX character classes. By default, only ASCII
- characters are recognized, but if PCRE_UCP is set, Unicode properties
- are used instead to classify characters. More details are given in the
- section on generic character types in the pcrepattern page. If you set
- PCRE_UCP, matching one of the items it affects takes much longer. The
- option is available only if PCRE has been compiled with Unicode prop-
+ This option changes the way PCRE processes \B, \b, \D, \d, \S, \s, \W,
+ \w, and some of the POSIX character classes. By default, only ASCII
+ characters are recognized, but if PCRE_UCP is set, Unicode properties
+ are used instead to classify characters. More details are given in the
+ section on generic character types in the pcrepattern page. If you set
+ PCRE_UCP, matching one of the items it affects takes much longer. The
+ option is available only if PCRE has been compiled with Unicode prop-
erty support.
PCRE_UNGREEDY
- This option inverts the "greediness" of the quantifiers so that they
- are not greedy by default, but become greedy if followed by "?". It is
- not compatible with Perl. It can also be set by a (?U) option setting
+ This option inverts the "greediness" of the quantifiers so that they
+ are not greedy by default, but become greedy if followed by "?". It is
+ not compatible with Perl. It can also be set by a (?U) option setting
within the pattern.
PCRE_UTF8
- This option causes PCRE to regard both the pattern and the subject as
+ This option causes PCRE to regard both the pattern and the subject as
strings of UTF-8 characters instead of single-byte strings. However, it
- is available only when PCRE is built to include UTF support. If not,
- the use of this option provokes an error. Details of how this option
+ is available only when PCRE is built to include UTF support. If not,
+ the use of this option provokes an error. Details of how this option
changes the behaviour of PCRE are given in the pcreunicode page.
PCRE_NO_UTF8_CHECK
When PCRE_UTF8 is set, the validity of the pattern as a UTF-8 string is
- automatically checked. There is a discussion about the validity of
- UTF-8 strings in the pcreunicode page. If an invalid UTF-8 sequence is
- found, pcre_compile() returns an error. If you already know that your
- pattern is valid, and you want to skip this check for performance rea-
- sons, you can set the PCRE_NO_UTF8_CHECK option. When it is set, the
+ automatically checked. There is a discussion about the validity of
+ UTF-8 strings in the pcreunicode page. If an invalid UTF-8 sequence is
+ found, pcre_compile() returns an error. If you already know that your
+ pattern is valid, and you want to skip this check for performance rea-
+ sons, you can set the PCRE_NO_UTF8_CHECK option. When it is set, the
effect of passing an invalid UTF-8 string as a pattern is undefined. It
- may cause your program to crash. Note that this option can also be
- passed to pcre_exec() and pcre_dfa_exec(), to suppress the validity
- checking of subject strings only. If the same string is being matched
- many times, the option can be safely set for the second and subsequent
+ may cause your program to crash or loop. Note that this option can also
+ be passed to pcre_exec() and pcre_dfa_exec(), to suppress the validity
+ checking of subject strings only. If the same string is being matched
+ many times, the option can be safely set for the second and subsequent
matchings to improve performance.
COMPILATION ERROR CODES
- The following table lists the error codes than may be returned by
- pcre_compile2(), along with the error messages that may be returned by
- both compiling functions. Note that error messages are always 8-bit
- ASCII strings, even in 16-bit or 32-bit mode. As PCRE has developed,
- some error codes have fallen out of use. To avoid confusion, they have
+ The following table lists the error codes than may be returned by
+ pcre_compile2(), along with the error messages that may be returned by
+ both compiling functions. Note that error messages are always 8-bit
+ ASCII strings, even in 16-bit or 32-bit mode. As PCRE has developed,
+ some error codes have fallen out of use. To avoid confusion, they have
not been re-used.
0 no error
@@ -2348,7 +2420,7 @@ COMPILATION ERROR CODES
31 POSIX collating elements are not supported
32 this version of PCRE is compiled without UTF support
33 [this code is not in use]
- 34 character value in \x{...} sequence is too large
+ 34 character value in \x{} or \o{} is too large
35 invalid condition (?(0)
36 \C not allowed in lookbehind assertion
37 PCRE does not support \L, \l, \N{name}, \U, or \u
@@ -2376,7 +2448,7 @@ COMPILATION ERROR CODES
name/number or by a plain number
58 a numbered reference must not be zero
59 an argument is not allowed for (*ACCEPT), (*FAIL), or (*COMMIT)
- 60 (*VERB) not recognized
+ 60 (*VERB) not recognized or malformed
61 number is too big
62 subpattern name expected
63 digit expected after (?+
@@ -2396,74 +2468,80 @@ COMPILATION ERROR CODES
75 name is too long in (*MARK), (*PRUNE), (*SKIP), or (*THEN)
76 character value in \u.... sequence is too large
77 invalid UTF-32 string (specifically UTF-32)
-
- The numbers 32 and 10000 in errors 48 and 49 are defaults; different
+ 78 setting UTF is disabled by the application
+ 79 non-hex character in \x{} (closing brace missing?)
+ 80 non-octal character in \o{} (closing brace missing?)
+ 81 missing opening brace after \o
+ 82 parentheses are too deeply nested
+ 83 invalid range in character class
+
+ The numbers 32 and 10000 in errors 48 and 49 are defaults; different
values may be used if the limits were changed when PCRE was built.
STUDYING A PATTERN
- pcre_extra *pcre_study(const pcre *code, int options
+ pcre_extra *pcre_study(const pcre *code, int options,
const char **errptr);
- If a compiled pattern is going to be used several times, it is worth
+ If a compiled pattern is going to be used several times, it is worth
spending more time analyzing it in order to speed up the time taken for
- matching. The function pcre_study() takes a pointer to a compiled pat-
+ matching. The function pcre_study() takes a pointer to a compiled pat-
tern as its first argument. If studying the pattern produces additional
- information that will help speed up matching, pcre_study() returns a
- pointer to a pcre_extra block, in which the study_data field points to
+ information that will help speed up matching, pcre_study() returns a
+ pointer to a pcre_extra block, in which the study_data field points to
the results of the study.
The returned value from pcre_study() can be passed directly to
- pcre_exec() or pcre_dfa_exec(). However, a pcre_extra block also con-
- tains other fields that can be set by the caller before the block is
+ pcre_exec() or pcre_dfa_exec(). However, a pcre_extra block also con-
+ tains other fields that can be set by the caller before the block is
passed; these are described below in the section on matching a pattern.
- If studying the pattern does not produce any useful information,
- pcre_study() returns NULL by default. In that circumstance, if the
+ If studying the pattern does not produce any useful information,
+ pcre_study() returns NULL by default. In that circumstance, if the
calling program wants to pass any of the other fields to pcre_exec() or
- pcre_dfa_exec(), it must set up its own pcre_extra block. However, if
- pcre_study() is called with the PCRE_STUDY_EXTRA_NEEDED option, it
+ pcre_dfa_exec(), it must set up its own pcre_extra block. However, if
+ pcre_study() is called with the PCRE_STUDY_EXTRA_NEEDED option, it
returns a pcre_extra block even if studying did not find any additional
- information. It may still return NULL, however, if an error occurs in
+ information. It may still return NULL, however, if an error occurs in
pcre_study().
- The second argument of pcre_study() contains option bits. There are
+ The second argument of pcre_study() contains option bits. There are
three further options in addition to PCRE_STUDY_EXTRA_NEEDED:
PCRE_STUDY_JIT_COMPILE
PCRE_STUDY_JIT_PARTIAL_HARD_COMPILE
PCRE_STUDY_JIT_PARTIAL_SOFT_COMPILE
- If any of these are set, and the just-in-time compiler is available,
- the pattern is further compiled into machine code that executes much
- faster than the pcre_exec() interpretive matching function. If the
- just-in-time compiler is not available, these options are ignored. All
+ If any of these are set, and the just-in-time compiler is available,
+ the pattern is further compiled into machine code that executes much
+ faster than the pcre_exec() interpretive matching function. If the
+ just-in-time compiler is not available, these options are ignored. All
undefined bits in the options argument must be zero.
- JIT compilation is a heavyweight optimization. It can take some time
- for patterns to be analyzed, and for one-off matches and simple pat-
- terns the benefit of faster execution might be offset by a much slower
+ JIT compilation is a heavyweight optimization. It can take some time
+ for patterns to be analyzed, and for one-off matches and simple pat-
+ terns the benefit of faster execution might be offset by a much slower
study time. Not all patterns can be optimized by the JIT compiler. For
- those that cannot be handled, matching automatically falls back to the
- pcre_exec() interpreter. For more details, see the pcrejit documenta-
+ those that cannot be handled, matching automatically falls back to the
+ pcre_exec() interpreter. For more details, see the pcrejit documenta-
tion.
- The third argument for pcre_study() is a pointer for an error message.
- If studying succeeds (even if no data is returned), the variable it
- points to is set to NULL. Otherwise it is set to point to a textual
+ The third argument for pcre_study() is a pointer for an error message.
+ If studying succeeds (even if no data is returned), the variable it
+ points to is set to NULL. Otherwise it is set to point to a textual
error message. This is a static string that is part of the library. You
- must not try to free it. You should test the error pointer for NULL
+ must not try to free it. You should test the error pointer for NULL
after calling pcre_study(), to be sure that it has run successfully.
- When you are finished with a pattern, you can free the memory used for
+ When you are finished with a pattern, you can free the memory used for
the study data by calling pcre_free_study(). This function was added to
- the API for release 8.20. For earlier versions, the memory could be
- freed with pcre_free(), just like the pattern itself. This will still
- work in cases where JIT optimization is not used, but it is advisable
+ the API for release 8.20. For earlier versions, the memory could be
+ freed with pcre_free(), just like the pattern itself. This will still
+ work in cases where JIT optimization is not used, but it is advisable
to change to the new function when convenient.
- This is a typical way in which pcre_study() is used (except that in a
+ This is a typical way in which pcre_study() is used (except that in a
real application there should be tests for errors):
int rc;
@@ -2483,41 +2561,50 @@ STUDYING A PATTERN
Studying a pattern does two things: first, a lower bound for the length
of subject string that is needed to match the pattern is computed. This
does not mean that there are any strings of that length that match, but
- it does guarantee that no shorter strings match. The value is used to
+ it does guarantee that no shorter strings match. The value is used to
avoid wasting time by trying to match strings that are shorter than the
- lower bound. You can find out the value in a calling program via the
+ lower bound. You can find out the value in a calling program via the
pcre_fullinfo() function.
Studying a pattern is also useful for non-anchored patterns that do not
- have a single fixed starting character. A bitmap of possible starting
- bytes is created. This speeds up finding a position in the subject at
+ have a single fixed starting character. A bitmap of possible starting
+ bytes is created. This speeds up finding a position in the subject at
which to start matching. (In 16-bit mode, the bitmap is used for 16-bit
- values less than 256. In 32-bit mode, the bitmap is used for 32-bit
+ values less than 256. In 32-bit mode, the bitmap is used for 32-bit
values less than 256.)
- These two optimizations apply to both pcre_exec() and pcre_dfa_exec(),
- and the information is also used by the JIT compiler. The optimiza-
- tions can be disabled by setting the PCRE_NO_START_OPTIMIZE option when
- calling pcre_exec() or pcre_dfa_exec(), but if this is done, JIT execu-
- tion is also disabled. You might want to do this if your pattern con-
- tains callouts or (*MARK) and you want to make use of these facilities
- in cases where matching fails. See the discussion of
- PCRE_NO_START_OPTIMIZE below.
+ These two optimizations apply to both pcre_exec() and pcre_dfa_exec(),
+ and the information is also used by the JIT compiler. The optimiza-
+ tions can be disabled by setting the PCRE_NO_START_OPTIMIZE option.
+ You might want to do this if your pattern contains callouts or (*MARK)
+ and you want to make use of these facilities in cases where matching
+ fails.
+
+ PCRE_NO_START_OPTIMIZE can be specified at either compile time or exe-
+ cution time. However, if PCRE_NO_START_OPTIMIZE is passed to
+ pcre_exec(), (that is, after any JIT compilation has happened) JIT exe-
+ cution is disabled. For JIT execution to work with PCRE_NO_START_OPTI-
+ MIZE, the option must be set at compile time.
+
+ There is a longer discussion of PCRE_NO_START_OPTIMIZE below.
LOCALE SUPPORT
- PCRE handles caseless matching, and determines whether characters are
- letters, digits, or whatever, by reference to a set of tables, indexed
- by character value. When running in UTF-8 mode, this applies only to
- characters with codes less than 128. By default, higher-valued codes
- never match escapes such as \w or \d, but they can be tested with \p if
- PCRE is built with Unicode character property support. Alternatively,
- the PCRE_UCP option can be set at compile time; this causes \w and
- friends to use Unicode property support instead of built-in tables. The
- use of locales with Unicode is discouraged. If you are handling charac-
- ters with codes greater than 128, you should either use UTF-8 and Uni-
- code, or use locales, but not try to mix the two.
+ PCRE handles caseless matching, and determines whether characters are
+ letters, digits, or whatever, by reference to a set of tables, indexed
+ by character code point. When running in UTF-8 mode, or in the 16- or
+ 32-bit libraries, this applies only to characters with code points less
+ than 256. By default, higher-valued code points never match escapes
+ such as \w or \d. However, if PCRE is built with Unicode property sup-
+ port, all characters can be tested with \p and \P, or, alternatively,
+ the PCRE_UCP option can be set when a pattern is compiled; this causes
+ \w and friends to use Unicode property support instead of the built-in
+ tables.
+
+ The use of locales with Unicode is discouraged. If you are handling
+ characters with code points greater than 128, you should either use
+ Unicode support, or use locales, but not try to mix the two.
PCRE contains an internal set of tables that are used when the final
argument of pcre_compile() is NULL. These are sufficient for many
@@ -2533,10 +2620,10 @@ LOCALE SUPPORT
External tables are built by calling the pcre_maketables() function,
which has no arguments, in the relevant locale. The result can then be
- passed to pcre_compile() or pcre_exec() as often as necessary. For
- example, to build and use tables that are appropriate for the French
- locale (where accented characters with values greater than 128 are
- treated as letters), the following code could be used:
+ passed to pcre_compile() as often as necessary. For example, to build
+ and use tables that are appropriate for the French locale (where
+ accented characters with values greater than 128 are treated as let-
+ ters), the following code could be used:
setlocale(LC_CTYPE, "fr_FR");
tables = pcre_maketables();
@@ -2552,15 +2639,19 @@ LOCALE SUPPORT
The pointer that is passed to pcre_compile() is saved with the compiled
pattern, and the same tables are used via this pointer by pcre_study()
- and normally also by pcre_exec(). Thus, by default, for any single pat-
+ and also by pcre_exec() and pcre_dfa_exec(). Thus, for any single pat-
tern, compilation, studying and matching all happen in the same locale,
- but different patterns can be compiled in different locales.
+ but different patterns can be processed in different locales.
It is possible to pass a table pointer or NULL (indicating the use of
- the internal tables) to pcre_exec(). Although not intended for this
- purpose, this facility could be used to match a pattern in a different
- locale from the one in which it was compiled. Passing table pointers at
- run time is discussed below in the section on matching a pattern.
+ the internal tables) to pcre_exec() or pcre_dfa_exec() (see the discus-
+ sion below in the section on matching a pattern). This facility is pro-
+ vided for use with pre-compiled patterns that have been saved and
+ reloaded. Character tables are not saved with patterns, so if a non-
+ standard table was used at compile time, it must be provided again when
+ the reloaded pattern is matched. Attempting to use this facility to
+ match a pattern in a different locale from the one in which it was com-
+ piled is likely to lead to anomalous (usually incorrect) results.
INFORMATION ABOUT A PATTERN
@@ -2585,6 +2676,7 @@ INFORMATION ABOUT A PATTERN
PCRE_ERROR_BADENDIANNESS the pattern was compiled with different
endianness
PCRE_ERROR_BADOPTION the value of what was invalid
+ PCRE_ERROR_UNSET the requested field is not set
The "magic number" is placed at the start of each compiled pattern as
an simple check against passing an arbitrary memory pointer. The endi-
@@ -2700,23 +2792,41 @@ INFORMATION ABOUT A PATTERN
/^a\dz\d/ the returned value is -1.
Since for the 32-bit library using the non-UTF-32 mode, this function
- is unable to return the full 32-bit range of the character, this value
- is deprecated; instead the PCRE_INFO_REQUIREDCHARFLAGS and
+ is unable to return the full 32-bit range of characters, this value is
+ deprecated; instead the PCRE_INFO_REQUIREDCHARFLAGS and
PCRE_INFO_REQUIREDCHAR values should be used.
+ PCRE_INFO_MATCH_EMPTY
+
+ Return 1 if the pattern can match an empty string, otherwise 0. The
+ fourth argument should point to an int variable.
+
+ PCRE_INFO_MATCHLIMIT
+
+ If the pattern set a match limit by including an item of the form
+ (*LIMIT_MATCH=nnnn) at the start, the value is returned. The fourth
+ argument should point to an unsigned 32-bit integer. If no such value
+ has been set, the call to pcre_fullinfo() returns the error
+ PCRE_ERROR_UNSET.
+
PCRE_INFO_MAXLOOKBEHIND
- Return the number of characters (NB not bytes) in the longest lookbe-
- hind assertion in the pattern. Note that the simple assertions \b and
- \B require a one-character lookbehind. This information is useful when
- doing multi-segment matching using the partial matching facilities.
+ Return the number of characters (NB not data units) in the longest
+ lookbehind assertion in the pattern. This information is useful when
+ doing multi-segment matching using the partial matching facilities.
+ Note that the simple assertions \b and \B require a one-character look-
+ behind. \A also registers a one-character lookbehind, though it does
+ not actually inspect the previous character. This is to ensure that at
+ least one character from the old segment is retained when a new segment
+ is processed. Otherwise, if there are no lookbehinds in the pattern, \A
+ might match incorrectly at the start of a new segment.
PCRE_INFO_MINLENGTH
If the pattern was studied and a minimum length for matching subject
strings was computed, its value is returned. Otherwise the returned
- value is -1. The value is a number of characters, which in UTF-8 mode
- may be different from the number of bytes. The fourth argument should
+ value is -1. The value is a number of characters, which in UTF mode may
+ be different from the number of data units. The fourth argument should
point to an int variable. A non-negative value is a lower bound to the
length of any matching string. There may not be any strings of that
length that do actually match, but every string that does match is at
@@ -2744,30 +2854,31 @@ INFORMATION ABOUT A PATTERN
the 8-bit library, where the first two bytes of each entry are the num-
ber of the capturing parenthesis, most significant byte first. In the
16-bit library, the pointer points to 16-bit data units, the first of
- which contains the parenthesis number. In the 32-bit library, the
+ which contains the parenthesis number. In the 32-bit library, the
pointer points to 32-bit data units, the first of which contains the
parenthesis number. The rest of the entry is the corresponding name,
zero terminated.
- The names are in alphabetical order. Duplicate names may appear if (?|
- is used to create multiple groups with the same number, as described in
- the section on duplicate subpattern numbers in the pcrepattern page.
- Duplicate names for subpatterns with different numbers are permitted
- only if PCRE_DUPNAMES is set. In all cases of duplicate names, they
- appear in the table in the order in which they were found in the pat-
- tern. In the absence of (?| this is the order of increasing number;
- when (?| is used this is not necessarily the case because later subpat-
- terns may have lower numbers.
-
- As a simple example of the name/number table, consider the following
+ The names are in alphabetical order. If (?| is used to create multiple
+ groups with the same number, as described in the section on duplicate
+ subpattern numbers in the pcrepattern page, the groups may be given the
+ same name, but there is only one entry in the table. Different names
+ for groups of the same number are not permitted. Duplicate names for
+ subpatterns with different numbers are permitted, but only if PCRE_DUP-
+ NAMES is set. They appear in the table in the order in which they were
+ found in the pattern. In the absence of (?| this is the order of
+ increasing number; when (?| is used this is not necessarily the case
+ because later subpatterns may have lower numbers.
+
+ As a simple example of the name/number table, consider the following
pattern after compilation by the 8-bit library (assume PCRE_EXTENDED is
set, so white space - including newlines - is ignored):
(?<date> (?<year>(\d\d)?\d\d) -
(?<month>\d\d) - (?<day>\d\d) )
- There are four named subpatterns, so the table has four entries, and
- each entry in the table is eight bytes long. The table is as follows,
+ There are four named subpatterns, so the table has four entries, and
+ each entry in the table is eight bytes long. The table is as follows,
with non-printing bytes shows in hexadecimal, and undefined bytes shown
as ??:
@@ -2776,31 +2887,31 @@ INFORMATION ABOUT A PATTERN
00 04 m o n t h 00
00 02 y e a r 00 ??
- When writing code to extract data from named subpatterns using the
- name-to-number map, remember that the length of the entries is likely
+ When writing code to extract data from named subpatterns using the
+ name-to-number map, remember that the length of the entries is likely
to be different for each compiled pattern.
PCRE_INFO_OKPARTIAL
- Return 1 if the pattern can be used for partial matching with
- pcre_exec(), otherwise 0. The fourth argument should point to an int
- variable. From release 8.00, this always returns 1, because the
- restrictions that previously applied to partial matching have been
- lifted. The pcrepartial documentation gives details of partial match-
+ Return 1 if the pattern can be used for partial matching with
+ pcre_exec(), otherwise 0. The fourth argument should point to an int
+ variable. From release 8.00, this always returns 1, because the
+ restrictions that previously applied to partial matching have been
+ lifted. The pcrepartial documentation gives details of partial match-
ing.
PCRE_INFO_OPTIONS
- Return a copy of the options with which the pattern was compiled. The
- fourth argument should point to an unsigned long int variable. These
+ Return a copy of the options with which the pattern was compiled. The
+ fourth argument should point to an unsigned long int variable. These
option bits are those specified in the call to pcre_compile(), modified
by any top-level option settings at the start of the pattern itself. In
- other words, they are the options that will be in force when matching
- starts. For example, if the pattern /(?im)abc(?-i)d/ is compiled with
- the PCRE_EXTENDED option, the result is PCRE_CASELESS, PCRE_MULTILINE,
+ other words, they are the options that will be in force when matching
+ starts. For example, if the pattern /(?im)abc(?-i)d/ is compiled with
+ the PCRE_EXTENDED option, the result is PCRE_CASELESS, PCRE_MULTILINE,
and PCRE_EXTENDED.
- A pattern is automatically anchored by PCRE if all of its top-level
+ A pattern is automatically anchored by PCRE if all of its top-level
alternatives begin with one of the following:
^ unless PCRE_MULTILINE is set
@@ -2812,42 +2923,50 @@ INFORMATION ABOUT A PATTERN
For such patterns, the PCRE_ANCHORED bit is set in the options returned
by pcre_fullinfo().
+ PCRE_INFO_RECURSIONLIMIT
+
+ If the pattern set a recursion limit by including an item of the form
+ (*LIMIT_RECURSION=nnnn) at the start, the value is returned. The fourth
+ argument should point to an unsigned 32-bit integer. If no such value
+ has been set, the call to pcre_fullinfo() returns the error
+ PCRE_ERROR_UNSET.
+
PCRE_INFO_SIZE
- Return the size of the compiled pattern in bytes (for both libraries).
- The fourth argument should point to a size_t variable. This value does
- not include the size of the pcre structure that is returned by
- pcre_compile(). The value that is passed as the argument to pcre_mal-
- loc() when pcre_compile() is getting memory in which to place the com-
- piled data is the value returned by this option plus the size of the
- pcre structure. Studying a compiled pattern, with or without JIT, does
- not alter the value returned by this option.
+ Return the size of the compiled pattern in bytes (for all three
+ libraries). The fourth argument should point to a size_t variable. This
+ value does not include the size of the pcre structure that is returned
+ by pcre_compile(). The value that is passed as the argument to
+ pcre_malloc() when pcre_compile() is getting memory in which to place
+ the compiled data is the value returned by this option plus the size of
+ the pcre structure. Studying a compiled pattern, with or without JIT,
+ does not alter the value returned by this option.
PCRE_INFO_STUDYSIZE
- Return the size in bytes of the data block pointed to by the study_data
- field in a pcre_extra block. If pcre_extra is NULL, or there is no
- study data, zero is returned. The fourth argument should point to a
- size_t variable. The study_data field is set by pcre_study() to record
- information that will speed up matching (see the section entitled
- "Studying a pattern" above). The format of the study_data block is pri-
- vate, but its length is made available via this option so that it can
- be saved and restored (see the pcreprecompile documentation for
- details).
+ Return the size in bytes (for all three libraries) of the data block
+ pointed to by the study_data field in a pcre_extra block. If pcre_extra
+ is NULL, or there is no study data, zero is returned. The fourth argu-
+ ment should point to a size_t variable. The study_data field is set by
+ pcre_study() to record information that will speed up matching (see the
+ section entitled "Studying a pattern" above). The format of the
+ study_data block is private, but its length is made available via this
+ option so that it can be saved and restored (see the pcreprecompile
+ documentation for details).
PCRE_INFO_FIRSTCHARACTERFLAGS
Return information about the first data unit of any matched string, for
- a non-anchored pattern. The fourth argument should point to an int
+ a non-anchored pattern. The fourth argument should point to an int
variable.
- If there is a fixed first value, for example, the letter "c" from a
- pattern such as (cat|cow|coyote), 1 is returned, and the character
+ If there is a fixed first value, for example, the letter "c" from a
+ pattern such as (cat|cow|coyote), 1 is returned, and the character
value can be retrieved using PCRE_INFO_FIRSTCHARACTER.
If there is no fixed first value, and if either
- (a) the pattern was compiled with the PCRE_MULTILINE option, and every
+ (a) the pattern was compiled with the PCRE_MULTILINE option, and every
branch starts with "^", or
(b) every branch of the pattern starts with ".*" and PCRE_DOTALL is not
@@ -2859,45 +2978,33 @@ INFORMATION ABOUT A PATTERN
PCRE_INFO_FIRSTCHARACTER
- Return the fixed first character value, if PCRE_INFO_FIRSTCHARACTER-
- FLAGS returned 1; otherwise returns 0. The fourth argument should point
- to an uint_t variable.
+ Return the fixed first character value in the situation where
+ PCRE_INFO_FIRSTCHARACTERFLAGS returns 1; otherwise return 0. The fourth
+ argument should point to an uint_t variable.
- In the 8-bit library, the value is always less than 256. In the 16-bit
- library the value can be up to 0xffff. In the 32-bit library in UTF-32
- mode the value can be up to 0x10ffff, and up to 0xffffffff when not
+ In the 8-bit library, the value is always less than 256. In the 16-bit
+ library the value can be up to 0xffff. In the 32-bit library in UTF-32
+ mode the value can be up to 0x10ffff, and up to 0xffffffff when not
using UTF-32 mode.
- If there is no fixed first value, and if either
-
- (a) the pattern was compiled with the PCRE_MULTILINE option, and every
- branch starts with "^", or
-
- (b) every branch of the pattern starts with ".*" and PCRE_DOTALL is not
- set (if it were set, the pattern would be anchored),
-
- -1 is returned, indicating that the pattern matches only at the start
- of a subject string or after any newline within the string. Otherwise
- -2 is returned. For anchored patterns, -2 is returned.
-
PCRE_INFO_REQUIREDCHARFLAGS
- Returns 1 if there is a rightmost literal data unit that must exist in
+ Returns 1 if there is a rightmost literal data unit that must exist in
any matched string, other than at its start. The fourth argument should
- point to an int variable. If there is no such value, 0 is returned. If
+ point to an int variable. If there is no such value, 0 is returned. If
returning 1, the character value itself can be retrieved using
PCRE_INFO_REQUIREDCHAR.
For anchored patterns, a last literal value is recorded only if it fol-
- lows something of variable length. For example, for the pattern
- /^a\d+z\d+/ the returned value 1 (with "z" returned from
+ lows something of variable length. For example, for the pattern
+ /^a\d+z\d+/ the returned value 1 (with "z" returned from
PCRE_INFO_REQUIREDCHAR), but for /^a\dz\d/ the returned value is 0.
PCRE_INFO_REQUIREDCHAR
- Return the value of the rightmost literal data unit that must exist in
- any matched string, other than at its start, if such a value has been
- recorded. The fourth argument should point to an uint32_t variable. If
+ Return the value of the rightmost literal data unit that must exist in
+ any matched string, other than at its start, if such a value has been
+ recorded. The fourth argument should point to an uint32_t variable. If
there is no such value, 0 is returned.
@@ -2905,21 +3012,21 @@ REFERENCE COUNTS
int pcre_refcount(pcre *code, int adjust);
- The pcre_refcount() function is used to maintain a reference count in
+ The pcre_refcount() function is used to maintain a reference count in
the data block that contains a compiled pattern. It is provided for the
- benefit of applications that operate in an object-oriented manner,
+ benefit of applications that operate in an object-oriented manner,
where different parts of the application may be using the same compiled
pattern, but you want to free the block when they are all done.
When a pattern is compiled, the reference count field is initialized to
- zero. It is changed only by calling this function, whose action is to
- add the adjust value (which may be positive or negative) to it. The
+ zero. It is changed only by calling this function, whose action is to
+ add the adjust value (which may be positive or negative) to it. The
yield of the function is the new value. However, the value of the count
- is constrained to lie between 0 and 65535, inclusive. If the new value
+ is constrained to lie between 0 and 65535, inclusive. If the new value
is outside these limits, it is forced to the appropriate limit value.
- Except when it is zero, the reference count is not correctly preserved
- if a pattern is compiled on one host and then transferred to a host
+ Except when it is zero, the reference count is not correctly preserved
+ if a pattern is compiled on one host and then transferred to a host
whose byte-order is different. (This seems a highly unlikely scenario.)
@@ -2929,22 +3036,22 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
const char *subject, int length, int startoffset,
int options, int *ovector, int ovecsize);
- The function pcre_exec() is called to match a subject string against a
- compiled pattern, which is passed in the code argument. If the pattern
- was studied, the result of the study should be passed in the extra
- argument. You can call pcre_exec() with the same code and extra argu-
- ments as many times as you like, in order to match different subject
+ The function pcre_exec() is called to match a subject string against a
+ compiled pattern, which is passed in the code argument. If the pattern
+ was studied, the result of the study should be passed in the extra
+ argument. You can call pcre_exec() with the same code and extra argu-
+ ments as many times as you like, in order to match different subject
strings with the same pattern.
- This function is the main matching facility of the library, and it
- operates in a Perl-like manner. For specialist use there is also an
- alternative matching function, which is described below in the section
+ This function is the main matching facility of the library, and it
+ operates in a Perl-like manner. For specialist use there is also an
+ alternative matching function, which is described below in the section
about the pcre_dfa_exec() function.
- In most applications, the pattern will have been compiled (and option-
- ally studied) in the same process that calls pcre_exec(). However, it
+ In most applications, the pattern will have been compiled (and option-
+ ally studied) in the same process that calls pcre_exec(). However, it
is possible to save compiled patterns and study data, and then use them
- later in different processes, possibly even on different hosts. For a
+ later in different processes, possibly even on different hosts. For a
discussion about this, see the pcreprecompile documentation.
Here is an example of a simple call to pcre_exec():
@@ -2963,10 +3070,10 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
Extra data for pcre_exec()
- If the extra argument is not NULL, it must point to a pcre_extra data
- block. The pcre_study() function returns such a block (when it doesn't
- return NULL), but you can also create one for yourself, and pass addi-
- tional information in it. The pcre_extra block contains the following
+ If the extra argument is not NULL, it must point to a pcre_extra data
+ block. The pcre_study() function returns such a block (when it doesn't
+ return NULL), but you can also create one for yourself, and pass addi-
+ tional information in it. The pcre_extra block contains the following
fields (not necessarily in this order):
unsigned long int flags;
@@ -2978,13 +3085,13 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
const unsigned char *tables;
unsigned char **mark;
- In the 16-bit version of this structure, the mark field has type
+ In the 16-bit version of this structure, the mark field has type
"PCRE_UCHAR16 **".
- In the 32-bit version of this structure, the mark field has type
+ In the 32-bit version of this structure, the mark field has type
"PCRE_UCHAR32 **".
- The flags field is used to specify which of the other fields are set.
+ The flags field is used to specify which of the other fields are set.
The flag bits are:
PCRE_EXTRA_CALLOUT_DATA
@@ -2995,39 +3102,48 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_EXTRA_STUDY_DATA
PCRE_EXTRA_TABLES
- Other flag bits should be set to zero. The study_data field and some-
- times the executable_jit field are set in the pcre_extra block that is
- returned by pcre_study(), together with the appropriate flag bits. You
- should not set these yourself, but you may add to the block by setting
+ Other flag bits should be set to zero. The study_data field and some-
+ times the executable_jit field are set in the pcre_extra block that is
+ returned by pcre_study(), together with the appropriate flag bits. You
+ should not set these yourself, but you may add to the block by setting
other fields and their corresponding flag bits.
The match_limit field provides a means of preventing PCRE from using up
- a vast amount of resources when running patterns that are not going to
- match, but which have a very large number of possibilities in their
- search trees. The classic example is a pattern that uses nested unlim-
+ a vast amount of resources when running patterns that are not going to
+ match, but which have a very large number of possibilities in their
+ search trees. The classic example is a pattern that uses nested unlim-
ited repeats.
- Internally, pcre_exec() uses a function called match(), which it calls
- repeatedly (sometimes recursively). The limit set by match_limit is
- imposed on the number of times this function is called during a match,
- which has the effect of limiting the amount of backtracking that can
+ Internally, pcre_exec() uses a function called match(), which it calls
+ repeatedly (sometimes recursively). The limit set by match_limit is
+ imposed on the number of times this function is called during a match,
+ which has the effect of limiting the amount of backtracking that can
take place. For patterns that are not anchored, the count restarts from
zero for each position in the subject string.
When pcre_exec() is called with a pattern that was successfully studied
- with a JIT option, the way that the matching is executed is entirely
+ with a JIT option, the way that the matching is executed is entirely
different. However, there is still the possibility of runaway matching
that goes on for a very long time, and so the match_limit value is also
used in this case (but in a different way) to limit how long the match-
ing can continue.
- The default value for the limit can be set when PCRE is built; the
- default default is 10 million, which handles all but the most extreme
- cases. You can override the default by suppling pcre_exec() with a
- pcre_extra block in which match_limit is set, and
- PCRE_EXTRA_MATCH_LIMIT is set in the flags field. If the limit is
+ The default value for the limit can be set when PCRE is built; the
+ default default is 10 million, which handles all but the most extreme
+ cases. You can override the default by suppling pcre_exec() with a
+ pcre_extra block in which match_limit is set, and
+ PCRE_EXTRA_MATCH_LIMIT is set in the flags field. If the limit is
exceeded, pcre_exec() returns PCRE_ERROR_MATCHLIMIT.
+ A value for the match limit may also be supplied by an item at the
+ start of a pattern of the form
+
+ (*LIMIT_MATCH=d)
+
+ where d is a decimal number. However, such a setting is ignored unless
+ d is less than the limit set by the caller of pcre_exec() or, if no
+ such limit is set, less than the default.
+
The match_limit_recursion field is similar to match_limit, but instead
of limiting the total number of times that match() is called, it limits
the depth of recursion. The recursion depth is a smaller number than
@@ -3047,60 +3163,73 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_EXTRA_MATCH_LIMIT_RECURSION is set in the flags field. If the
limit is exceeded, pcre_exec() returns PCRE_ERROR_RECURSIONLIMIT.
- The callout_data field is used in conjunction with the "callout" fea-
+ A value for the recursion limit may also be supplied by an item at the
+ start of a pattern of the form
+
+ (*LIMIT_RECURSION=d)
+
+ where d is a decimal number. However, such a setting is ignored unless
+ d is less than the limit set by the caller of pcre_exec() or, if no
+ such limit is set, less than the default.
+
+ The callout_data field is used in conjunction with the "callout" fea-
ture, and is described in the pcrecallout documentation.
- The tables field is used to pass a character tables pointer to
- pcre_exec(); this overrides the value that is stored with the compiled
- pattern. A non-NULL value is stored with the compiled pattern only if
- custom tables were supplied to pcre_compile() via its tableptr argu-
- ment. If NULL is passed to pcre_exec() using this mechanism, it forces
- PCRE's internal tables to be used. This facility is helpful when re-
- using patterns that have been saved after compiling with an external
- set of tables, because the external tables might be at a different
- address when pcre_exec() is called. See the pcreprecompile documenta-
- tion for a discussion of saving compiled patterns for later use.
-
- If PCRE_EXTRA_MARK is set in the flags field, the mark field must be
- set to point to a suitable variable. If the pattern contains any back-
- tracking control verbs such as (*MARK:NAME), and the execution ends up
- with a name to pass back, a pointer to the name string (zero termi-
- nated) is placed in the variable pointed to by the mark field. The
- names are within the compiled pattern; if you wish to retain such a
- name you must copy it before freeing the memory of a compiled pattern.
- If there is no name to pass back, the variable pointed to by the mark
- field is set to NULL. For details of the backtracking control verbs,
+ The tables field is provided for use with patterns that have been pre-
+ compiled using custom character tables, saved to disc or elsewhere, and
+ then reloaded, because the tables that were used to compile a pattern
+ are not saved with it. See the pcreprecompile documentation for a dis-
+ cussion of saving compiled patterns for later use. If NULL is passed
+ using this mechanism, it forces PCRE's internal tables to be used.
+
+ Warning: The tables that pcre_exec() uses must be the same as those
+ that were used when the pattern was compiled. If this is not the case,
+ the behaviour of pcre_exec() is undefined. Therefore, when a pattern is
+ compiled and matched in the same process, this field should never be
+ set. In this (the most common) case, the correct table pointer is auto-
+ matically passed with the compiled pattern from pcre_compile() to
+ pcre_exec().
+
+ If PCRE_EXTRA_MARK is set in the flags field, the mark field must be
+ set to point to a suitable variable. If the pattern contains any back-
+ tracking control verbs such as (*MARK:NAME), and the execution ends up
+ with a name to pass back, a pointer to the name string (zero termi-
+ nated) is placed in the variable pointed to by the mark field. The
+ names are within the compiled pattern; if you wish to retain such a
+ name you must copy it before freeing the memory of a compiled pattern.
+ If there is no name to pass back, the variable pointed to by the mark
+ field is set to NULL. For details of the backtracking control verbs,
see the section entitled "Backtracking control" in the pcrepattern doc-
umentation.
Option bits for pcre_exec()
- The unused bits of the options argument for pcre_exec() must be zero.
- The only bits that may be set are PCRE_ANCHORED, PCRE_NEWLINE_xxx,
- PCRE_NOTBOL, PCRE_NOTEOL, PCRE_NOTEMPTY, PCRE_NOTEMPTY_ATSTART,
- PCRE_NO_START_OPTIMIZE, PCRE_NO_UTF8_CHECK, PCRE_PARTIAL_HARD, and
+ The unused bits of the options argument for pcre_exec() must be zero.
+ The only bits that may be set are PCRE_ANCHORED, PCRE_NEWLINE_xxx,
+ PCRE_NOTBOL, PCRE_NOTEOL, PCRE_NOTEMPTY, PCRE_NOTEMPTY_ATSTART,
+ PCRE_NO_START_OPTIMIZE, PCRE_NO_UTF8_CHECK, PCRE_PARTIAL_HARD, and
PCRE_PARTIAL_SOFT.
- If the pattern was successfully studied with one of the just-in-time
+ If the pattern was successfully studied with one of the just-in-time
(JIT) compile options, the only supported options for JIT execution are
- PCRE_NO_UTF8_CHECK, PCRE_NOTBOL, PCRE_NOTEOL, PCRE_NOTEMPTY,
- PCRE_NOTEMPTY_ATSTART, PCRE_PARTIAL_HARD, and PCRE_PARTIAL_SOFT. If an
- unsupported option is used, JIT execution is disabled and the normal
+ PCRE_NO_UTF8_CHECK, PCRE_NOTBOL, PCRE_NOTEOL, PCRE_NOTEMPTY,
+ PCRE_NOTEMPTY_ATSTART, PCRE_PARTIAL_HARD, and PCRE_PARTIAL_SOFT. If an
+ unsupported option is used, JIT execution is disabled and the normal
interpretive code in pcre_exec() is run.
PCRE_ANCHORED
- The PCRE_ANCHORED option limits pcre_exec() to matching at the first
- matching position. If a pattern was compiled with PCRE_ANCHORED, or
- turned out to be anchored by virtue of its contents, it cannot be made
+ The PCRE_ANCHORED option limits pcre_exec() to matching at the first
+ matching position. If a pattern was compiled with PCRE_ANCHORED, or
+ turned out to be anchored by virtue of its contents, it cannot be made
unachored at matching time.
PCRE_BSR_ANYCRLF
PCRE_BSR_UNICODE
These options (which are mutually exclusive) control what the \R escape
- sequence matches. The choice is either to match only CR, LF, or CRLF,
- or to match any Unicode newline sequence. These options override the
+ sequence matches. The choice is either to match only CR, LF, or CRLF,
+ or to match any Unicode newline sequence. These options override the
choice that was made or defaulted when the pattern was compiled.
PCRE_NEWLINE_CR
@@ -3109,109 +3238,110 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_NEWLINE_ANYCRLF
PCRE_NEWLINE_ANY
- These options override the newline definition that was chosen or
- defaulted when the pattern was compiled. For details, see the descrip-
- tion of pcre_compile() above. During matching, the newline choice
- affects the behaviour of the dot, circumflex, and dollar metacharac-
- ters. It may also alter the way the match position is advanced after a
+ These options override the newline definition that was chosen or
+ defaulted when the pattern was compiled. For details, see the descrip-
+ tion of pcre_compile() above. During matching, the newline choice
+ affects the behaviour of the dot, circumflex, and dollar metacharac-
+ ters. It may also alter the way the match position is advanced after a
match failure for an unanchored pattern.
- When PCRE_NEWLINE_CRLF, PCRE_NEWLINE_ANYCRLF, or PCRE_NEWLINE_ANY is
- set, and a match attempt for an unanchored pattern fails when the cur-
- rent position is at a CRLF sequence, and the pattern contains no
- explicit matches for CR or LF characters, the match position is
+ When PCRE_NEWLINE_CRLF, PCRE_NEWLINE_ANYCRLF, or PCRE_NEWLINE_ANY is
+ set, and a match attempt for an unanchored pattern fails when the cur-
+ rent position is at a CRLF sequence, and the pattern contains no
+ explicit matches for CR or LF characters, the match position is
advanced by two characters instead of one, in other words, to after the
CRLF.
The above rule is a compromise that makes the most common cases work as
- expected. For example, if the pattern is .+A (and the PCRE_DOTALL
+ expected. For example, if the pattern is .+A (and the PCRE_DOTALL
option is not set), it does not match the string "\r\nA" because, after
- failing at the start, it skips both the CR and the LF before retrying.
- However, the pattern [\r\n]A does match that string, because it con-
+ failing at the start, it skips both the CR and the LF before retrying.
+ However, the pattern [\r\n]A does match that string, because it con-
tains an explicit CR or LF reference, and so advances only by one char-
acter after the first failure.
An explicit match for CR of LF is either a literal appearance of one of
- those characters, or one of the \r or \n escape sequences. Implicit
- matches such as [^X] do not count, nor does \s (which includes CR and
+ those characters, or one of the \r or \n escape sequences. Implicit
+ matches such as [^X] do not count, nor does \s (which includes CR and
LF in the characters that it matches).
- Notwithstanding the above, anomalous effects may still occur when CRLF
+ Notwithstanding the above, anomalous effects may still occur when CRLF
is a valid newline sequence and explicit \r or \n escapes appear in the
pattern.
PCRE_NOTBOL
This option specifies that first character of the subject string is not
- the beginning of a line, so the circumflex metacharacter should not
- match before it. Setting this without PCRE_MULTILINE (at compile time)
- causes circumflex never to match. This option affects only the behav-
+ the beginning of a line, so the circumflex metacharacter should not
+ match before it. Setting this without PCRE_MULTILINE (at compile time)
+ causes circumflex never to match. This option affects only the behav-
iour of the circumflex metacharacter. It does not affect \A.
PCRE_NOTEOL
This option specifies that the end of the subject string is not the end
- of a line, so the dollar metacharacter should not match it nor (except
- in multiline mode) a newline immediately before it. Setting this with-
+ of a line, so the dollar metacharacter should not match it nor (except
+ in multiline mode) a newline immediately before it. Setting this with-
out PCRE_MULTILINE (at compile time) causes dollar never to match. This
- option affects only the behaviour of the dollar metacharacter. It does
+ option affects only the behaviour of the dollar metacharacter. It does
not affect \Z or \z.
PCRE_NOTEMPTY
An empty string is not considered to be a valid match if this option is
- set. If there are alternatives in the pattern, they are tried. If all
- the alternatives match the empty string, the entire match fails. For
+ set. If there are alternatives in the pattern, they are tried. If all
+ the alternatives match the empty string, the entire match fails. For
example, if the pattern
a?b?
- is applied to a string not beginning with "a" or "b", it matches an
- empty string at the start of the subject. With PCRE_NOTEMPTY set, this
+ is applied to a string not beginning with "a" or "b", it matches an
+ empty string at the start of the subject. With PCRE_NOTEMPTY set, this
match is not valid, so PCRE searches further into the string for occur-
rences of "a" or "b".
PCRE_NOTEMPTY_ATSTART
- This is like PCRE_NOTEMPTY, except that an empty string match that is
- not at the start of the subject is permitted. If the pattern is
+ This is like PCRE_NOTEMPTY, except that an empty string match that is
+ not at the start of the subject is permitted. If the pattern is
anchored, such a match can occur only if the pattern contains \K.
- Perl has no direct equivalent of PCRE_NOTEMPTY or
- PCRE_NOTEMPTY_ATSTART, but it does make a special case of a pattern
- match of the empty string within its split() function, and when using
- the /g modifier. It is possible to emulate Perl's behaviour after
+ Perl has no direct equivalent of PCRE_NOTEMPTY or
+ PCRE_NOTEMPTY_ATSTART, but it does make a special case of a pattern
+ match of the empty string within its split() function, and when using
+ the /g modifier. It is possible to emulate Perl's behaviour after
matching a null string by first trying the match again at the same off-
- set with PCRE_NOTEMPTY_ATSTART and PCRE_ANCHORED, and then if that
+ set with PCRE_NOTEMPTY_ATSTART and PCRE_ANCHORED, and then if that
fails, by advancing the starting offset (see below) and trying an ordi-
- nary match again. There is some code that demonstrates how to do this
- in the pcredemo sample program. In the most general case, you have to
- check to see if the newline convention recognizes CRLF as a newline,
- and if so, and the current character is CR followed by LF, advance the
+ nary match again. There is some code that demonstrates how to do this
+ in the pcredemo sample program. In the most general case, you have to
+ check to see if the newline convention recognizes CRLF as a newline,
+ and if so, and the current character is CR followed by LF, advance the
starting offset by two characters instead of one.
PCRE_NO_START_OPTIMIZE
- There are a number of optimizations that pcre_exec() uses at the start
- of a match, in order to speed up the process. For example, if it is
+ There are a number of optimizations that pcre_exec() uses at the start
+ of a match, in order to speed up the process. For example, if it is
known that an unanchored match must start with a specific character, it
- searches the subject for that character, and fails immediately if it
- cannot find it, without actually running the main matching function.
+ searches the subject for that character, and fails immediately if it
+ cannot find it, without actually running the main matching function.
This means that a special item such as (*COMMIT) at the start of a pat-
- tern is not considered until after a suitable starting point for the
- match has been found. When callouts or (*MARK) items are in use, these
- "start-up" optimizations can cause them to be skipped if the pattern is
- never actually used. The start-up optimizations are in effect a pre-
- scan of the subject that takes place before the pattern is run.
-
- The PCRE_NO_START_OPTIMIZE option disables the start-up optimizations,
- possibly causing performance to suffer, but ensuring that in cases
- where the result is "no match", the callouts do occur, and that items
+ tern is not considered until after a suitable starting point for the
+ match has been found. Also, when callouts or (*MARK) items are in use,
+ these "start-up" optimizations can cause them to be skipped if the pat-
+ tern is never actually used. The start-up optimizations are in effect a
+ pre-scan of the subject that takes place before the pattern is run.
+
+ The PCRE_NO_START_OPTIMIZE option disables the start-up optimizations,
+ possibly causing performance to suffer, but ensuring that in cases
+ where the result is "no match", the callouts do occur, and that items
such as (*COMMIT) and (*MARK) are considered at every possible starting
- position in the subject string. If PCRE_NO_START_OPTIMIZE is set at
- compile time, it cannot be unset at matching time. The use of
- PCRE_NO_START_OPTIMIZE disables JIT execution; when it is set, matching
- is always done using interpretively.
+ position in the subject string. If PCRE_NO_START_OPTIMIZE is set at
+ compile time, it cannot be unset at matching time. The use of
+ PCRE_NO_START_OPTIMIZE at matching time (that is, passing it to
+ pcre_exec()) disables JIT execution; in this situation, matching is
+ always done using interpretively.
Setting PCRE_NO_START_OPTIMIZE can change the outcome of a matching
operation. Consider the pattern
@@ -3267,7 +3397,7 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
points to the start of a character (or the end of the subject). When
PCRE_NO_UTF8_CHECK is set, the effect of passing an invalid string as a
subject or an invalid value of startoffset is undefined. Your program
- may crash.
+ may crash or loop.
PCRE_PARTIAL_HARD
PCRE_PARTIAL_SOFT
@@ -3297,149 +3427,156 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
The string to be matched by pcre_exec()
The subject string is passed to pcre_exec() as a pointer in subject, a
- length in bytes in length, and a starting byte offset in startoffset.
- If this is negative or greater than the length of the subject,
+ length in length, and a starting offset in startoffset. The units for
+ length and startoffset are bytes for the 8-bit library, 16-bit data
+ items for the 16-bit library, and 32-bit data items for the 32-bit
+ library.
+
+ If startoffset is negative or greater than the length of the subject,
pcre_exec() returns PCRE_ERROR_BADOFFSET. When the starting offset is
zero, the search for a match starts at the beginning of the subject,
- and this is by far the most common case. In UTF-8 mode, the byte offset
- must point to the start of a UTF-8 character (or the end of the sub-
- ject). Unlike the pattern string, the subject may contain binary zero
- bytes.
-
- A non-zero starting offset is useful when searching for another match
- in the same subject by calling pcre_exec() again after a previous suc-
- cess. Setting startoffset differs from just passing over a shortened
- string and setting PCRE_NOTBOL in the case of a pattern that begins
+ and this is by far the most common case. In UTF-8 or UTF-16 mode, the
+ offset must point to the start of a character, or the end of the sub-
+ ject (in UTF-32 mode, one data unit equals one character, so all off-
+ sets are valid). Unlike the pattern string, the subject may contain
+ binary zeroes.
+
+ A non-zero starting offset is useful when searching for another match
+ in the same subject by calling pcre_exec() again after a previous suc-
+ cess. Setting startoffset differs from just passing over a shortened
+ string and setting PCRE_NOTBOL in the case of a pattern that begins
with any kind of lookbehind. For example, consider the pattern
\Biss\B
- which finds occurrences of "iss" in the middle of words. (\B matches
- only if the current position in the subject is not a word boundary.)
- When applied to the string "Mississipi" the first call to pcre_exec()
- finds the first occurrence. If pcre_exec() is called again with just
- the remainder of the subject, namely "issipi", it does not match,
+ which finds occurrences of "iss" in the middle of words. (\B matches
+ only if the current position in the subject is not a word boundary.)
+ When applied to the string "Mississipi" the first call to pcre_exec()
+ finds the first occurrence. If pcre_exec() is called again with just
+ the remainder of the subject, namely "issipi", it does not match,
because \B is always false at the start of the subject, which is deemed
- to be a word boundary. However, if pcre_exec() is passed the entire
+ to be a word boundary. However, if pcre_exec() is passed the entire
string again, but with startoffset set to 4, it finds the second occur-
- rence of "iss" because it is able to look behind the starting point to
+ rence of "iss" because it is able to look behind the starting point to
discover that it is preceded by a letter.
- Finding all the matches in a subject is tricky when the pattern can
+ Finding all the matches in a subject is tricky when the pattern can
match an empty string. It is possible to emulate Perl's /g behaviour by
- first trying the match again at the same offset, with the
- PCRE_NOTEMPTY_ATSTART and PCRE_ANCHORED options, and then if that
- fails, advancing the starting offset and trying an ordinary match
+ first trying the match again at the same offset, with the
+ PCRE_NOTEMPTY_ATSTART and PCRE_ANCHORED options, and then if that
+ fails, advancing the starting offset and trying an ordinary match
again. There is some code that demonstrates how to do this in the pcre-
demo sample program. In the most general case, you have to check to see
- if the newline convention recognizes CRLF as a newline, and if so, and
+ if the newline convention recognizes CRLF as a newline, and if so, and
the current character is CR followed by LF, advance the starting offset
by two characters instead of one.
- If a non-zero starting offset is passed when the pattern is anchored,
+ If a non-zero starting offset is passed when the pattern is anchored,
one attempt to match at the given offset is made. This can only succeed
- if the pattern does not require the match to be at the start of the
+ if the pattern does not require the match to be at the start of the
subject.
How pcre_exec() returns captured substrings
- In general, a pattern matches a certain portion of the subject, and in
- addition, further substrings from the subject may be picked out by
- parts of the pattern. Following the usage in Jeffrey Friedl's book,
- this is called "capturing" in what follows, and the phrase "capturing
- subpattern" is used for a fragment of a pattern that picks out a sub-
- string. PCRE supports several other kinds of parenthesized subpattern
+ In general, a pattern matches a certain portion of the subject, and in
+ addition, further substrings from the subject may be picked out by
+ parts of the pattern. Following the usage in Jeffrey Friedl's book,
+ this is called "capturing" in what follows, and the phrase "capturing
+ subpattern" is used for a fragment of a pattern that picks out a sub-
+ string. PCRE supports several other kinds of parenthesized subpattern
that do not cause substrings to be captured.
Captured substrings are returned to the caller via a vector of integers
- whose address is passed in ovector. The number of elements in the vec-
- tor is passed in ovecsize, which must be a non-negative number. Note:
+ whose address is passed in ovector. The number of elements in the vec-
+ tor is passed in ovecsize, which must be a non-negative number. Note:
this argument is NOT the size of ovector in bytes.
- The first two-thirds of the vector is used to pass back captured sub-
- strings, each substring using a pair of integers. The remaining third
- of the vector is used as workspace by pcre_exec() while matching cap-
- turing subpatterns, and is not available for passing back information.
- The number passed in ovecsize should always be a multiple of three. If
+ The first two-thirds of the vector is used to pass back captured sub-
+ strings, each substring using a pair of integers. The remaining third
+ of the vector is used as workspace by pcre_exec() while matching cap-
+ turing subpatterns, and is not available for passing back information.
+ The number passed in ovecsize should always be a multiple of three. If
it is not, it is rounded down.
- When a match is successful, information about captured substrings is
- returned in pairs of integers, starting at the beginning of ovector,
- and continuing up to two-thirds of its length at the most. The first
- element of each pair is set to the byte offset of the first character
- in a substring, and the second is set to the byte offset of the first
- character after the end of a substring. Note: these values are always
- byte offsets, even in UTF-8 mode. They are not character counts.
-
- The first pair of integers, ovector[0] and ovector[1], identify the
- portion of the subject string matched by the entire pattern. The next
- pair is used for the first capturing subpattern, and so on. The value
+ When a match is successful, information about captured substrings is
+ returned in pairs of integers, starting at the beginning of ovector,
+ and continuing up to two-thirds of its length at the most. The first
+ element of each pair is set to the offset of the first character in a
+ substring, and the second is set to the offset of the first character
+ after the end of a substring. These values are always data unit off-
+ sets, even in UTF mode. They are byte offsets in the 8-bit library,
+ 16-bit data item offsets in the 16-bit library, and 32-bit data item
+ offsets in the 32-bit library. Note: they are not character counts.
+
+ The first pair of integers, ovector[0] and ovector[1], identify the
+ portion of the subject string matched by the entire pattern. The next
+ pair is used for the first capturing subpattern, and so on. The value
returned by pcre_exec() is one more than the highest numbered pair that
- has been set. For example, if two substrings have been captured, the
- returned value is 3. If there are no capturing subpatterns, the return
+ has been set. For example, if two substrings have been captured, the
+ returned value is 3. If there are no capturing subpatterns, the return
value from a successful match is 1, indicating that just the first pair
of offsets has been set.
If a capturing subpattern is matched repeatedly, it is the last portion
of the string that it matched that is returned.
- If the vector is too small to hold all the captured substring offsets,
+ If the vector is too small to hold all the captured substring offsets,
it is used as far as possible (up to two-thirds of its length), and the
- function returns a value of zero. If neither the actual string matched
- nor any captured substrings are of interest, pcre_exec() may be called
- with ovector passed as NULL and ovecsize as zero. However, if the pat-
- tern contains back references and the ovector is not big enough to
- remember the related substrings, PCRE has to get additional memory for
- use during matching. Thus it is usually advisable to supply an ovector
+ function returns a value of zero. If neither the actual string matched
+ nor any captured substrings are of interest, pcre_exec() may be called
+ with ovector passed as NULL and ovecsize as zero. However, if the pat-
+ tern contains back references and the ovector is not big enough to
+ remember the related substrings, PCRE has to get additional memory for
+ use during matching. Thus it is usually advisable to supply an ovector
of reasonable size.
- There are some cases where zero is returned (indicating vector over-
- flow) when in fact the vector is exactly the right size for the final
+ There are some cases where zero is returned (indicating vector over-
+ flow) when in fact the vector is exactly the right size for the final
match. For example, consider the pattern
(a)(?:(b)c|bd)
- If a vector of 6 elements (allowing for only 1 captured substring) is
+ If a vector of 6 elements (allowing for only 1 captured substring) is
given with subject string "abd", pcre_exec() will try to set the second
captured string, thereby recording a vector overflow, before failing to
- match "c" and backing up to try the second alternative. The zero
- return, however, does correctly indicate that the maximum number of
+ match "c" and backing up to try the second alternative. The zero
+ return, however, does correctly indicate that the maximum number of
slots (namely 2) have been filled. In similar cases where there is tem-
- porary overflow, but the final number of used slots is actually less
+ porary overflow, but the final number of used slots is actually less
than the maximum, a non-zero value is returned.
The pcre_fullinfo() function can be used to find out how many capturing
- subpatterns there are in a compiled pattern. The smallest size for
- ovector that will allow for n captured substrings, in addition to the
+ subpatterns there are in a compiled pattern. The smallest size for
+ ovector that will allow for n captured substrings, in addition to the
offsets of the substring matched by the whole pattern, is (n+1)*3.
- It is possible for capturing subpattern number n+1 to match some part
+ It is possible for capturing subpattern number n+1 to match some part
of the subject when subpattern n has not been used at all. For example,
- if the string "abc" is matched against the pattern (a|(z))(bc) the
+ if the string "abc" is matched against the pattern (a|(z))(bc) the
return from the function is 4, and subpatterns 1 and 3 are matched, but
- 2 is not. When this happens, both values in the offset pairs corre-
+ 2 is not. When this happens, both values in the offset pairs corre-
sponding to unused subpatterns are set to -1.
- Offset values that correspond to unused subpatterns at the end of the
- expression are also set to -1. For example, if the string "abc" is
- matched against the pattern (abc)(x(yz)?)? subpatterns 2 and 3 are not
- matched. The return from the function is 2, because the highest used
- capturing subpattern number is 1, and the offsets for for the second
- and third capturing subpatterns (assuming the vector is large enough,
+ Offset values that correspond to unused subpatterns at the end of the
+ expression are also set to -1. For example, if the string "abc" is
+ matched against the pattern (abc)(x(yz)?)? subpatterns 2 and 3 are not
+ matched. The return from the function is 2, because the highest used
+ capturing subpattern number is 1, and the offsets for for the second
+ and third capturing subpatterns (assuming the vector is large enough,
of course) are set to -1.
- Note: Elements in the first two-thirds of ovector that do not corre-
- spond to capturing parentheses in the pattern are never changed. That
- is, if a pattern contains n capturing parentheses, no more than ovec-
- tor[0] to ovector[2n+1] are set by pcre_exec(). The other elements (in
+ Note: Elements in the first two-thirds of ovector that do not corre-
+ spond to capturing parentheses in the pattern are never changed. That
+ is, if a pattern contains n capturing parentheses, no more than ovec-
+ tor[0] to ovector[2n+1] are set by pcre_exec(). The other elements (in
the first two-thirds) retain whatever values they previously had.
- Some convenience functions are provided for extracting the captured
+ Some convenience functions are provided for extracting the captured
substrings as separate strings. These are described below.
Error return values from pcre_exec()
- If pcre_exec() fails, it returns a negative number. The following are
+ If pcre_exec() fails, it returns a negative number. The following are
defined in the header file:
PCRE_ERROR_NOMATCH (-1)
@@ -3448,7 +3585,7 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_ERROR_NULL (-2)
- Either code or subject was passed as NULL, or ovector was NULL and
+ Either code or subject was passed as NULL, or ovector was NULL and
ovecsize was not zero.
PCRE_ERROR_BADOPTION (-3)
@@ -3457,82 +3594,82 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_ERROR_BADMAGIC (-4)
- PCRE stores a 4-byte "magic number" at the start of the compiled code,
+ PCRE stores a 4-byte "magic number" at the start of the compiled code,
to catch the case when it is passed a junk pointer and to detect when a
pattern that was compiled in an environment of one endianness is run in
- an environment with the other endianness. This is the error that PCRE
+ an environment with the other endianness. This is the error that PCRE
gives when the magic number is not present.
PCRE_ERROR_UNKNOWN_OPCODE (-5)
While running the pattern match, an unknown item was encountered in the
- compiled pattern. This error could be caused by a bug in PCRE or by
+ compiled pattern. This error could be caused by a bug in PCRE or by
overwriting of the compiled pattern.
PCRE_ERROR_NOMEMORY (-6)
- If a pattern contains back references, but the ovector that is passed
+ If a pattern contains back references, but the ovector that is passed
to pcre_exec() is not big enough to remember the referenced substrings,
- PCRE gets a block of memory at the start of matching to use for this
- purpose. If the call via pcre_malloc() fails, this error is given. The
+ PCRE gets a block of memory at the start of matching to use for this
+ purpose. If the call via pcre_malloc() fails, this error is given. The
memory is automatically freed at the end of matching.
- This error is also given if pcre_stack_malloc() fails in pcre_exec().
- This can happen only when PCRE has been compiled with --disable-stack-
+ This error is also given if pcre_stack_malloc() fails in pcre_exec().
+ This can happen only when PCRE has been compiled with --disable-stack-
for-recursion.
PCRE_ERROR_NOSUBSTRING (-7)
- This error is used by the pcre_copy_substring(), pcre_get_substring(),
+ This error is used by the pcre_copy_substring(), pcre_get_substring(),
and pcre_get_substring_list() functions (see below). It is never
returned by pcre_exec().
PCRE_ERROR_MATCHLIMIT (-8)
- The backtracking limit, as specified by the match_limit field in a
- pcre_extra structure (or defaulted) was reached. See the description
+ The backtracking limit, as specified by the match_limit field in a
+ pcre_extra structure (or defaulted) was reached. See the description
above.
PCRE_ERROR_CALLOUT (-9)
This error is never generated by pcre_exec() itself. It is provided for
- use by callout functions that want to yield a distinctive error code.
+ use by callout functions that want to yield a distinctive error code.
See the pcrecallout documentation for details.
PCRE_ERROR_BADUTF8 (-10)
- A string that contains an invalid UTF-8 byte sequence was passed as a
- subject, and the PCRE_NO_UTF8_CHECK option was not set. If the size of
- the output vector (ovecsize) is at least 2, the byte offset to the
- start of the the invalid UTF-8 character is placed in the first ele-
- ment, and a reason code is placed in the second element. The reason
+ A string that contains an invalid UTF-8 byte sequence was passed as a
+ subject, and the PCRE_NO_UTF8_CHECK option was not set. If the size of
+ the output vector (ovecsize) is at least 2, the byte offset to the
+ start of the the invalid UTF-8 character is placed in the first ele-
+ ment, and a reason code is placed in the second element. The reason
codes are listed in the following section. For backward compatibility,
- if PCRE_PARTIAL_HARD is set and the problem is a truncated UTF-8 char-
- acter at the end of the subject (reason codes 1 to 5),
+ if PCRE_PARTIAL_HARD is set and the problem is a truncated UTF-8 char-
+ acter at the end of the subject (reason codes 1 to 5),
PCRE_ERROR_SHORTUTF8 is returned instead of PCRE_ERROR_BADUTF8.
PCRE_ERROR_BADUTF8_OFFSET (-11)
- The UTF-8 byte sequence that was passed as a subject was checked and
- found to be valid (the PCRE_NO_UTF8_CHECK option was not set), but the
- value of startoffset did not point to the beginning of a UTF-8 charac-
+ The UTF-8 byte sequence that was passed as a subject was checked and
+ found to be valid (the PCRE_NO_UTF8_CHECK option was not set), but the
+ value of startoffset did not point to the beginning of a UTF-8 charac-
ter or the end of the subject.
PCRE_ERROR_PARTIAL (-12)
- The subject string did not match, but it did match partially. See the
+ The subject string did not match, but it did match partially. See the
pcrepartial documentation for details of partial matching.
PCRE_ERROR_BADPARTIAL (-13)
- This code is no longer in use. It was formerly returned when the
- PCRE_PARTIAL option was used with a compiled pattern containing items
- that were not supported for partial matching. From release 8.00
+ This code is no longer in use. It was formerly returned when the
+ PCRE_PARTIAL option was used with a compiled pattern containing items
+ that were not supported for partial matching. From release 8.00
onwards, there are no restrictions on partial matching.
PCRE_ERROR_INTERNAL (-14)
- An unexpected internal error has occurred. This error could be caused
+ An unexpected internal error has occurred. This error could be caused
by a bug in PCRE or by overwriting of the compiled pattern.
PCRE_ERROR_BADCOUNT (-15)
@@ -3542,7 +3679,7 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_ERROR_RECURSIONLIMIT (-21)
The internal recursion limit, as specified by the match_limit_recursion
- field in a pcre_extra structure (or defaulted) was reached. See the
+ field in a pcre_extra structure (or defaulted) was reached. See the
description above.
PCRE_ERROR_BADNEWLINE (-23)
@@ -3556,29 +3693,29 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_ERROR_SHORTUTF8 (-25)
- This error is returned instead of PCRE_ERROR_BADUTF8 when the subject
- string ends with a truncated UTF-8 character and the PCRE_PARTIAL_HARD
- option is set. Information about the failure is returned as for
- PCRE_ERROR_BADUTF8. It is in fact sufficient to detect this case, but
- this special error code for PCRE_PARTIAL_HARD precedes the implementa-
- tion of returned information; it is retained for backwards compatibil-
+ This error is returned instead of PCRE_ERROR_BADUTF8 when the subject
+ string ends with a truncated UTF-8 character and the PCRE_PARTIAL_HARD
+ option is set. Information about the failure is returned as for
+ PCRE_ERROR_BADUTF8. It is in fact sufficient to detect this case, but
+ this special error code for PCRE_PARTIAL_HARD precedes the implementa-
+ tion of returned information; it is retained for backwards compatibil-
ity.
PCRE_ERROR_RECURSELOOP (-26)
This error is returned when pcre_exec() detects a recursion loop within
- the pattern. Specifically, it means that either the whole pattern or a
- subpattern has been called recursively for the second time at the same
+ the pattern. Specifically, it means that either the whole pattern or a
+ subpattern has been called recursively for the second time at the same
position in the subject string. Some simple patterns that might do this
- are detected and faulted at compile time, but more complicated cases,
+ are detected and faulted at compile time, but more complicated cases,
in particular mutual recursions between two different subpatterns, can-
not be detected until run time.
PCRE_ERROR_JIT_STACKLIMIT (-27)
- This error is returned when a pattern that was successfully studied
- using a JIT compile option is being matched, but the memory available
- for the just-in-time processing stack is not large enough. See the
+ This error is returned when a pattern that was successfully studied
+ using a JIT compile option is being matched, but the memory available
+ for the just-in-time processing stack is not large enough. See the
pcrejit documentation for more details.
PCRE_ERROR_BADMODE (-28)
@@ -3588,38 +3725,38 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_ERROR_BADENDIANNESS (-29)
- This error is given if a pattern that was compiled and saved is
- reloaded on a host with different endianness. The utility function
+ This error is given if a pattern that was compiled and saved is
+ reloaded on a host with different endianness. The utility function
pcre_pattern_to_host_byte_order() can be used to convert such a pattern
so that it runs on the new host.
PCRE_ERROR_JIT_BADOPTION
- This error is returned when a pattern that was successfully studied
- using a JIT compile option is being matched, but the matching mode
- (partial or complete match) does not correspond to any JIT compilation
- mode. When the JIT fast path function is used, this error may be also
- given for invalid options. See the pcrejit documentation for more
+ This error is returned when a pattern that was successfully studied
+ using a JIT compile option is being matched, but the matching mode
+ (partial or complete match) does not correspond to any JIT compilation
+ mode. When the JIT fast path function is used, this error may be also
+ given for invalid options. See the pcrejit documentation for more
details.
PCRE_ERROR_BADLENGTH (-32)
- This error is given if pcre_exec() is called with a negative value for
+ This error is given if pcre_exec() is called with a negative value for
the length argument.
Error numbers -16 to -20, -22, and 30 are not used by pcre_exec().
Reason codes for invalid UTF-8 strings
- This section applies only to the 8-bit library. The corresponding
- information for the 16-bit and 32-bit libraries is given in the pcre16
+ This section applies only to the 8-bit library. The corresponding
+ information for the 16-bit and 32-bit libraries is given in the pcre16
and pcre32 pages.
When pcre_exec() returns either PCRE_ERROR_BADUTF8 or PCRE_ERROR_SHORT-
- UTF8, and the size of the output vector (ovecsize) is at least 2, the
- offset of the start of the invalid UTF-8 character is placed in the
+ UTF8, and the size of the output vector (ovecsize) is at least 2, the
+ offset of the start of the invalid UTF-8 character is placed in the
first output vector element (ovector[0]) and a reason code is placed in
- the second element (ovector[1]). The reason codes are given names in
+ the second element (ovector[1]). The reason codes are given names in
the pcre.h header file:
PCRE_UTF8_ERR1
@@ -3628,10 +3765,10 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_UTF8_ERR4
PCRE_UTF8_ERR5
- The string ends with a truncated UTF-8 character; the code specifies
- how many bytes are missing (1 to 5). Although RFC 3629 restricts UTF-8
- characters to be no longer than 4 bytes, the encoding scheme (origi-
- nally defined by RFC 2279) allows for up to 6 bytes, and this is
+ The string ends with a truncated UTF-8 character; the code specifies
+ how many bytes are missing (1 to 5). Although RFC 3629 restricts UTF-8
+ characters to be no longer than 4 bytes, the encoding scheme (origi-
+ nally defined by RFC 2279) allows for up to 6 bytes, and this is
checked first; hence the possibility of 4 or 5 missing bytes.
PCRE_UTF8_ERR6
@@ -3641,24 +3778,24 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_UTF8_ERR10
The two most significant bits of the 2nd, 3rd, 4th, 5th, or 6th byte of
- the character do not have the binary value 0b10 (that is, either the
+ the character do not have the binary value 0b10 (that is, either the
most significant bit is 0, or the next bit is 1).
PCRE_UTF8_ERR11
PCRE_UTF8_ERR12
- A character that is valid by the RFC 2279 rules is either 5 or 6 bytes
+ A character that is valid by the RFC 2279 rules is either 5 or 6 bytes
long; these code points are excluded by RFC 3629.
PCRE_UTF8_ERR13
- A 4-byte character has a value greater than 0x10fff; these code points
+ A 4-byte character has a value greater than 0x10fff; these code points
are excluded by RFC 3629.
PCRE_UTF8_ERR14
- A 3-byte character has a value in the range 0xd800 to 0xdfff; this
- range of code points are reserved by RFC 3629 for use with UTF-16, and
+ A 3-byte character has a value in the range 0xd800 to 0xdfff; this
+ range of code points are reserved by RFC 3629 for use with UTF-16, and
so are excluded from UTF-8.
PCRE_UTF8_ERR15
@@ -3667,28 +3804,29 @@ MATCHING A PATTERN: THE TRADITIONAL FUNCTION
PCRE_UTF8_ERR18
PCRE_UTF8_ERR19
- A 2-, 3-, 4-, 5-, or 6-byte character is "overlong", that is, it codes
- for a value that can be represented by fewer bytes, which is invalid.
- For example, the two bytes 0xc0, 0xae give the value 0x2e, whose cor-
+ A 2-, 3-, 4-, 5-, or 6-byte character is "overlong", that is, it codes
+ for a value that can be represented by fewer bytes, which is invalid.
+ For example, the two bytes 0xc0, 0xae give the value 0x2e, whose cor-
rect coding uses just one byte.
PCRE_UTF8_ERR20
The two most significant bits of the first byte of a character have the
- binary value 0b10 (that is, the most significant bit is 1 and the sec-
- ond is 0). Such a byte can only validly occur as the second or subse-
+ binary value 0b10 (that is, the most significant bit is 1 and the sec-
+ ond is 0). Such a byte can only validly occur as the second or subse-
quent byte of a multi-byte character.
PCRE_UTF8_ERR21
- The first byte of a character has the value 0xfe or 0xff. These values
+ The first byte of a character has the value 0xfe or 0xff. These values
can never occur in a valid UTF-8 string.
- PCRE_UTF8_ERR2
+ PCRE_UTF8_ERR22
- Non-character. These are the last two characters in each plane (0xfffe,
- 0xffff, 0x1fffe, 0x1ffff .. 0x10fffe, 0x10ffff), and the characters
- 0xfdd0..0xfdef.
+ This error code was formerly used when the presence of a so-called
+ "non-character" caused an error. Unicode corrigendum #9 makes it clear
+ that such characters should not cause a string to be rejected, and so
+ this code is no longer in use and is never returned.
EXTRACTING CAPTURED SUBSTRINGS BY NUMBER
@@ -4039,55 +4177,64 @@ MATCHING A PATTERN: THE ALTERNATIVE FUNCTION
filled with the longest matches. Unlike pcre_exec(), pcre_dfa_exec()
can use the entire ovector for returning matched strings.
+ NOTE: PCRE's "auto-possessification" optimization usually applies to
+ character repeats at the end of a pattern (as well as internally). For
+ example, the pattern "a\d+" is compiled as if it were "a\d++" because
+ there is no point even considering the possibility of backtracking into
+ the repeated digits. For DFA matching, this means that only one possi-
+ ble match is found. If you really do want multiple matches in such
+ cases, either use an ungreedy repeat ("a\d+?") or set the
+ PCRE_NO_AUTO_POSSESS option when compiling.
+
Error returns from pcre_dfa_exec()
- The pcre_dfa_exec() function returns a negative number when it fails.
- Many of the errors are the same as for pcre_exec(), and these are
- described above. There are in addition the following errors that are
+ The pcre_dfa_exec() function returns a negative number when it fails.
+ Many of the errors are the same as for pcre_exec(), and these are
+ described above. There are in addition the following errors that are
specific to pcre_dfa_exec():
PCRE_ERROR_DFA_UITEM (-16)
- This return is given if pcre_dfa_exec() encounters an item in the pat-
- tern that it does not support, for instance, the use of \C or a back
+ This return is given if pcre_dfa_exec() encounters an item in the pat-
+ tern that it does not support, for instance, the use of \C or a back
reference.
PCRE_ERROR_DFA_UCOND (-17)
- This return is given if pcre_dfa_exec() encounters a condition item
- that uses a back reference for the condition, or a test for recursion
+ This return is given if pcre_dfa_exec() encounters a condition item
+ that uses a back reference for the condition, or a test for recursion
in a specific group. These are not supported.
PCRE_ERROR_DFA_UMLIMIT (-18)
- This return is given if pcre_dfa_exec() is called with an extra block
- that contains a setting of the match_limit or match_limit_recursion
- fields. This is not supported (these fields are meaningless for DFA
+ This return is given if pcre_dfa_exec() is called with an extra block
+ that contains a setting of the match_limit or match_limit_recursion
+ fields. This is not supported (these fields are meaningless for DFA
matching).
PCRE_ERROR_DFA_WSSIZE (-19)
- This return is given if pcre_dfa_exec() runs out of space in the
+ This return is given if pcre_dfa_exec() runs out of space in the
workspace vector.
PCRE_ERROR_DFA_RECURSE (-20)
- When a recursive subpattern is processed, the matching function calls
- itself recursively, using private vectors for ovector and workspace.
- This error is given if the output vector is not large enough. This
+ When a recursive subpattern is processed, the matching function calls
+ itself recursively, using private vectors for ovector and workspace.
+ This error is given if the output vector is not large enough. This
should be extremely rare, as a vector of size 1000 is used.
PCRE_ERROR_DFA_BADRESTART (-30)
- When pcre_dfa_exec() is called with the PCRE_DFA_RESTART option, some
- plausibility checks are made on the contents of the workspace, which
- should contain data about the previous partial match. If any of these
+ When pcre_dfa_exec() is called with the PCRE_DFA_RESTART option, some
+ plausibility checks are made on the contents of the workspace, which
+ should contain data about the previous partial match. If any of these
checks fail, this error is given.
SEE ALSO
- pcre16(3), pcre32(3), pcrebuild(3), pcrecallout(3), pcrecpp(3)(3),
+ pcre16(3), pcre32(3), pcrebuild(3), pcrecallout(3), pcrecpp(3)(3),
pcrematching(3), pcrepartial(3), pcreposix(3), pcreprecompile(3), pcre-
sample(3), pcrestack(3).
@@ -4101,18 +4248,18 @@ AUTHOR
REVISION
- Last updated: 08 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRECALLOUT(3) PCRECALLOUT(3)
+PCRECALLOUT(3) Library Functions Manual PCRECALLOUT(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
SYNOPSIS
#include <pcre.h>
@@ -4153,48 +4300,88 @@ DESCRIPTION
(?C255)A(?C255)((?C255)\d{2}(?C255)|(?C255)-(?C255)-(?C255))(?C255)
Notice that there is a callout before and after each parenthesis and
- alternation bar. Automatic callouts can be used for tracking the
- progress of pattern matching. The pcretest command has an option that
- sets automatic callouts; when it is used, the output indicates how the
- pattern is matched. This is useful information when you are trying to
- optimize the performance of a particular pattern.
+ alternation bar. If the pattern contains a conditional group whose con-
+ dition is an assertion, an automatic callout is inserted immediately
+ before the condition. Such a callout may also be inserted explicitly,
+ for example:
+
+ (?(?C9)(?=a)ab|de)
+
+ This applies only to assertion conditions (because they are themselves
+ independent groups).
- The use of callouts in a pattern makes it ineligible for optimization
- by the just-in-time compiler. Studying such a pattern with the
- PCRE_STUDY_JIT_COMPILE option always fails.
+ Automatic callouts can be used for tracking the progress of pattern
+ matching. The pcretest program has a pattern qualifier (/C) that sets
+ automatic callouts; when it is used, the output indicates how the pat-
+ tern is being matched. This is useful information when you are trying
+ to optimize the performance of a particular pattern.
MISSING CALLOUTS
- You should be aware that, because of optimizations in the way PCRE
- matches patterns by default, callouts sometimes do not happen. For
- example, if the pattern is
+ You should be aware that, because of optimizations in the way PCRE com-
+ piles and matches patterns, callouts sometimes do not happen exactly as
+ you might expect.
+
+ At compile time, PCRE "auto-possessifies" repeated items when it knows
+ that what follows cannot be part of the repeat. For example, a+[bc] is
+ compiled as if it were a++[bc]. The pcretest output when this pattern
+ is anchored and then applied with automatic callouts to the string
+ "aaaa" is:
+
+ --->aaaa
+ +0 ^ ^
+ +1 ^ a+
+ +3 ^ ^ [bc]
+ No match
+
+ This indicates that when matching [bc] fails, there is no backtracking
+ into a+ and therefore the callouts that would be taken for the back-
+ tracks do not occur. You can disable the auto-possessify feature by
+ passing PCRE_NO_AUTO_POSSESS to pcre_compile(), or starting the pattern
+ with (*NO_AUTO_POSSESS). If this is done in pcretest (using the /O
+ qualifier), the output changes to this:
+
+ --->aaaa
+ +0 ^ ^
+ +1 ^ a+
+ +3 ^ ^ [bc]
+ +3 ^ ^ [bc]
+ +3 ^ ^ [bc]
+ +3 ^^ [bc]
+ No match
+
+ This time, when matching [bc] fails, the matcher backtracks into a+ and
+ tries again, repeatedly, until a+ itself fails.
+
+ Other optimizations that provide fast "no match" results also affect
+ callouts. For example, if the pattern is
ab(?C4)cd
PCRE knows that any matching string must contain the letter "d". If the
- subject string is "abyz", the lack of "d" means that matching doesn't
- ever start, and the callout is never reached. However, with "abyd",
+ subject string is "abyz", the lack of "d" means that matching doesn't
+ ever start, and the callout is never reached. However, with "abyd",
though the result is still no match, the callout is obeyed.
- If the pattern is studied, PCRE knows the minimum length of a matching
- string, and will immediately give a "no match" return without actually
- running a match if the subject is not long enough, or, for unanchored
+ If the pattern is studied, PCRE knows the minimum length of a matching
+ string, and will immediately give a "no match" return without actually
+ running a match if the subject is not long enough, or, for unanchored
patterns, if it has been scanned far enough.
- You can disable these optimizations by passing the PCRE_NO_START_OPTI-
- MIZE option to the matching function, or by starting the pattern with
- (*NO_START_OPT). This slows down the matching process, but does ensure
+ You can disable these optimizations by passing the PCRE_NO_START_OPTI-
+ MIZE option to the matching function, or by starting the pattern with
+ (*NO_START_OPT). This slows down the matching process, but does ensure
that callouts such as the example above are obeyed.
THE CALLOUT INTERFACE
- During matching, when PCRE reaches a callout point, the external func-
+ During matching, when PCRE reaches a callout point, the external func-
tion defined by pcre_callout or pcre[16|32]_callout is called (if it is
- set). This applies to both normal and DFA matching. The only argument
- to the callout function is a pointer to a pcre_callout or
- pcre[16|32]_callout block. These structures contains the following
+ set). This applies to both normal and DFA matching. The only argument
+ to the callout function is a pointer to a pcre_callout or
+ pcre[16|32]_callout block. These structures contains the following
fields:
int version;
@@ -4215,44 +4402,47 @@ THE CALLOUT INTERFACE
const PCRE_UCHAR16 *mark; (16-bit version)
const PCRE_UCHAR32 *mark; (32-bit version)
- The version field is an integer containing the version number of the
- block format. The initial version was 0; the current version is 2. The
- version number will change again in future if additional fields are
+ The version field is an integer containing the version number of the
+ block format. The initial version was 0; the current version is 2. The
+ version number will change again in future if additional fields are
added, but the intention is never to remove any of the existing fields.
- The callout_number field contains the number of the callout, as com-
- piled into the pattern (that is, the number after ?C for manual call-
+ The callout_number field contains the number of the callout, as com-
+ piled into the pattern (that is, the number after ?C for manual call-
outs, and 255 for automatically generated callouts).
- The offset_vector field is a pointer to the vector of offsets that was
- passed by the caller to the matching function. When pcre_exec() or
- pcre[16|32]_exec() is used, the contents can be inspected, in order to
- extract substrings that have been matched so far, in the same way as
- for extracting substrings after a match has completed. For the DFA
+ The offset_vector field is a pointer to the vector of offsets that was
+ passed by the caller to the matching function. When pcre_exec() or
+ pcre[16|32]_exec() is used, the contents can be inspected, in order to
+ extract substrings that have been matched so far, in the same way as
+ for extracting substrings after a match has completed. For the DFA
matching functions, this field is not useful.
The subject and subject_length fields contain copies of the values that
were passed to the matching function.
- The start_match field normally contains the offset within the subject
- at which the current match attempt started. However, if the escape
- sequence \K has been encountered, this value is changed to reflect the
- modified starting point. If the pattern is not anchored, the callout
+ The start_match field normally contains the offset within the subject
+ at which the current match attempt started. However, if the escape
+ sequence \K has been encountered, this value is changed to reflect the
+ modified starting point. If the pattern is not anchored, the callout
function may be called several times from the same point in the pattern
for different starting points in the subject.
- The current_position field contains the offset within the subject of
+ The current_position field contains the offset within the subject of
the current match pointer.
- When the pcre_exec() or pcre[16|32]_exec() is used, the capture_top
- field contains one more than the number of the highest numbered cap-
- tured substring so far. If no substrings have been captured, the value
- of capture_top is one. This is always the case when the DFA functions
+ When the pcre_exec() or pcre[16|32]_exec() is used, the capture_top
+ field contains one more than the number of the highest numbered cap-
+ tured substring so far. If no substrings have been captured, the value
+ of capture_top is one. This is always the case when the DFA functions
are used, because they do not support captured substrings.
- The capture_last field contains the number of the most recently cap-
- tured substring. If no substrings have been captured, its value is -1.
- This is always the case for the DFA matching functions.
+ The capture_last field contains the number of the most recently cap-
+ tured substring. However, when a recursion exits, the value reverts to
+ what it was outside the recursion, as do the values of all captured
+ substrings. If no substrings have been captured, the value of cap-
+ ture_last is -1. This is always the case for the DFA matching func-
+ tions.
The callout_data field contains a value that is passed to a matching
function specifically so that it can be passed back in callouts. It is
@@ -4310,18 +4500,18 @@ AUTHOR
REVISION
- Last updated: 24 June 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRECOMPAT(3) PCRECOMPAT(3)
+PCRECOMPAT(3) Library Functions Manual PCRECOMPAT(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
DIFFERENCES BETWEEN PCRE AND PERL
This document describes the differences in the ways that PCRE and Perl
@@ -4340,10 +4530,8 @@ DIFFERENCES BETWEEN PCRE AND PERL
3. Capturing subpatterns that occur inside negative lookahead asser-
tions are counted, but their entries in the offsets vector are never
- set. Perl sets its numerical variables from any such patterns that are
- matched before the assertion fails to match something (thereby succeed-
- ing), but only if the negative lookahead assertion contains just one
- branch.
+ set. Perl sometimes (but not always) sets its numerical variables from
+ inside negative assertions.
4. Though binary zero characters are supported in the subject string,
they are not allowed in a pattern string because it is passed as a nor-
@@ -4398,24 +4586,30 @@ DIFFERENCES BETWEEN PCRE AND PERL
There is a discussion that explains these differences in more detail in
the section on recursion differences from Perl in the pcrepattern page.
- 10. If any of the backtracking control verbs are used in an assertion
- or in a subpattern that is called as a subroutine (whether or not
- recursively), their effect is confined to that subpattern; it does not
- extend to the surrounding pattern. This is not always the case in Perl.
- In particular, if (*THEN) is present in a group that is called as a
- subroutine, its action is limited to that group, even if the group does
- not contain any | characters. There is one exception to this: the name
- from a *(MARK), (*PRUNE), or (*THEN) that is encountered in a success-
- ful positive assertion is passed back when a match succeeds (compare
- capturing parentheses in assertions). Note that such subpatterns are
- processed as anchored at the point where they are tested.
-
- 11. There are some differences that are concerned with the settings of
+ 10. If any of the backtracking control verbs are used in a subpattern
+ that is called as a subroutine (whether or not recursively), their
+ effect is confined to that subpattern; it does not extend to the sur-
+ rounding pattern. This is not always the case in Perl. In particular,
+ if (*THEN) is present in a group that is called as a subroutine, its
+ action is limited to that group, even if the group does not contain any
+ | characters. Note that such subpatterns are processed as anchored at
+ the point where they are tested.
+
+ 11. If a pattern contains more than one backtracking control verb, the
+ first one that is backtracked onto acts. For example, in the pattern
+ A(*COMMIT)B(*PRUNE)C a failure in B triggers (*COMMIT), but a failure
+ in C triggers (*PRUNE). Perl's behaviour is more complex; in many cases
+ it is the same as PCRE, but there are examples where it differs.
+
+ 12. Most backtracking verbs in assertions have their normal actions.
+ They are not confined to the assertion.
+
+ 13. There are some differences that are concerned with the settings of
captured strings when part of a pattern is repeated. For example,
matching "aba" against the pattern /^(a(b)?)+$/ in Perl leaves $2
unset, but in PCRE it is set to "b".
- 12. PCRE's handling of duplicate subpattern numbers and duplicate sub-
+ 14. PCRE's handling of duplicate subpattern numbers and duplicate sub-
pattern names is not as general as Perl's. This is a consequence of the
fact the PCRE works internally just with numbers, using an external ta-
ble to translate between numbers and names. In particular, a pattern
@@ -4426,29 +4620,42 @@ DIFFERENCES BETWEEN PCRE AND PERL
turing subpattern number 1. To avoid this confusing situation, an error
is given at compile time.
- 13. Perl recognizes comments in some places that PCRE does not, for
+ 15. Perl recognizes comments in some places that PCRE does not, for
example, between the ( and ? at the start of a subpattern. If the /x
- modifier is set, Perl allows white space between ( and ? but PCRE never
- does, even if the PCRE_EXTENDED option is set.
-
- 14. PCRE provides some extensions to the Perl regular expression facil-
- ities. Perl 5.10 includes new features that are not in earlier ver-
- sions of Perl, some of which (such as named parentheses) have been in
+ modifier is set, Perl allows white space between ( and ? (though cur-
+ rent Perls warn that this is deprecated) but PCRE never does, even if
+ the PCRE_EXTENDED option is set.
+
+ 16. Perl, when in warning mode, gives warnings for character classes
+ such as [A-\d] or [a-[:digit:]]. It then treats the hyphens as liter-
+ als. PCRE has no warning features, so it gives an error in these cases
+ because they are almost certainly user mistakes.
+
+ 17. In PCRE, the upper/lower case character properties Lu and Ll are
+ not affected when case-independent matching is specified. For example,
+ \p{Lu} always matches an upper case letter. I think Perl has changed in
+ this respect; in the release at the time of writing (5.16), \p{Lu} and
+ \p{Ll} match all letters, regardless of case, when case independence is
+ specified.
+
+ 18. PCRE provides some extensions to the Perl regular expression facil-
+ ities. Perl 5.10 includes new features that are not in earlier ver-
+ sions of Perl, some of which (such as named parentheses) have been in
PCRE for some time. This list is with respect to Perl 5.10:
- (a) Although lookbehind assertions in PCRE must match fixed length
- strings, each alternative branch of a lookbehind assertion can match a
- different length of string. Perl requires them all to have the same
+ (a) Although lookbehind assertions in PCRE must match fixed length
+ strings, each alternative branch of a lookbehind assertion can match a
+ different length of string. Perl requires them all to have the same
length.
- (b) If PCRE_DOLLAR_ENDONLY is set and PCRE_MULTILINE is not set, the $
+ (b) If PCRE_DOLLAR_ENDONLY is set and PCRE_MULTILINE is not set, the $
meta-character matches only at the very end of the string.
(c) If PCRE_EXTRA is set, a backslash followed by a letter with no spe-
cial meaning is faulted. Otherwise, like Perl, the backslash is quietly
ignored. (Perl can be made to issue a warning.)
- (d) If PCRE_UNGREEDY is set, the greediness of the repetition quanti-
+ (d) If PCRE_UNGREEDY is set, the greediness of the repetition quanti-
fiers is inverted, that is, by default they are not greedy, but if fol-
lowed by a question mark they are.
@@ -4456,10 +4663,10 @@ DIFFERENCES BETWEEN PCRE AND PERL
tried only at the first matching position in the subject string.
(f) The PCRE_NOTBOL, PCRE_NOTEOL, PCRE_NOTEMPTY, PCRE_NOTEMPTY_ATSTART,
- and PCRE_NO_AUTO_CAPTURE options for pcre_exec() have no Perl equiva-
+ and PCRE_NO_AUTO_CAPTURE options for pcre_exec() have no Perl equiva-
lents.
- (g) The \R escape sequence can be restricted to match only CR, LF, or
+ (g) The \R escape sequence can be restricted to match only CR, LF, or
CRLF by the PCRE_BSR_ANYCRLF option.
(h) The callout facility is PCRE-specific.
@@ -4467,14 +4674,14 @@ DIFFERENCES BETWEEN PCRE AND PERL
(i) The partial matching facility is PCRE-specific.
(j) Patterns compiled by PCRE can be saved and re-used at a later time,
- even on different hosts that have the other endianness. However, this
+ even on different hosts that have the other endianness. However, this
does not apply to optimized data created by the just-in-time compiler.
(k) The alternative matching functions (pcre_dfa_exec(),
- pcre16_dfa_exec() and pcre32_dfa_exec(),) match in a different way and
+ pcre16_dfa_exec() and pcre32_dfa_exec(),) match in a different way and
are not Perl-compatible.
- (l) PCRE recognizes some special sequences such as (*CR) at the start
+ (l) PCRE recognizes some special sequences such as (*CR) at the start
of a pattern that set overall options that cannot be changed within the
pattern.
@@ -4488,18 +4695,18 @@ AUTHOR
REVISION
- Last updated: 25 August 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 10 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREPATTERN(3) PCREPATTERN(3)
+PCREPATTERN(3) Library Functions Manual PCREPATTERN(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE REGULAR EXPRESSION DETAILS
The syntax and semantics of the regular expressions that are supported
@@ -4517,6 +4724,29 @@ PCRE REGULAR EXPRESSION DETAILS
great detail. This description of PCRE's regular expressions is
intended as reference material.
+ This document discusses the patterns that are supported by PCRE when
+ one its main matching functions, pcre_exec() (8-bit) or
+ pcre[16|32]_exec() (16- or 32-bit), is used. PCRE also has alternative
+ matching functions, pcre_dfa_exec() and pcre[16|32_dfa_exec(), which
+ match using a different algorithm that is not Perl-compatible. Some of
+ the features discussed below are not available when DFA matching is
+ used. The advantages and disadvantages of the alternative functions,
+ and how they differ from the normal functions, are discussed in the
+ pcrematching page.
+
+
+SPECIAL START-OF-PATTERN ITEMS
+
+ A number of options that can be passed to pcre_compile() can also be
+ set by special items at the start of a pattern. These are not Perl-com-
+ patible, but are provided to make these options accessible to pattern
+ writers who are not able to change the program that processes the pat-
+ tern. Any number of these items may appear, but they must all be
+ together right at the start of the pattern string, and the letters must
+ be in upper case.
+
+ UTF support
+
The original operation of PCRE was on strings of one-byte characters.
However, there is now also support for UTF-8 strings in the original
library, an extra library that supports 16-bit and UTF-16 character
@@ -4533,47 +4763,39 @@ PCRE REGULAR EXPRESSION DETAILS
(*UTF) is a generic sequence that can be used with any of the
libraries. Starting a pattern with such a sequence is equivalent to
- setting the relevant option. This feature is not Perl-compatible. How
- setting a UTF mode affects pattern matching is mentioned in several
- places below. There is also a summary of features in the pcreunicode
- page.
+ setting the relevant option. How setting a UTF mode affects pattern
+ matching is mentioned in several places below. There is also a summary
+ of features in the pcreunicode page.
- Another special sequence that may appear at the start of a pattern or
- in combination with (*UTF8), (*UTF16), (*UTF32) or (*UTF) is:
+ Some applications that allow their users to supply patterns may wish to
+ restrict them to non-UTF data for security reasons. If the
+ PCRE_NEVER_UTF option is set at compile time, (*UTF) etc. are not
+ allowed, and their appearance causes an error.
- (*UCP)
+ Unicode property support
- This has the same effect as setting the PCRE_UCP option: it causes
- sequences such as \d and \w to use Unicode properties to determine
- character types, instead of recognizing only characters with codes less
- than 128 via a lookup table.
+ Another special sequence that may appear at the start of a pattern is
+ (*UCP). This has the same effect as setting the PCRE_UCP option: it
+ causes sequences such as \d and \w to use Unicode properties to deter-
+ mine character types, instead of recognizing only characters with codes
+ less than 128 via a lookup table.
- If a pattern starts with (*NO_START_OPT), it has the same effect as
- setting the PCRE_NO_START_OPTIMIZE option either at compile or matching
- time. There are also some more of these special sequences that are con-
- cerned with the handling of newlines; they are described below.
+ Disabling auto-possessification
- The remainder of this document discusses the patterns that are sup-
- ported by PCRE when one its main matching functions, pcre_exec()
- (8-bit) or pcre[16|32]_exec() (16- or 32-bit), is used. PCRE also has
- alternative matching functions, pcre_dfa_exec() and
- pcre[16|32_dfa_exec(), which match using a different algorithm that is
- not Perl-compatible. Some of the features discussed below are not
- available when DFA matching is used. The advantages and disadvantages
- of the alternative functions, and how they differ from the normal func-
- tions, are discussed in the pcrematching page.
+ If a pattern starts with (*NO_AUTO_POSSESS), it has the same effect as
+ setting the PCRE_NO_AUTO_POSSESS option at compile time. This stops
+ PCRE from making quantifiers possessive when what follows cannot match
+ the repeated item. For example, by default a+b is treated as a++b. For
+ more details, see the pcreapi documentation.
+ Disabling start-up optimizations
-EBCDIC CHARACTER CODES
-
- PCRE can be compiled to run in an environment that uses EBCDIC as its
- character code rather than ASCII or Unicode (typically a mainframe sys-
- tem). In the sections below, character code values are ASCII or Uni-
- code; in an EBCDIC environment these characters may have different code
- values, and there are no code points greater than 255.
-
+ If a pattern starts with (*NO_START_OPT), it has the same effect as
+ setting the PCRE_NO_START_OPTIMIZE option either at compile or matching
+ time. This disables several optimizations for quickly reaching "no
+ match" results. For more details, see the pcreapi documentation.
-NEWLINE CONVENTIONS
+ Newline conventions
PCRE supports five different conventions for indicating line breaks in
strings: a single CR (carriage return) character, a single LF (line-
@@ -4598,10 +4820,8 @@ NEWLINE CONVENTIONS
(*CR)a.b
changes the convention to CR. That pattern matches "a\nb" because LF is
- no longer a newline. Note that these special settings, which are not
- Perl-compatible, are recognized only at the very start of a pattern,
- and that they must be in upper case. If more than one of them is
- present, the last one is used.
+ no longer a newline. If more than one of these settings is present, the
+ last one is used.
The newline convention affects where the circumflex and dollar asser-
tions are true. It also affects the interpretation of the dot metachar-
@@ -4612,6 +4832,36 @@ NEWLINE CONVENTIONS
line sequences" below. A change of \R setting can be combined with a
change of newline convention.
+ Setting match and recursion limits
+
+ The caller of pcre_exec() can set a limit on the number of times the
+ internal match() function is called and on the maximum depth of recur-
+ sive calls. These facilities are provided to catch runaway matches that
+ are provoked by patterns with huge matching trees (a typical example is
+ a pattern with nested unlimited repeats) and to avoid running out of
+ system stack by too much recursion. When one of these limits is
+ reached, pcre_exec() gives an error return. The limits can also be set
+ by items at the start of the pattern of the form
+
+ (*LIMIT_MATCH=d)
+ (*LIMIT_RECURSION=d)
+
+ where d is any number of decimal digits. However, the value of the set-
+ ting must be less than the value set (or defaulted) by the caller of
+ pcre_exec() for it to have any effect. In other words, the pattern
+ writer can lower the limits set by the programmer, but not raise them.
+ If there is more than one setting of one of these limits, the lower
+ value is used.
+
+
+EBCDIC CHARACTER CODES
+
+ PCRE can be compiled to run in an environment that uses EBCDIC as its
+ character code rather than ASCII or Unicode (typically a mainframe sys-
+ tem). In the sections below, character code values are ASCII or Uni-
+ code; in an EBCDIC environment these characters may have different code
+ values, and there are no code points greater than 255.
+
CHARACTERS AND METACHARACTERS
@@ -4689,11 +4939,11 @@ BACKSLASH
after a backslash. All other characters (in particular, those whose
codepoints are greater than 127) are treated as literals.
- If a pattern is compiled with the PCRE_EXTENDED option, white space in
- the pattern (other than in a character class) and characters between a
- # outside a character class and the next newline are ignored. An escap-
- ing backslash can be used to include a white space or # character as
- part of the pattern.
+ If a pattern is compiled with the PCRE_EXTENDED option, most white
+ space in the pattern (other than in a character class), and characters
+ between a # outside a character class and the next newline, inclusive,
+ are ignored. An escaping backslash can be used to include a white space
+ or # character as part of the pattern.
If you want to remove the special meaning from a sequence of charac-
ters, you can do so by putting them between \Q and \E. This is differ-
@@ -4731,7 +4981,9 @@ BACKSLASH
\n linefeed (hex 0A)
\r carriage return (hex 0D)
\t tab (hex 09)
+ \0dd character with octal code 0dd
\ddd character with octal code ddd, or back reference
+ \o{ddd..} character with octal code ddd..
\xhh character with hex code hh
\x{hhh..} character with hex code hhh.. (non-JavaScript mode)
\uhhhh character with hex code hhhh (JavaScript mode only)
@@ -4754,61 +5006,38 @@ BACKSLASH
are disjoint, \cZ becomes hex 29 (Z is E9), and other characters also
generate different values.
- By default, after \x, from zero to two hexadecimal digits are read
- (letters can be in upper or lower case). Any number of hexadecimal dig-
- its may appear between \x{ and }, but the character code is constrained
- as follows:
-
- 8-bit non-UTF mode less than 0x100
- 8-bit UTF-8 mode less than 0x10ffff and a valid codepoint
- 16-bit non-UTF mode less than 0x10000
- 16-bit UTF-16 mode less than 0x10ffff and a valid codepoint
- 32-bit non-UTF mode less than 0x80000000
- 32-bit UTF-32 mode less than 0x10ffff and a valid codepoint
-
- Invalid Unicode codepoints are the range 0xd800 to 0xdfff (the so-
- called "surrogate" codepoints), and 0xffef.
-
- If characters other than hexadecimal digits appear between \x{ and },
- or if there is no terminating }, this form of escape is not recognized.
- Instead, the initial \x will be interpreted as a basic hexadecimal
- escape, with no following digits, giving a character whose value is
- zero.
-
- If the PCRE_JAVASCRIPT_COMPAT option is set, the interpretation of \x
- is as just described only when it is followed by two hexadecimal dig-
- its. Otherwise, it matches a literal "x" character. In JavaScript
- mode, support for code points greater than 256 is provided by \u, which
- must be followed by four hexadecimal digits; otherwise it matches a
- literal "u" character. Character codes specified by \u in JavaScript
- mode are constrained in the same was as those specified by \x in non-
- JavaScript mode.
-
- Characters whose value is less than 256 can be defined by either of the
- two syntaxes for \x (or by \u in JavaScript mode). There is no differ-
- ence in the way they are handled. For example, \xdc is exactly the same
- as \x{dc} (or \u00dc in JavaScript mode).
-
After \0 up to two further octal digits are read. If there are fewer
than two digits, just those that are present are used. Thus the
sequence \0\x\07 specifies two binary zeros followed by a BEL character
(code value 7). Make sure you supply two digits after the initial zero
if the pattern character that follows is itself an octal digit.
+ The escape \o must be followed by a sequence of octal digits, enclosed
+ in braces. An error occurs if this is not the case. This escape is a
+ recent addition to Perl; it provides way of specifying character code
+ points as octal numbers greater than 0777, and it also allows octal
+ numbers and back references to be unambiguously specified.
+
+ For greater clarity and unambiguity, it is best to avoid following \ by
+ a digit greater than zero. Instead, use \o{} or \x{} to specify charac-
+ ter numbers, and \g{} to specify back references. The following para-
+ graphs describe the old, ambiguous syntax.
+
The handling of a backslash followed by a digit other than 0 is compli-
- cated. Outside a character class, PCRE reads it and any following dig-
- its as a decimal number. If the number is less than 10, or if there
- have been at least that many previous capturing left parentheses in the
- expression, the entire sequence is taken as a back reference. A
+ cated, and Perl has changed in recent releases, causing PCRE also to
+ change. Outside a character class, PCRE reads the digit and any follow-
+ ing digits as a decimal number. If the number is less than 8, or if
+ there have been at least that many previous capturing left parentheses
+ in the expression, the entire sequence is taken as a back reference. A
description of how this works is given later, following the discussion
of parenthesized subpatterns.
- Inside a character class, or if the decimal number is greater than 9
- and there have not been that many capturing subpatterns, PCRE re-reads
- up to three octal digits following the backslash, and uses them to gen-
- erate a data character. Any subsequent digits stand for themselves. The
- value of the character is constrained in the same way as characters
- specified in hexadecimal. For example:
+ Inside a character class, or if the decimal number following \ is
+ greater than 7 and there have not been that many capturing subpatterns,
+ PCRE handles \8 and \9 as the literal characters "8" and "9", and oth-
+ erwise re-reads up to three octal digits following the backslash, using
+ them to generate a data character. Any subsequent digits stand for
+ themselves. For example:
\040 is another way of writing an ASCII space
\40 is the same, provided there are fewer than 40
@@ -4822,45 +5051,81 @@ BACKSLASH
character with octal code 113
\377 might be a back reference, otherwise
the value 255 (decimal)
- \81 is either a back reference, or a binary zero
- followed by the two characters "8" and "1"
+ \81 is either a back reference, or the two
+ characters "8" and "1"
+
+ Note that octal values of 100 or greater that are specified using this
+ syntax must not be introduced by a leading zero, because no more than
+ three octal digits are ever read.
+
+ By default, after \x that is not followed by {, from zero to two hexa-
+ decimal digits are read (letters can be in upper or lower case). Any
+ number of hexadecimal digits may appear between \x{ and }. If a charac-
+ ter other than a hexadecimal digit appears between \x{ and }, or if
+ there is no terminating }, an error occurs.
+
+ If the PCRE_JAVASCRIPT_COMPAT option is set, the interpretation of \x
+ is as just described only when it is followed by two hexadecimal dig-
+ its. Otherwise, it matches a literal "x" character. In JavaScript
+ mode, support for code points greater than 256 is provided by \u, which
+ must be followed by four hexadecimal digits; otherwise it matches a
+ literal "u" character.
+
+ Characters whose value is less than 256 can be defined by either of the
+ two syntaxes for \x (or by \u in JavaScript mode). There is no differ-
+ ence in the way they are handled. For example, \xdc is exactly the same
+ as \x{dc} (or \u00dc in JavaScript mode).
- Note that octal values of 100 or greater must not be introduced by a
- leading zero, because no more than three octal digits are ever read.
+ Constraints on character values
+
+ Characters that are specified using octal or hexadecimal numbers are
+ limited to certain values, as follows:
+
+ 8-bit non-UTF mode less than 0x100
+ 8-bit UTF-8 mode less than 0x10ffff and a valid codepoint
+ 16-bit non-UTF mode less than 0x10000
+ 16-bit UTF-16 mode less than 0x10ffff and a valid codepoint
+ 32-bit non-UTF mode less than 0x100000000
+ 32-bit UTF-32 mode less than 0x10ffff and a valid codepoint
+
+ Invalid Unicode codepoints are the range 0xd800 to 0xdfff (the so-
+ called "surrogate" codepoints), and 0xffef.
+
+ Escape sequences in character classes
All the sequences that define a single character value can be used both
- inside and outside character classes. In addition, inside a character
+ inside and outside character classes. In addition, inside a character
class, \b is interpreted as the backspace character (hex 08).
- \N is not allowed in a character class. \B, \R, and \X are not special
- inside a character class. Like other unrecognized escape sequences,
- they are treated as the literal characters "B", "R", and "X" by
- default, but cause an error if the PCRE_EXTRA option is set. Outside a
+ \N is not allowed in a character class. \B, \R, and \X are not special
+ inside a character class. Like other unrecognized escape sequences,
+ they are treated as the literal characters "B", "R", and "X" by
+ default, but cause an error if the PCRE_EXTRA option is set. Outside a
character class, these sequences have different meanings.
Unsupported escape sequences
- In Perl, the sequences \l, \L, \u, and \U are recognized by its string
- handler and used to modify the case of following characters. By
- default, PCRE does not support these escape sequences. However, if the
- PCRE_JAVASCRIPT_COMPAT option is set, \U matches a "U" character, and
+ In Perl, the sequences \l, \L, \u, and \U are recognized by its string
+ handler and used to modify the case of following characters. By
+ default, PCRE does not support these escape sequences. However, if the
+ PCRE_JAVASCRIPT_COMPAT option is set, \U matches a "U" character, and
\u can be used to define a character by code point, as described in the
previous section.
Absolute and relative back references
- The sequence \g followed by an unsigned or a negative number, option-
- ally enclosed in braces, is an absolute or relative back reference. A
+ The sequence \g followed by an unsigned or a negative number, option-
+ ally enclosed in braces, is an absolute or relative back reference. A
named back reference can be coded as \g{name}. Back references are dis-
cussed later, following the discussion of parenthesized subpatterns.
Absolute and relative subroutine calls
- For compatibility with Oniguruma, the non-Perl syntax \g followed by a
+ For compatibility with Oniguruma, the non-Perl syntax \g followed by a
name or a number enclosed either in angle brackets or single quotes, is
- an alternative syntax for referencing a subpattern as a "subroutine".
- Details are discussed later. Note that \g{...} (Perl syntax) and
- \g<...> (Oniguruma syntax) are not synonymous. The former is a back
+ an alternative syntax for referencing a subpattern as a "subroutine".
+ Details are discussed later. Note that \g{...} (Perl syntax) and
+ \g<...> (Oniguruma syntax) are not synonymous. The former is a back
reference; the latter is a subroutine call.
Generic character types
@@ -4879,44 +5144,49 @@ BACKSLASH
\W any "non-word" character
There is also the single sequence \N, which matches a non-newline char-
- acter. This is the same as the "." metacharacter when PCRE_DOTALL is
- not set. Perl also uses \N to match characters by name; PCRE does not
+ acter. This is the same as the "." metacharacter when PCRE_DOTALL is
+ not set. Perl also uses \N to match characters by name; PCRE does not
support this.
- Each pair of lower and upper case escape sequences partitions the com-
- plete set of characters into two disjoint sets. Any given character
- matches one, and only one, of each pair. The sequences can appear both
- inside and outside character classes. They each match one character of
- the appropriate type. If the current matching point is at the end of
- the subject string, all of them fail, because there is no character to
+ Each pair of lower and upper case escape sequences partitions the com-
+ plete set of characters into two disjoint sets. Any given character
+ matches one, and only one, of each pair. The sequences can appear both
+ inside and outside character classes. They each match one character of
+ the appropriate type. If the current matching point is at the end of
+ the subject string, all of them fail, because there is no character to
match.
- For compatibility with Perl, \s does not match the VT character (code
- 11). This makes it different from the the POSIX "space" class. The \s
- characters are HT (9), LF (10), FF (12), CR (13), and space (32). If
- "use locale;" is included in a Perl script, \s may match the VT charac-
- ter. In PCRE, it never does.
-
- A "word" character is an underscore or any character that is a letter
- or digit. By default, the definition of letters and digits is con-
- trolled by PCRE's low-valued character tables, and may vary if locale-
- specific matching is taking place (see "Locale support" in the pcreapi
- page). For example, in a French locale such as "fr_FR" in Unix-like
- systems, or "french" in Windows, some character codes greater than 128
- are used for accented letters, and these are then matched by \w. The
+ For compatibility with Perl, \s did not used to match the VT character
+ (code 11), which made it different from the the POSIX "space" class.
+ However, Perl added VT at release 5.18, and PCRE followed suit at
+ release 8.34. The default \s characters are now HT (9), LF (10), VT
+ (11), FF (12), CR (13), and space (32), which are defined as white
+ space in the "C" locale. This list may vary if locale-specific matching
+ is taking place. For example, in some locales the "non-breaking space"
+ character (\xA0) is recognized as white space, and in others the VT
+ character is not.
+
+ A "word" character is an underscore or any character that is a letter
+ or digit. By default, the definition of letters and digits is con-
+ trolled by PCRE's low-valued character tables, and may vary if locale-
+ specific matching is taking place (see "Locale support" in the pcreapi
+ page). For example, in a French locale such as "fr_FR" in Unix-like
+ systems, or "french" in Windows, some character codes greater than 127
+ are used for accented letters, and these are then matched by \w. The
use of locales with Unicode is discouraged.
- By default, in a UTF mode, characters with values greater than 128
- never match \d, \s, or \w, and always match \D, \S, and \W. These
- sequences retain their original meanings from before UTF support was
- available, mainly for efficiency reasons. However, if PCRE is compiled
- with Unicode property support, and the PCRE_UCP option is set, the be-
- haviour is changed so that Unicode properties are used to determine
- character types, as follows:
+ By default, characters whose code points are greater than 127 never
+ match \d, \s, or \w, and always match \D, \S, and \W, although this may
+ vary for characters in the range 128-255 when locale-specific matching
+ is happening. These escape sequences retain their original meanings
+ from before Unicode support was available, mainly for efficiency rea-
+ sons. If PCRE is compiled with Unicode property support, and the
+ PCRE_UCP option is set, the behaviour is changed so that Unicode prop-
+ erties are used to determine character types, as follows:
- \d any character that \p{Nd} matches (decimal digit)
- \s any character that \p{Z} matches, plus HT, LF, FF, CR
- \w any character that \p{L} or \p{N} matches, plus underscore
+ \d any character that matches \p{Nd} (decimal digit)
+ \s any character that matches \p{Z} or \h or \v
+ \w any character that matches \p{L} or \p{N}, plus underscore
The upper case escapes match the inverse sets of characters. Note that
\d matches only decimal digits, whereas \w matches any Unicode digit,
@@ -4927,7 +5197,7 @@ BACKSLASH
The sequences \h, \H, \v, and \V are features that were added to Perl
at release 5.10. In contrast to the other sequences, which match only
ASCII characters by default, these always match certain high-valued
- codepoints, whether or not PCRE_UCP is set. The horizontal space char-
+ code points, whether or not PCRE_UCP is set. The horizontal space char-
acters are:
U+0009 Horizontal tab (HT)
@@ -5136,52 +5406,53 @@ BACKSLASH
in the Unicode table.
Specifying caseless matching does not affect these escape sequences.
- For example, \p{Lu} always matches only upper case letters.
+ For example, \p{Lu} always matches only upper case letters. This is
+ different from the behaviour of current versions of Perl.
- Matching characters by Unicode property is not fast, because PCRE has
- to do a multistage table lookup in order to find a character's prop-
+ Matching characters by Unicode property is not fast, because PCRE has
+ to do a multistage table lookup in order to find a character's prop-
erty. That is why the traditional escape sequences such as \d and \w do
not use Unicode properties in PCRE by default, though you can make them
- do so by setting the PCRE_UCP option or by starting the pattern with
+ do so by setting the PCRE_UCP option or by starting the pattern with
(*UCP).
Extended grapheme clusters
- The \X escape matches any number of Unicode characters that form an
+ The \X escape matches any number of Unicode characters that form an
"extended grapheme cluster", and treats the sequence as an atomic group
- (see below). Up to and including release 8.31, PCRE matched an ear-
+ (see below). Up to and including release 8.31, PCRE matched an ear-
lier, simpler definition that was equivalent to
(?>\PM\pM*)
- That is, it matched a character without the "mark" property, followed
- by zero or more characters with the "mark" property. Characters with
- the "mark" property are typically non-spacing accents that affect the
+ That is, it matched a character without the "mark" property, followed
+ by zero or more characters with the "mark" property. Characters with
+ the "mark" property are typically non-spacing accents that affect the
preceding character.
- This simple definition was extended in Unicode to include more compli-
- cated kinds of composite character by giving each character a grapheme
- breaking property, and creating rules that use these properties to
- define the boundaries of extended grapheme clusters. In releases of
+ This simple definition was extended in Unicode to include more compli-
+ cated kinds of composite character by giving each character a grapheme
+ breaking property, and creating rules that use these properties to
+ define the boundaries of extended grapheme clusters. In releases of
PCRE later than 8.31, \X matches one of these clusters.
- \X always matches at least one character. Then it decides whether to
+ \X always matches at least one character. Then it decides whether to
add additional characters according to the following rules for ending a
cluster:
1. End at the end of the subject string.
- 2. Do not end between CR and LF; otherwise end after any control char-
+ 2. Do not end between CR and LF; otherwise end after any control char-
acter.
- 3. Do not break Hangul (a Korean script) syllable sequences. Hangul
- characters are of five types: L, V, T, LV, and LVT. An L character may
- be followed by an L, V, LV, or LVT character; an LV or V character may
+ 3. Do not break Hangul (a Korean script) syllable sequences. Hangul
+ characters are of five types: L, V, T, LV, and LVT. An L character may
+ be followed by an L, V, LV, or LVT character; an LV or V character may
be followed by a V or T character; an LVT or T character may be follwed
only by a T character.
- 4. Do not end before extending characters or spacing marks. Characters
- with the "mark" property always have the "extend" grapheme breaking
+ 4. Do not end before extending characters or spacing marks. Characters
+ with the "mark" property always have the "extend" grapheme breaking
property.
5. Do not end after prepend characters.
@@ -5190,51 +5461,63 @@ BACKSLASH
PCRE's additional properties
- As well as the standard Unicode properties described above, PCRE sup-
- ports four more that make it possible to convert traditional escape
- sequences such as \w and \s and POSIX character classes to use Unicode
- properties. PCRE uses these non-standard, non-Perl properties inter-
- nally when PCRE_UCP is set. They are:
+ As well as the standard Unicode properties described above, PCRE sup-
+ ports four more that make it possible to convert traditional escape
+ sequences such as \w and \s to use Unicode properties. PCRE uses these
+ non-standard, non-Perl properties internally when PCRE_UCP is set. How-
+ ever, they may also be used explicitly. These properties are:
Xan Any alphanumeric character
Xps Any POSIX space character
Xsp Any Perl space character
Xwd Any Perl "word" character
- Xan matches characters that have either the L (letter) or the N (num-
- ber) property. Xps matches the characters tab, linefeed, vertical tab,
- form feed, or carriage return, and any other character that has the Z
- (separator) property. Xsp is the same as Xps, except that vertical tab
- is excluded. Xwd matches the same characters as Xan, plus underscore.
+ Xan matches characters that have either the L (letter) or the N (num-
+ ber) property. Xps matches the characters tab, linefeed, vertical tab,
+ form feed, or carriage return, and any other character that has the Z
+ (separator) property. Xsp is the same as Xps; it used to exclude ver-
+ tical tab, for Perl compatibility, but Perl changed, and so PCRE fol-
+ lowed at release 8.34. Xwd matches the same characters as Xan, plus
+ underscore.
+
+ There is another non-standard property, Xuc, which matches any charac-
+ ter that can be represented by a Universal Character Name in C++ and
+ other programming languages. These are the characters $, @, ` (grave
+ accent), and all characters with Unicode code points greater than or
+ equal to U+00A0, except for the surrogates U+D800 to U+DFFF. Note that
+ most base (ASCII) characters are excluded. (Universal Character Names
+ are of the form \uHHHH or \UHHHHHHHH where H is a hexadecimal digit.
+ Note that the Xuc property does not match these sequences but the char-
+ acters that they represent.)
Resetting the match start
- The escape sequence \K causes any previously matched characters not to
+ The escape sequence \K causes any previously matched characters not to
be included in the final matched sequence. For example, the pattern:
foo\Kbar
- matches "foobar", but reports that it has matched "bar". This feature
- is similar to a lookbehind assertion (described below). However, in
- this case, the part of the subject before the real match does not have
- to be of fixed length, as lookbehind assertions do. The use of \K does
- not interfere with the setting of captured substrings. For example,
+ matches "foobar", but reports that it has matched "bar". This feature
+ is similar to a lookbehind assertion (described below). However, in
+ this case, the part of the subject before the real match does not have
+ to be of fixed length, as lookbehind assertions do. The use of \K does
+ not interfere with the setting of captured substrings. For example,
when the pattern
(foo)\Kbar
matches "foobar", the first substring is still set to "foo".
- Perl documents that the use of \K within assertions is "not well
- defined". In PCRE, \K is acted upon when it occurs inside positive
+ Perl documents that the use of \K within assertions is "not well
+ defined". In PCRE, \K is acted upon when it occurs inside positive
assertions, but is ignored in negative assertions.
Simple assertions
- The final use of backslash is for certain simple assertions. An asser-
- tion specifies a condition that has to be met at a particular point in
- a match, without consuming any characters from the subject string. The
- use of subpatterns for more complicated assertions is described below.
+ The final use of backslash is for certain simple assertions. An asser-
+ tion specifies a condition that has to be met at a particular point in
+ a match, without consuming any characters from the subject string. The
+ use of subpatterns for more complicated assertions is described below.
The backslashed assertions are:
\b matches at a word boundary
@@ -5245,161 +5528,161 @@ BACKSLASH
\z matches only at the end of the subject
\G matches at the first matching position in the subject
- Inside a character class, \b has a different meaning; it matches the
- backspace character. If any other of these assertions appears in a
- character class, by default it matches the corresponding literal char-
+ Inside a character class, \b has a different meaning; it matches the
+ backspace character. If any other of these assertions appears in a
+ character class, by default it matches the corresponding literal char-
acter (for example, \B matches the letter B). However, if the
- PCRE_EXTRA option is set, an "invalid escape sequence" error is gener-
+ PCRE_EXTRA option is set, an "invalid escape sequence" error is gener-
ated instead.
- A word boundary is a position in the subject string where the current
- character and the previous character do not both match \w or \W (i.e.
- one matches \w and the other matches \W), or the start or end of the
- string if the first or last character matches \w, respectively. In a
- UTF mode, the meanings of \w and \W can be changed by setting the
- PCRE_UCP option. When this is done, it also affects \b and \B. Neither
- PCRE nor Perl has a separate "start of word" or "end of word" metase-
- quence. However, whatever follows \b normally determines which it is.
+ A word boundary is a position in the subject string where the current
+ character and the previous character do not both match \w or \W (i.e.
+ one matches \w and the other matches \W), or the start or end of the
+ string if the first or last character matches \w, respectively. In a
+ UTF mode, the meanings of \w and \W can be changed by setting the
+ PCRE_UCP option. When this is done, it also affects \b and \B. Neither
+ PCRE nor Perl has a separate "start of word" or "end of word" metase-
+ quence. However, whatever follows \b normally determines which it is.
For example, the fragment \ba matches "a" at the start of a word.
- The \A, \Z, and \z assertions differ from the traditional circumflex
+ The \A, \Z, and \z assertions differ from the traditional circumflex
and dollar (described in the next section) in that they only ever match
- at the very start and end of the subject string, whatever options are
- set. Thus, they are independent of multiline mode. These three asser-
+ at the very start and end of the subject string, whatever options are
+ set. Thus, they are independent of multiline mode. These three asser-
tions are not affected by the PCRE_NOTBOL or PCRE_NOTEOL options, which
- affect only the behaviour of the circumflex and dollar metacharacters.
- However, if the startoffset argument of pcre_exec() is non-zero, indi-
+ affect only the behaviour of the circumflex and dollar metacharacters.
+ However, if the startoffset argument of pcre_exec() is non-zero, indi-
cating that matching is to start at a point other than the beginning of
- the subject, \A can never match. The difference between \Z and \z is
+ the subject, \A can never match. The difference between \Z and \z is
that \Z matches before a newline at the end of the string as well as at
the very end, whereas \z matches only at the end.
- The \G assertion is true only when the current matching position is at
- the start point of the match, as specified by the startoffset argument
- of pcre_exec(). It differs from \A when the value of startoffset is
- non-zero. By calling pcre_exec() multiple times with appropriate argu-
+ The \G assertion is true only when the current matching position is at
+ the start point of the match, as specified by the startoffset argument
+ of pcre_exec(). It differs from \A when the value of startoffset is
+ non-zero. By calling pcre_exec() multiple times with appropriate argu-
ments, you can mimic Perl's /g option, and it is in this kind of imple-
mentation where \G can be useful.
- Note, however, that PCRE's interpretation of \G, as the start of the
+ Note, however, that PCRE's interpretation of \G, as the start of the
current match, is subtly different from Perl's, which defines it as the
- end of the previous match. In Perl, these can be different when the
- previously matched string was empty. Because PCRE does just one match
+ end of the previous match. In Perl, these can be different when the
+ previously matched string was empty. Because PCRE does just one match
at a time, it cannot reproduce this behaviour.
- If all the alternatives of a pattern begin with \G, the expression is
+ If all the alternatives of a pattern begin with \G, the expression is
anchored to the starting match position, and the "anchored" flag is set
in the compiled regular expression.
CIRCUMFLEX AND DOLLAR
- The circumflex and dollar metacharacters are zero-width assertions.
- That is, they test for a particular condition being true without con-
+ The circumflex and dollar metacharacters are zero-width assertions.
+ That is, they test for a particular condition being true without con-
suming any characters from the subject string.
Outside a character class, in the default matching mode, the circumflex
- character is an assertion that is true only if the current matching
- point is at the start of the subject string. If the startoffset argu-
- ment of pcre_exec() is non-zero, circumflex can never match if the
- PCRE_MULTILINE option is unset. Inside a character class, circumflex
+ character is an assertion that is true only if the current matching
+ point is at the start of the subject string. If the startoffset argu-
+ ment of pcre_exec() is non-zero, circumflex can never match if the
+ PCRE_MULTILINE option is unset. Inside a character class, circumflex
has an entirely different meaning (see below).
- Circumflex need not be the first character of the pattern if a number
- of alternatives are involved, but it should be the first thing in each
- alternative in which it appears if the pattern is ever to match that
- branch. If all possible alternatives start with a circumflex, that is,
- if the pattern is constrained to match only at the start of the sub-
- ject, it is said to be an "anchored" pattern. (There are also other
+ Circumflex need not be the first character of the pattern if a number
+ of alternatives are involved, but it should be the first thing in each
+ alternative in which it appears if the pattern is ever to match that
+ branch. If all possible alternatives start with a circumflex, that is,
+ if the pattern is constrained to match only at the start of the sub-
+ ject, it is said to be an "anchored" pattern. (There are also other
constructs that can cause a pattern to be anchored.)
- The dollar character is an assertion that is true only if the current
- matching point is at the end of the subject string, or immediately
- before a newline at the end of the string (by default). Note, however,
- that it does not actually match the newline. Dollar need not be the
+ The dollar character is an assertion that is true only if the current
+ matching point is at the end of the subject string, or immediately
+ before a newline at the end of the string (by default). Note, however,
+ that it does not actually match the newline. Dollar need not be the
last character of the pattern if a number of alternatives are involved,
- but it should be the last item in any branch in which it appears. Dol-
+ but it should be the last item in any branch in which it appears. Dol-
lar has no special meaning in a character class.
- The meaning of dollar can be changed so that it matches only at the
- very end of the string, by setting the PCRE_DOLLAR_ENDONLY option at
+ The meaning of dollar can be changed so that it matches only at the
+ very end of the string, by setting the PCRE_DOLLAR_ENDONLY option at
compile time. This does not affect the \Z assertion.
The meanings of the circumflex and dollar characters are changed if the
- PCRE_MULTILINE option is set. When this is the case, a circumflex
- matches immediately after internal newlines as well as at the start of
- the subject string. It does not match after a newline that ends the
- string. A dollar matches before any newlines in the string, as well as
- at the very end, when PCRE_MULTILINE is set. When newline is specified
- as the two-character sequence CRLF, isolated CR and LF characters do
+ PCRE_MULTILINE option is set. When this is the case, a circumflex
+ matches immediately after internal newlines as well as at the start of
+ the subject string. It does not match after a newline that ends the
+ string. A dollar matches before any newlines in the string, as well as
+ at the very end, when PCRE_MULTILINE is set. When newline is specified
+ as the two-character sequence CRLF, isolated CR and LF characters do
not indicate newlines.
- For example, the pattern /^abc$/ matches the subject string "def\nabc"
- (where \n represents a newline) in multiline mode, but not otherwise.
- Consequently, patterns that are anchored in single line mode because
- all branches start with ^ are not anchored in multiline mode, and a
- match for circumflex is possible when the startoffset argument of
- pcre_exec() is non-zero. The PCRE_DOLLAR_ENDONLY option is ignored if
+ For example, the pattern /^abc$/ matches the subject string "def\nabc"
+ (where \n represents a newline) in multiline mode, but not otherwise.
+ Consequently, patterns that are anchored in single line mode because
+ all branches start with ^ are not anchored in multiline mode, and a
+ match for circumflex is possible when the startoffset argument of
+ pcre_exec() is non-zero. The PCRE_DOLLAR_ENDONLY option is ignored if
PCRE_MULTILINE is set.
- Note that the sequences \A, \Z, and \z can be used to match the start
- and end of the subject in both modes, and if all branches of a pattern
- start with \A it is always anchored, whether or not PCRE_MULTILINE is
+ Note that the sequences \A, \Z, and \z can be used to match the start
+ and end of the subject in both modes, and if all branches of a pattern
+ start with \A it is always anchored, whether or not PCRE_MULTILINE is
set.
FULL STOP (PERIOD, DOT) AND \N
Outside a character class, a dot in the pattern matches any one charac-
- ter in the subject string except (by default) a character that signi-
+ ter in the subject string except (by default) a character that signi-
fies the end of a line.
- When a line ending is defined as a single character, dot never matches
- that character; when the two-character sequence CRLF is used, dot does
- not match CR if it is immediately followed by LF, but otherwise it
- matches all characters (including isolated CRs and LFs). When any Uni-
- code line endings are being recognized, dot does not match CR or LF or
+ When a line ending is defined as a single character, dot never matches
+ that character; when the two-character sequence CRLF is used, dot does
+ not match CR if it is immediately followed by LF, but otherwise it
+ matches all characters (including isolated CRs and LFs). When any Uni-
+ code line endings are being recognized, dot does not match CR or LF or
any of the other line ending characters.
- The behaviour of dot with regard to newlines can be changed. If the
- PCRE_DOTALL option is set, a dot matches any one character, without
+ The behaviour of dot with regard to newlines can be changed. If the
+ PCRE_DOTALL option is set, a dot matches any one character, without
exception. If the two-character sequence CRLF is present in the subject
string, it takes two dots to match it.
- The handling of dot is entirely independent of the handling of circum-
- flex and dollar, the only relationship being that they both involve
+ The handling of dot is entirely independent of the handling of circum-
+ flex and dollar, the only relationship being that they both involve
newlines. Dot has no special meaning in a character class.
- The escape sequence \N behaves like a dot, except that it is not
- affected by the PCRE_DOTALL option. In other words, it matches any
- character except one that signifies the end of a line. Perl also uses
+ The escape sequence \N behaves like a dot, except that it is not
+ affected by the PCRE_DOTALL option. In other words, it matches any
+ character except one that signifies the end of a line. Perl also uses
\N to match characters by name; PCRE does not support this.
MATCHING A SINGLE DATA UNIT
- Outside a character class, the escape sequence \C matches any one data
- unit, whether or not a UTF mode is set. In the 8-bit library, one data
- unit is one byte; in the 16-bit library it is a 16-bit unit; in the
- 32-bit library it is a 32-bit unit. Unlike a dot, \C always matches
- line-ending characters. The feature is provided in Perl in order to
+ Outside a character class, the escape sequence \C matches any one data
+ unit, whether or not a UTF mode is set. In the 8-bit library, one data
+ unit is one byte; in the 16-bit library it is a 16-bit unit; in the
+ 32-bit library it is a 32-bit unit. Unlike a dot, \C always matches
+ line-ending characters. The feature is provided in Perl in order to
match individual bytes in UTF-8 mode, but it is unclear how it can use-
- fully be used. Because \C breaks up characters into individual data
- units, matching one unit with \C in a UTF mode means that the rest of
+ fully be used. Because \C breaks up characters into individual data
+ units, matching one unit with \C in a UTF mode means that the rest of
the string may start with a malformed UTF character. This has undefined
results, because PCRE assumes that it is dealing with valid UTF strings
- (and by default it checks this at the start of processing unless the
- PCRE_NO_UTF8_CHECK, PCRE_NO_UTF16_CHECK or PCRE_NO_UTF32_CHECK option
+ (and by default it checks this at the start of processing unless the
+ PCRE_NO_UTF8_CHECK, PCRE_NO_UTF16_CHECK or PCRE_NO_UTF32_CHECK option
is used).
- PCRE does not allow \C to appear in lookbehind assertions (described
- below) in a UTF mode, because this would make it impossible to calcu-
+ PCRE does not allow \C to appear in lookbehind assertions (described
+ below) in a UTF mode, because this would make it impossible to calcu-
late the length of the lookbehind.
In general, the \C escape sequence is best avoided. However, one way of
- using it that avoids the problem of malformed UTF characters is to use
- a lookahead to check the length of the next character, as in this pat-
- tern, which could be used with a UTF-8 string (ignore white space and
+ using it that avoids the problem of malformed UTF characters is to use
+ a lookahead to check the length of the next character, as in this pat-
+ tern, which could be used with a UTF-8 string (ignore white space and
line breaks):
(?| (?=[\x00-\x7f])(\C) |
@@ -5407,11 +5690,11 @@ MATCHING A SINGLE DATA UNIT
(?=[\x{800}-\x{ffff}])(\C)(\C)(\C) |
(?=[\x{10000}-\x{1fffff}])(\C)(\C)(\C)(\C))
- A group that starts with (?| resets the capturing parentheses numbers
- in each alternative (see "Duplicate Subpattern Numbers" below). The
- assertions at the start of each branch check the next UTF-8 character
- for values whose encoding uses 1, 2, 3, or 4 bytes, respectively. The
- character's individual bytes are then captured by the appropriate num-
+ A group that starts with (?| resets the capturing parentheses numbers
+ in each alternative (see "Duplicate Subpattern Numbers" below). The
+ assertions at the start of each branch check the next UTF-8 character
+ for values whose encoding uses 1, 2, 3, or 4 bytes, respectively. The
+ character's individual bytes are then captured by the appropriate num-
ber of groups.
@@ -5421,64 +5704,71 @@ SQUARE BRACKETS AND CHARACTER CLASSES
closing square bracket. A closing square bracket on its own is not spe-
cial by default. However, if the PCRE_JAVASCRIPT_COMPAT option is set,
a lone closing square bracket causes a compile-time error. If a closing
- square bracket is required as a member of the class, it should be the
- first data character in the class (after an initial circumflex, if
+ square bracket is required as a member of the class, it should be the
+ first data character in the class (after an initial circumflex, if
present) or escaped with a backslash.
- A character class matches a single character in the subject. In a UTF
- mode, the character may be more than one data unit long. A matched
+ A character class matches a single character in the subject. In a UTF
+ mode, the character may be more than one data unit long. A matched
character must be in the set of characters defined by the class, unless
- the first character in the class definition is a circumflex, in which
+ the first character in the class definition is a circumflex, in which
case the subject character must not be in the set defined by the class.
- If a circumflex is actually required as a member of the class, ensure
+ If a circumflex is actually required as a member of the class, ensure
it is not the first character, or escape it with a backslash.
- For example, the character class [aeiou] matches any lower case vowel,
- while [^aeiou] matches any character that is not a lower case vowel.
+ For example, the character class [aeiou] matches any lower case vowel,
+ while [^aeiou] matches any character that is not a lower case vowel.
Note that a circumflex is just a convenient notation for specifying the
- characters that are in the class by enumerating those that are not. A
- class that starts with a circumflex is not an assertion; it still con-
- sumes a character from the subject string, and therefore it fails if
+ characters that are in the class by enumerating those that are not. A
+ class that starts with a circumflex is not an assertion; it still con-
+ sumes a character from the subject string, and therefore it fails if
the current pointer is at the end of the string.
In UTF-8 (UTF-16, UTF-32) mode, characters with values greater than 255
- (0xffff) can be included in a class as a literal string of data units,
+ (0xffff) can be included in a class as a literal string of data units,
or by using the \x{ escaping mechanism.
- When caseless matching is set, any letters in a class represent both
- their upper case and lower case versions, so for example, a caseless
- [aeiou] matches "A" as well as "a", and a caseless [^aeiou] does not
- match "A", whereas a caseful version would. In a UTF mode, PCRE always
- understands the concept of case for characters whose values are less
- than 128, so caseless matching is always possible. For characters with
- higher values, the concept of case is supported if PCRE is compiled
- with Unicode property support, but not otherwise. If you want to use
- caseless matching in a UTF mode for characters 128 and above, you must
- ensure that PCRE is compiled with Unicode property support as well as
+ When caseless matching is set, any letters in a class represent both
+ their upper case and lower case versions, so for example, a caseless
+ [aeiou] matches "A" as well as "a", and a caseless [^aeiou] does not
+ match "A", whereas a caseful version would. In a UTF mode, PCRE always
+ understands the concept of case for characters whose values are less
+ than 128, so caseless matching is always possible. For characters with
+ higher values, the concept of case is supported if PCRE is compiled
+ with Unicode property support, but not otherwise. If you want to use
+ caseless matching in a UTF mode for characters 128 and above, you must
+ ensure that PCRE is compiled with Unicode property support as well as
with UTF support.
- Characters that might indicate line breaks are never treated in any
- special way when matching character classes, whatever line-ending
- sequence is in use, and whatever setting of the PCRE_DOTALL and
+ Characters that might indicate line breaks are never treated in any
+ special way when matching character classes, whatever line-ending
+ sequence is in use, and whatever setting of the PCRE_DOTALL and
PCRE_MULTILINE options is used. A class such as [^a] always matches one
of these characters.
- The minus (hyphen) character can be used to specify a range of charac-
- ters in a character class. For example, [d-m] matches any letter
- between d and m, inclusive. If a minus character is required in a
- class, it must be escaped with a backslash or appear in a position
- where it cannot be interpreted as indicating a range, typically as the
- first or last character in the class.
+ The minus (hyphen) character can be used to specify a range of charac-
+ ters in a character class. For example, [d-m] matches any letter
+ between d and m, inclusive. If a minus character is required in a
+ class, it must be escaped with a backslash or appear in a position
+ where it cannot be interpreted as indicating a range, typically as the
+ first or last character in the class, or immediately after a range. For
+ example, [b-d-z] matches letters in the range b to d, a hyphen charac-
+ ter, or z.
It is not possible to have the literal character "]" as the end charac-
- ter of a range. A pattern such as [W-]46] is interpreted as a class of
- two characters ("W" and "-") followed by a literal string "46]", so it
- would match "W46]" or "-46]". However, if the "]" is escaped with a
- backslash it is interpreted as the end of range, so [W-\]46] is inter-
- preted as a class containing a range followed by two other characters.
- The octal or hexadecimal representation of "]" can also be used to end
+ ter of a range. A pattern such as [W-]46] is interpreted as a class of
+ two characters ("W" and "-") followed by a literal string "46]", so it
+ would match "W46]" or "-46]". However, if the "]" is escaped with a
+ backslash it is interpreted as the end of range, so [W-\]46] is inter-
+ preted as a class containing a range followed by two other characters.
+ The octal or hexadecimal representation of "]" can also be used to end
a range.
+ An error is generated if a POSIX character class (see below) or an
+ escape sequence other than one that defines a single character appears
+ at a point where a range ending character is expected. For example,
+ [z-\xff] is valid, but [A-\d] and [A-[:digit:]] are not.
+
Ranges operate in the collating sequence of character values. They can
also be used for characters specified numerically, for example
[\000-\037]. Ranges can include any characters that are valid for the
@@ -5515,15 +5805,16 @@ SQUARE BRACKETS AND CHARACTER CLASSES
The only metacharacters that are recognized in character classes are
backslash, hyphen (only where it can be interpreted as specifying a
range), circumflex (only at the start), opening square bracket (only
- when it can be interpreted as introducing a POSIX class name - see the
- next section), and the terminating closing square bracket. However,
- escaping other non-alphanumeric characters does no harm.
+ when it can be interpreted as introducing a POSIX class name, or for a
+ special compatibility feature - see the next two sections), and the
+ terminating closing square bracket. However, escaping other non-
+ alphanumeric characters does no harm.
POSIX CHARACTER CLASSES
Perl supports the POSIX notation for character classes. This uses names
- enclosed by [: and :] within the enclosing square brackets. PCRE also
+ enclosed by [: and :] within the enclosing square brackets. PCRE also
supports this notation. For example,
[01[:alpha:]%]
@@ -5541,15 +5832,18 @@ POSIX CHARACTER CLASSES
lower lower case letters
print printing characters, including space
punct printing characters, excluding letters and digits and space
- space white space (not quite the same as \s)
+ space white space (the same as \s from PCRE 8.34)
upper upper case letters
word "word" characters (same as \w)
xdigit hexadecimal digits
- The "space" characters are HT (9), LF (10), VT (11), FF (12), CR (13),
- and space (32). Notice that this list includes the VT character (code
- 11). This makes "space" different to \s, which does not include VT (for
- Perl compatibility).
+ The default "space" characters are HT (9), LF (10), VT (11), FF (12),
+ CR (13), and space (32). If locale-specific matching is taking place,
+ the list of space characters may be different; there may be fewer or
+ more of them. "Space" used to be different to \s, which did not include
+ VT, for Perl compatibility. However, Perl changed at release 5.18, and
+ PCRE followed at release 8.34. "Space" and \s now match the same set
+ of characters.
The name "word" is a Perl extension, and "blank" is a GNU extension
from Perl 5.8. Another Perl extension is negation, which is indicated
@@ -5561,11 +5855,11 @@ POSIX CHARACTER CLASSES
POSIX syntax [.ch.] and [=ch=] where "ch" is a "collating element", but
these are not supported, and an error is given if they are encountered.
- By default, in UTF modes, characters with values greater than 128 do
- not match any of the POSIX character classes. However, if the PCRE_UCP
- option is passed to pcre_compile(), some of the classes are changed so
- that Unicode character properties are used. This is achieved by replac-
- ing the POSIX classes by other sequences, as follows:
+ By default, characters with values greater than 128 do not match any of
+ the POSIX character classes. However, if the PCRE_UCP option is passed
+ to pcre_compile(), some of the classes are changed so that Unicode
+ character properties are used. This is achieved by replacing certain
+ POSIX classes by other sequences, as follows:
[:alnum:] becomes \p{Xan}
[:alpha:] becomes \p{L}
@@ -5576,9 +5870,48 @@ POSIX CHARACTER CLASSES
[:upper:] becomes \p{Lu}
[:word:] becomes \p{Xwd}
- Negated versions, such as [:^alpha:] use \P instead of \p. The other
- POSIX classes are unchanged, and match only characters with code points
- less than 128.
+ Negated versions, such as [:^alpha:] use \P instead of \p. Three other
+ POSIX classes are handled specially in UCP mode:
+
+ [:graph:] This matches characters that have glyphs that mark the page
+ when printed. In Unicode property terms, it matches all char-
+ acters with the L, M, N, P, S, or Cf properties, except for:
+
+ U+061C Arabic Letter Mark
+ U+180E Mongolian Vowel Separator
+ U+2066 - U+2069 Various "isolate"s
+
+
+ [:print:] This matches the same characters as [:graph:] plus space
+ characters that are not controls, that is, characters with
+ the Zs property.
+
+ [:punct:] This matches all characters that have the Unicode P (punctua-
+ tion) property, plus those characters whose code points are
+ less than 128 that have the S (Symbol) property.
+
+ The other POSIX classes are unchanged, and match only characters with
+ code points less than 128.
+
+
+COMPATIBILITY FEATURE FOR WORD BOUNDARIES
+
+ In the POSIX.2 compliant library that was included in 4.4BSD Unix, the
+ ugly syntax [[:<:]] and [[:>:]] is used for matching "start of word"
+ and "end of word". PCRE treats these items as follows:
+
+ [[:<:]] is converted to \b(?=\w)
+ [[:>:]] is converted to \b(?<=\w)
+
+ Only these exact character sequences are recognized. A sequence such as
+ [a[:<:]b] provokes error for an unrecognized POSIX class name. This
+ support is not compatible with Perl. It is provided to help migrations
+ from other environments, and is best not used in any new patterns. Note
+ that \b matches at the start and the end of a word (see "Simple asser-
+ tions" above), and in a Perl-style pattern the preceding or following
+ character normally shows which is wanted, without the need for the
+ assertions that are used above in order to give exactly the POSIX be-
+ haviour.
VERTICAL BAR
@@ -5653,7 +5986,9 @@ INTERNAL OPTION SETTING
(*UCP) leading sequences that can be used to set UTF and Unicode prop-
erty modes; they are equivalent to setting the PCRE_UTF8, PCRE_UTF16,
PCRE_UTF32 and the PCRE_UCP options, respectively. The (*UTF) sequence
- is a generic version that can be used with any of the libraries.
+ is a generic version that can be used with any of the libraries. How-
+ ever, the application can set the PCRE_NEVER_UTF option, which locks
+ out the use of the (*UTF) sequences.
SUBPATTERNS
@@ -5773,12 +6108,12 @@ NAMED SUBPATTERNS
references, recursion, and conditions, can be made by name as well as
by number.
- Names consist of up to 32 alphanumeric characters and underscores.
- Named capturing parentheses are still allocated numbers as well as
- names, exactly as if the names were not present. The PCRE API provides
- function calls for extracting the name-to-number translation table from
- a compiled pattern. There is also a convenience function for extracting
- a captured substring by name.
+ Names consist of up to 32 alphanumeric characters and underscores, but
+ must start with a non-digit. Named capturing parentheses are still
+ allocated numbers as well as names, exactly as if the names were not
+ present. The PCRE API provides function calls for extracting the name-
+ to-number translation table from a compiled pattern. There is also a
+ convenience function for extracting a captured substring by name.
By default, a name must be unique within a pattern, but it is possible
to relax this constraint by setting the PCRE_DUPNAMES option at compile
@@ -5806,28 +6141,38 @@ NAMED SUBPATTERNS
subpattern it was.
If you make a back reference to a non-unique named subpattern from
- elsewhere in the pattern, the one that corresponds to the first occur-
- rence of the name is used. In the absence of duplicate numbers (see the
- previous section) this is the one with the lowest number. If you use a
- named reference in a condition test (see the section about conditions
- below), either to check whether a subpattern has matched, or to check
- for recursion, all subpatterns with the same name are tested. If the
- condition is true for any one of them, the overall condition is true.
- This is the same behaviour as testing by number. For further details of
- the interfaces for handling named subpatterns, see the pcreapi documen-
- tation.
+ elsewhere in the pattern, the subpatterns to which the name refers are
+ checked in the order in which they appear in the overall pattern. The
+ first one that is set is used for the reference. For example, this pat-
+ tern matches both "foofoo" and "barbar" but not "foobar" or "barfoo":
+
+ (?:(?<n>foo)|(?<n>bar))\k<n>
+
+
+ If you make a subroutine call to a non-unique named subpattern, the one
+ that corresponds to the first occurrence of the name is used. In the
+ absence of duplicate numbers (see the previous section) this is the one
+ with the lowest number.
+
+ If you use a named reference in a condition test (see the section about
+ conditions below), either to check whether a subpattern has matched, or
+ to check for recursion, all subpatterns with the same name are tested.
+ If the condition is true for any one of them, the overall condition is
+ true. This is the same behaviour as testing by number. For further
+ details of the interfaces for handling named subpatterns, see the
+ pcreapi documentation.
Warning: You cannot use different names to distinguish between two sub-
- patterns with the same number because PCRE uses only the numbers when
+ patterns with the same number because PCRE uses only the numbers when
matching. For this reason, an error is given at compile time if differ-
- ent names are given to subpatterns with the same number. However, you
- can give the same name to subpatterns with the same number, even when
- PCRE_DUPNAMES is not set.
+ ent names are given to subpatterns with the same number. However, you
+ can always give the same name to subpatterns with the same number, even
+ when PCRE_DUPNAMES is not set.
REPETITION
- Repetition is specified by quantifiers, which can follow any of the
+ Repetition is specified by quantifiers, which can follow any of the
following items:
a literal data character
@@ -5841,17 +6186,17 @@ REPETITION
a parenthesized subpattern (including assertions)
a subroutine call to a subpattern (recursive or otherwise)
- The general repetition quantifier specifies a minimum and maximum num-
- ber of permitted matches, by giving the two numbers in curly brackets
- (braces), separated by a comma. The numbers must be less than 65536,
+ The general repetition quantifier specifies a minimum and maximum num-
+ ber of permitted matches, by giving the two numbers in curly brackets
+ (braces), separated by a comma. The numbers must be less than 65536,
and the first must be less than or equal to the second. For example:
z{2,4}
- matches "zz", "zzz", or "zzzz". A closing brace on its own is not a
- special character. If the second number is omitted, but the comma is
- present, there is no upper limit; if the second number and the comma
- are both omitted, the quantifier specifies an exact number of required
+ matches "zz", "zzz", or "zzzz". A closing brace on its own is not a
+ special character. If the second number is omitted, but the comma is
+ present, there is no upper limit; if the second number and the comma
+ are both omitted, the quantifier specifies an exact number of required
matches. Thus
[aeiou]{3,}
@@ -5860,50 +6205,50 @@ REPETITION
\d{8}
- matches exactly 8 digits. An opening curly bracket that appears in a
- position where a quantifier is not allowed, or one that does not match
- the syntax of a quantifier, is taken as a literal character. For exam-
+ matches exactly 8 digits. An opening curly bracket that appears in a
+ position where a quantifier is not allowed, or one that does not match
+ the syntax of a quantifier, is taken as a literal character. For exam-
ple, {,6} is not a quantifier, but a literal string of four characters.
In UTF modes, quantifiers apply to characters rather than to individual
- data units. Thus, for example, \x{100}{2} matches two characters, each
+ data units. Thus, for example, \x{100}{2} matches two characters, each
of which is represented by a two-byte sequence in a UTF-8 string. Simi-
- larly, \X{3} matches three Unicode extended grapheme clusters, each of
- which may be several data units long (and they may be of different
+ larly, \X{3} matches three Unicode extended grapheme clusters, each of
+ which may be several data units long (and they may be of different
lengths).
The quantifier {0} is permitted, causing the expression to behave as if
the previous item and the quantifier were not present. This may be use-
- ful for subpatterns that are referenced as subroutines from elsewhere
+ ful for subpatterns that are referenced as subroutines from elsewhere
in the pattern (but see also the section entitled "Defining subpatterns
- for use by reference only" below). Items other than subpatterns that
+ for use by reference only" below). Items other than subpatterns that
have a {0} quantifier are omitted from the compiled pattern.
- For convenience, the three most common quantifiers have single-charac-
+ For convenience, the three most common quantifiers have single-charac-
ter abbreviations:
* is equivalent to {0,}
+ is equivalent to {1,}
? is equivalent to {0,1}
- It is possible to construct infinite loops by following a subpattern
+ It is possible to construct infinite loops by following a subpattern
that can match no characters with a quantifier that has no upper limit,
for example:
(a?)*
Earlier versions of Perl and PCRE used to give an error at compile time
- for such patterns. However, because there are cases where this can be
- useful, such patterns are now accepted, but if any repetition of the
- subpattern does in fact match no characters, the loop is forcibly bro-
+ for such patterns. However, because there are cases where this can be
+ useful, such patterns are now accepted, but if any repetition of the
+ subpattern does in fact match no characters, the loop is forcibly bro-
ken.
- By default, the quantifiers are "greedy", that is, they match as much
- as possible (up to the maximum number of permitted times), without
- causing the rest of the pattern to fail. The classic example of where
+ By default, the quantifiers are "greedy", that is, they match as much
+ as possible (up to the maximum number of permitted times), without
+ causing the rest of the pattern to fail. The classic example of where
this gives problems is in trying to match comments in C programs. These
- appear between /* and */ and within the comment, individual * and /
- characters may appear. An attempt to match C comments by applying the
+ appear between /* and */ and within the comment, individual * and /
+ characters may appear. An attempt to match C comments by applying the
pattern
/\*.*\*/
@@ -5912,19 +6257,19 @@ REPETITION
/* first comment */ not comment /* second comment */
- fails, because it matches the entire string owing to the greediness of
+ fails, because it matches the entire string owing to the greediness of
the .* item.
- However, if a quantifier is followed by a question mark, it ceases to
+ However, if a quantifier is followed by a question mark, it ceases to
be greedy, and instead matches the minimum number of times possible, so
the pattern
/\*.*?\*/
- does the right thing with the C comments. The meaning of the various
- quantifiers is not otherwise changed, just the preferred number of
- matches. Do not confuse this use of question mark with its use as a
- quantifier in its own right. Because it has two uses, it can sometimes
+ does the right thing with the C comments. The meaning of the various
+ quantifiers is not otherwise changed, just the preferred number of
+ matches. Do not confuse this use of question mark with its use as a
+ quantifier in its own right. Because it has two uses, it can sometimes
appear doubled, as in
\d??\d
@@ -5932,45 +6277,45 @@ REPETITION
which matches one digit by preference, but can match two if that is the
only way the rest of the pattern matches.
- If the PCRE_UNGREEDY option is set (an option that is not available in
- Perl), the quantifiers are not greedy by default, but individual ones
- can be made greedy by following them with a question mark. In other
+ If the PCRE_UNGREEDY option is set (an option that is not available in
+ Perl), the quantifiers are not greedy by default, but individual ones
+ can be made greedy by following them with a question mark. In other
words, it inverts the default behaviour.
- When a parenthesized subpattern is quantified with a minimum repeat
- count that is greater than 1 or with a limited maximum, more memory is
- required for the compiled pattern, in proportion to the size of the
+ When a parenthesized subpattern is quantified with a minimum repeat
+ count that is greater than 1 or with a limited maximum, more memory is
+ required for the compiled pattern, in proportion to the size of the
minimum or maximum.
If a pattern starts with .* or .{0,} and the PCRE_DOTALL option (equiv-
- alent to Perl's /s) is set, thus allowing the dot to match newlines,
- the pattern is implicitly anchored, because whatever follows will be
- tried against every character position in the subject string, so there
- is no point in retrying the overall match at any position after the
- first. PCRE normally treats such a pattern as though it were preceded
+ alent to Perl's /s) is set, thus allowing the dot to match newlines,
+ the pattern is implicitly anchored, because whatever follows will be
+ tried against every character position in the subject string, so there
+ is no point in retrying the overall match at any position after the
+ first. PCRE normally treats such a pattern as though it were preceded
by \A.
- In cases where it is known that the subject string contains no new-
- lines, it is worth setting PCRE_DOTALL in order to obtain this opti-
+ In cases where it is known that the subject string contains no new-
+ lines, it is worth setting PCRE_DOTALL in order to obtain this opti-
mization, or alternatively using ^ to indicate anchoring explicitly.
- However, there are some cases where the optimization cannot be used.
+ However, there are some cases where the optimization cannot be used.
When .* is inside capturing parentheses that are the subject of a back
reference elsewhere in the pattern, a match at the start may fail where
a later one succeeds. Consider, for example:
(.*)abc\1
- If the subject is "xyz123abc123" the match point is the fourth charac-
+ If the subject is "xyz123abc123" the match point is the fourth charac-
ter. For this reason, such a pattern is not implicitly anchored.
- Another case where implicit anchoring is not applied is when the lead-
- ing .* is inside an atomic group. Once again, a match at the start may
+ Another case where implicit anchoring is not applied is when the lead-
+ ing .* is inside an atomic group. Once again, a match at the start may
fail where a later one succeeds. Consider this pattern:
(?>.*?a)b
- It matches "ab" in the subject "aab". The use of the backtracking con-
+ It matches "ab" in the subject "aab". The use of the backtracking con-
trol verbs (*PRUNE) and (*SKIP) also disable this optimization.
When a capturing subpattern is repeated, the value captured is the sub-
@@ -5979,8 +6324,8 @@ REPETITION
(tweedle[dume]{3}\s*)+
has matched "tweedledum tweedledee" the value of the captured substring
- is "tweedledee". However, if there are nested capturing subpatterns,
- the corresponding captured values may have been set in previous itera-
+ is "tweedledee". However, if there are nested capturing subpatterns,
+ the corresponding captured values may have been set in previous itera-
tions. For example, after
/(a|(b))+/
@@ -5990,53 +6335,53 @@ REPETITION
ATOMIC GROUPING AND POSSESSIVE QUANTIFIERS
- With both maximizing ("greedy") and minimizing ("ungreedy" or "lazy")
- repetition, failure of what follows normally causes the repeated item
- to be re-evaluated to see if a different number of repeats allows the
- rest of the pattern to match. Sometimes it is useful to prevent this,
- either to change the nature of the match, or to cause it fail earlier
- than it otherwise might, when the author of the pattern knows there is
+ With both maximizing ("greedy") and minimizing ("ungreedy" or "lazy")
+ repetition, failure of what follows normally causes the repeated item
+ to be re-evaluated to see if a different number of repeats allows the
+ rest of the pattern to match. Sometimes it is useful to prevent this,
+ either to change the nature of the match, or to cause it fail earlier
+ than it otherwise might, when the author of the pattern knows there is
no point in carrying on.
- Consider, for example, the pattern \d+foo when applied to the subject
+ Consider, for example, the pattern \d+foo when applied to the subject
line
123456bar
After matching all 6 digits and then failing to match "foo", the normal
- action of the matcher is to try again with only 5 digits matching the
- \d+ item, and then with 4, and so on, before ultimately failing.
- "Atomic grouping" (a term taken from Jeffrey Friedl's book) provides
- the means for specifying that once a subpattern has matched, it is not
+ action of the matcher is to try again with only 5 digits matching the
+ \d+ item, and then with 4, and so on, before ultimately failing.
+ "Atomic grouping" (a term taken from Jeffrey Friedl's book) provides
+ the means for specifying that once a subpattern has matched, it is not
to be re-evaluated in this way.
- If we use atomic grouping for the previous example, the matcher gives
- up immediately on failing to match "foo" the first time. The notation
+ If we use atomic grouping for the previous example, the matcher gives
+ up immediately on failing to match "foo" the first time. The notation
is a kind of special parenthesis, starting with (?> as in this example:
(?>\d+)foo
- This kind of parenthesis "locks up" the part of the pattern it con-
- tains once it has matched, and a failure further into the pattern is
- prevented from backtracking into it. Backtracking past it to previous
+ This kind of parenthesis "locks up" the part of the pattern it con-
+ tains once it has matched, and a failure further into the pattern is
+ prevented from backtracking into it. Backtracking past it to previous
items, however, works as normal.
- An alternative description is that a subpattern of this type matches
- the string of characters that an identical standalone pattern would
+ An alternative description is that a subpattern of this type matches
+ the string of characters that an identical standalone pattern would
match, if anchored at the current point in the subject string.
Atomic grouping subpatterns are not capturing subpatterns. Simple cases
such as the above example can be thought of as a maximizing repeat that
- must swallow everything it can. So, while both \d+ and \d+? are pre-
- pared to adjust the number of digits they match in order to make the
+ must swallow everything it can. So, while both \d+ and \d+? are pre-
+ pared to adjust the number of digits they match in order to make the
rest of the pattern match, (?>\d+) can only match an entire sequence of
digits.
- Atomic groups in general can of course contain arbitrarily complicated
- subpatterns, and can be nested. However, when the subpattern for an
+ Atomic groups in general can of course contain arbitrarily complicated
+ subpatterns, and can be nested. However, when the subpattern for an
atomic group is just a single repeated item, as in the example above, a
- simpler notation, called a "possessive quantifier" can be used. This
- consists of an additional + character following a quantifier. Using
+ simpler notation, called a "possessive quantifier" can be used. This
+ consists of an additional + character following a quantifier. Using
this notation, the previous example can be rewritten as
\d++foo
@@ -6046,45 +6391,45 @@ ATOMIC GROUPING AND POSSESSIVE QUANTIFIERS
(abc|xyz){2,3}+
- Possessive quantifiers are always greedy; the setting of the
+ Possessive quantifiers are always greedy; the setting of the
PCRE_UNGREEDY option is ignored. They are a convenient notation for the
- simpler forms of atomic group. However, there is no difference in the
- meaning of a possessive quantifier and the equivalent atomic group,
- though there may be a performance difference; possessive quantifiers
+ simpler forms of atomic group. However, there is no difference in the
+ meaning of a possessive quantifier and the equivalent atomic group,
+ though there may be a performance difference; possessive quantifiers
should be slightly faster.
- The possessive quantifier syntax is an extension to the Perl 5.8 syn-
- tax. Jeffrey Friedl originated the idea (and the name) in the first
+ The possessive quantifier syntax is an extension to the Perl 5.8 syn-
+ tax. Jeffrey Friedl originated the idea (and the name) in the first
edition of his book. Mike McCloskey liked it, so implemented it when he
- built Sun's Java package, and PCRE copied it from there. It ultimately
+ built Sun's Java package, and PCRE copied it from there. It ultimately
found its way into Perl at release 5.10.
PCRE has an optimization that automatically "possessifies" certain sim-
- ple pattern constructs. For example, the sequence A+B is treated as
- A++B because there is no point in backtracking into a sequence of A's
+ ple pattern constructs. For example, the sequence A+B is treated as
+ A++B because there is no point in backtracking into a sequence of A's
when B must follow.
- When a pattern contains an unlimited repeat inside a subpattern that
- can itself be repeated an unlimited number of times, the use of an
- atomic group is the only way to avoid some failing matches taking a
+ When a pattern contains an unlimited repeat inside a subpattern that
+ can itself be repeated an unlimited number of times, the use of an
+ atomic group is the only way to avoid some failing matches taking a
very long time indeed. The pattern
(\D+|<\d+>)*[!?]
- matches an unlimited number of substrings that either consist of non-
- digits, or digits enclosed in <>, followed by either ! or ?. When it
+ matches an unlimited number of substrings that either consist of non-
+ digits, or digits enclosed in <>, followed by either ! or ?. When it
matches, it runs quickly. However, if it is applied to
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
- it takes a long time before reporting failure. This is because the
- string can be divided between the internal \D+ repeat and the external
- * repeat in a large number of ways, and all have to be tried. (The
- example uses [!?] rather than a single character at the end, because
- both PCRE and Perl have an optimization that allows for fast failure
- when a single character is used. They remember the last single charac-
- ter that is required for a match, and fail early if it is not present
- in the string.) If the pattern is changed so that it uses an atomic
+ it takes a long time before reporting failure. This is because the
+ string can be divided between the internal \D+ repeat and the external
+ * repeat in a large number of ways, and all have to be tried. (The
+ example uses [!?] rather than a single character at the end, because
+ both PCRE and Perl have an optimization that allows for fast failure
+ when a single character is used. They remember the last single charac-
+ ter that is required for a match, and fail early if it is not present
+ in the string.) If the pattern is changed so that it uses an atomic
group, like this:
((?>\D+)|<\d+>)*[!?]
@@ -6096,28 +6441,28 @@ BACK REFERENCES
Outside a character class, a backslash followed by a digit greater than
0 (and possibly further digits) is a back reference to a capturing sub-
- pattern earlier (that is, to its left) in the pattern, provided there
+ pattern earlier (that is, to its left) in the pattern, provided there
have been that many previous capturing left parentheses.
However, if the decimal number following the backslash is less than 10,
- it is always taken as a back reference, and causes an error only if
- there are not that many capturing left parentheses in the entire pat-
- tern. In other words, the parentheses that are referenced need not be
- to the left of the reference for numbers less than 10. A "forward back
- reference" of this type can make sense when a repetition is involved
- and the subpattern to the right has participated in an earlier itera-
+ it is always taken as a back reference, and causes an error only if
+ there are not that many capturing left parentheses in the entire pat-
+ tern. In other words, the parentheses that are referenced need not be
+ to the left of the reference for numbers less than 10. A "forward back
+ reference" of this type can make sense when a repetition is involved
+ and the subpattern to the right has participated in an earlier itera-
tion.
- It is not possible to have a numerical "forward back reference" to a
- subpattern whose number is 10 or more using this syntax because a
- sequence such as \50 is interpreted as a character defined in octal.
+ It is not possible to have a numerical "forward back reference" to a
+ subpattern whose number is 10 or more using this syntax because a
+ sequence such as \50 is interpreted as a character defined in octal.
See the subsection entitled "Non-printing characters" above for further
- details of the handling of digits following a backslash. There is no
- such problem when named parentheses are used. A back reference to any
+ details of the handling of digits following a backslash. There is no
+ such problem when named parentheses are used. A back reference to any
subpattern is possible using named parentheses (see below).
- Another way of avoiding the ambiguity inherent in the use of digits
- following a backslash is to use the \g escape sequence. This escape
+ Another way of avoiding the ambiguity inherent in the use of digits
+ following a backslash is to use the \g escape sequence. This escape
must be followed by an unsigned number or a negative number, optionally
enclosed in braces. These examples are all identical:
@@ -6125,7 +6470,7 @@ BACK REFERENCES
(ring), \g1
(ring), \g{1}
- An unsigned number specifies an absolute reference without the ambigu-
+ An unsigned number specifies an absolute reference without the ambigu-
ity that is present in the older syntax. It is also useful when literal
digits follow the reference. A negative number is a relative reference.
Consider this example:
@@ -6134,33 +6479,33 @@ BACK REFERENCES
The sequence \g{-1} is a reference to the most recently started captur-
ing subpattern before \g, that is, is it equivalent to \2 in this exam-
- ple. Similarly, \g{-2} would be equivalent to \1. The use of relative
- references can be helpful in long patterns, and also in patterns that
- are created by joining together fragments that contain references
+ ple. Similarly, \g{-2} would be equivalent to \1. The use of relative
+ references can be helpful in long patterns, and also in patterns that
+ are created by joining together fragments that contain references
within themselves.
- A back reference matches whatever actually matched the capturing sub-
- pattern in the current subject string, rather than anything matching
+ A back reference matches whatever actually matched the capturing sub-
+ pattern in the current subject string, rather than anything matching
the subpattern itself (see "Subpatterns as subroutines" below for a way
of doing that). So the pattern
(sens|respons)e and \1ibility
- matches "sense and sensibility" and "response and responsibility", but
- not "sense and responsibility". If caseful matching is in force at the
- time of the back reference, the case of letters is relevant. For exam-
+ matches "sense and sensibility" and "response and responsibility", but
+ not "sense and responsibility". If caseful matching is in force at the
+ time of the back reference, the case of letters is relevant. For exam-
ple,
((?i)rah)\s+\1
- matches "rah rah" and "RAH RAH", but not "RAH rah", even though the
+ matches "rah rah" and "RAH RAH", but not "RAH rah", even though the
original capturing subpattern is matched caselessly.
- There are several different ways of writing back references to named
- subpatterns. The .NET syntax \k{name} and the Perl syntax \k<name> or
- \k'name' are supported, as is the Python syntax (?P=name). Perl 5.10's
+ There are several different ways of writing back references to named
+ subpatterns. The .NET syntax \k{name} and the Perl syntax \k<name> or
+ \k'name' are supported, as is the Python syntax (?P=name). Perl 5.10's
unified back reference syntax, in which \g can be used for both numeric
- and named references, is also supported. We could rewrite the above
+ and named references, is also supported. We could rewrite the above
example in any of the following ways:
(?<p1>(?i)rah)\s+\k<p1>
@@ -6168,66 +6513,67 @@ BACK REFERENCES
(?P<p1>(?i)rah)\s+(?P=p1)
(?<p1>(?i)rah)\s+\g{p1}
- A subpattern that is referenced by name may appear in the pattern
+ A subpattern that is referenced by name may appear in the pattern
before or after the reference.
- There may be more than one back reference to the same subpattern. If a
- subpattern has not actually been used in a particular match, any back
+ There may be more than one back reference to the same subpattern. If a
+ subpattern has not actually been used in a particular match, any back
references to it always fail by default. For example, the pattern
(a|(bc))\2
- always fails if it starts to match "a" rather than "bc". However, if
+ always fails if it starts to match "a" rather than "bc". However, if
the PCRE_JAVASCRIPT_COMPAT option is set at compile time, a back refer-
ence to an unset value matches an empty string.
- Because there may be many capturing parentheses in a pattern, all dig-
- its following a backslash are taken as part of a potential back refer-
- ence number. If the pattern continues with a digit character, some
- delimiter must be used to terminate the back reference. If the
- PCRE_EXTENDED option is set, this can be white space. Otherwise, the
+ Because there may be many capturing parentheses in a pattern, all dig-
+ its following a backslash are taken as part of a potential back refer-
+ ence number. If the pattern continues with a digit character, some
+ delimiter must be used to terminate the back reference. If the
+ PCRE_EXTENDED option is set, this can be white space. Otherwise, the
\g{ syntax or an empty comment (see "Comments" below) can be used.
Recursive back references
- A back reference that occurs inside the parentheses to which it refers
- fails when the subpattern is first used, so, for example, (a\1) never
- matches. However, such references can be useful inside repeated sub-
+ A back reference that occurs inside the parentheses to which it refers
+ fails when the subpattern is first used, so, for example, (a\1) never
+ matches. However, such references can be useful inside repeated sub-
patterns. For example, the pattern
(a|b\1)+
matches any number of "a"s and also "aba", "ababbaa" etc. At each iter-
- ation of the subpattern, the back reference matches the character
- string corresponding to the previous iteration. In order for this to
- work, the pattern must be such that the first iteration does not need
- to match the back reference. This can be done using alternation, as in
+ ation of the subpattern, the back reference matches the character
+ string corresponding to the previous iteration. In order for this to
+ work, the pattern must be such that the first iteration does not need
+ to match the back reference. This can be done using alternation, as in
the example above, or by a quantifier with a minimum of zero.
- Back references of this type cause the group that they reference to be
- treated as an atomic group. Once the whole group has been matched, a
- subsequent matching failure cannot cause backtracking into the middle
+ Back references of this type cause the group that they reference to be
+ treated as an atomic group. Once the whole group has been matched, a
+ subsequent matching failure cannot cause backtracking into the middle
of the group.
ASSERTIONS
- An assertion is a test on the characters following or preceding the
- current matching point that does not actually consume any characters.
- The simple assertions coded as \b, \B, \A, \G, \Z, \z, ^ and $ are
+ An assertion is a test on the characters following or preceding the
+ current matching point that does not actually consume any characters.
+ The simple assertions coded as \b, \B, \A, \G, \Z, \z, ^ and $ are
described above.
- More complicated assertions are coded as subpatterns. There are two
- kinds: those that look ahead of the current position in the subject
- string, and those that look behind it. An assertion subpattern is
- matched in the normal way, except that it does not cause the current
+ More complicated assertions are coded as subpatterns. There are two
+ kinds: those that look ahead of the current position in the subject
+ string, and those that look behind it. An assertion subpattern is
+ matched in the normal way, except that it does not cause the current
matching position to be changed.
- Assertion subpatterns are not capturing subpatterns. If such an asser-
- tion contains capturing subpatterns within it, these are counted for
- the purposes of numbering the capturing subpatterns in the whole pat-
- tern. However, substring capturing is carried out only for positive
- assertions, because it does not make sense for negative assertions.
+ Assertion subpatterns are not capturing subpatterns. If such an asser-
+ tion contains capturing subpatterns within it, these are counted for
+ the purposes of numbering the capturing subpatterns in the whole pat-
+ tern. However, substring capturing is carried out only for positive
+ assertions. (Perl sometimes, but not always, does do capturing in nega-
+ tive assertions.)
For compatibility with Perl, assertion subpatterns may be repeated;
though it makes no sense to assert the same thing several times, the
@@ -6456,25 +6802,20 @@ CONDITIONAL SUBPATTERNS
Perl uses the syntax (?(<name>)...) or (?('name')...) to test for a
used subpattern by name. For compatibility with earlier versions of
PCRE, which had this facility before Perl, the syntax (?(name)...) is
- also recognized. However, there is a possible ambiguity with this syn-
- tax, because subpattern names may consist entirely of digits. PCRE
- looks first for a named subpattern; if it cannot find one and the name
- consists entirely of digits, PCRE looks for a subpattern of that num-
- ber, which must be greater than zero. Using subpattern names that con-
- sist entirely of digits is not recommended.
+ also recognized.
Rewriting the above example to use a named subpattern gives this:
(?<OPEN> \( )? [^()]+ (?(<OPEN>) \) )
- If the name used in a condition of this kind is a duplicate, the test
- is applied to all subpatterns of the same name, and is true if any one
+ If the name used in a condition of this kind is a duplicate, the test
+ is applied to all subpatterns of the same name, and is true if any one
of them has matched.
Checking for pattern recursion
If the condition is the string (R), and there is no subpattern with the
- name R, the condition is true if a recursive call to the whole pattern
+ name R, the condition is true if a recursive call to the whole pattern
or any subpattern has been made. If digits or a name preceded by amper-
sand follow the letter R, for example:
@@ -6482,51 +6823,51 @@ CONDITIONAL SUBPATTERNS
the condition is true if the most recent recursion is into a subpattern
whose number or name is given. This condition does not check the entire
- recursion stack. If the name used in a condition of this kind is a
+ recursion stack. If the name used in a condition of this kind is a
duplicate, the test is applied to all subpatterns of the same name, and
is true if any one of them is the most recent recursion.
- At "top level", all these recursion test conditions are false. The
+ At "top level", all these recursion test conditions are false. The
syntax for recursive patterns is described below.
Defining subpatterns for use by reference only
- If the condition is the string (DEFINE), and there is no subpattern
- with the name DEFINE, the condition is always false. In this case,
- there may be only one alternative in the subpattern. It is always
- skipped if control reaches this point in the pattern; the idea of
- DEFINE is that it can be used to define subroutines that can be refer-
- enced from elsewhere. (The use of subroutines is described below.) For
- example, a pattern to match an IPv4 address such as "192.168.23.245"
+ If the condition is the string (DEFINE), and there is no subpattern
+ with the name DEFINE, the condition is always false. In this case,
+ there may be only one alternative in the subpattern. It is always
+ skipped if control reaches this point in the pattern; the idea of
+ DEFINE is that it can be used to define subroutines that can be refer-
+ enced from elsewhere. (The use of subroutines is described below.) For
+ example, a pattern to match an IPv4 address such as "192.168.23.245"
could be written like this (ignore white space and line breaks):
(?(DEFINE) (?<byte> 2[0-4]\d | 25[0-5] | 1\d\d | [1-9]?\d) )
\b (?&byte) (\.(?&byte)){3} \b
- The first part of the pattern is a DEFINE group inside which a another
- group named "byte" is defined. This matches an individual component of
- an IPv4 address (a number less than 256). When matching takes place,
- this part of the pattern is skipped because DEFINE acts like a false
- condition. The rest of the pattern uses references to the named group
- to match the four dot-separated components of an IPv4 address, insist-
+ The first part of the pattern is a DEFINE group inside which a another
+ group named "byte" is defined. This matches an individual component of
+ an IPv4 address (a number less than 256). When matching takes place,
+ this part of the pattern is skipped because DEFINE acts like a false
+ condition. The rest of the pattern uses references to the named group
+ to match the four dot-separated components of an IPv4 address, insist-
ing on a word boundary at each end.
Assertion conditions
- If the condition is not in any of the above formats, it must be an
- assertion. This may be a positive or negative lookahead or lookbehind
- assertion. Consider this pattern, again containing non-significant
+ If the condition is not in any of the above formats, it must be an
+ assertion. This may be a positive or negative lookahead or lookbehind
+ assertion. Consider this pattern, again containing non-significant
white space, and with the two alternatives on the second line:
(?(?=[^a-z]*[a-z])
\d{2}-[a-z]{3}-\d{2} | \d{2}-\d{2}-\d{2} )
- The condition is a positive lookahead assertion that matches an
- optional sequence of non-letters followed by a letter. In other words,
- it tests for the presence of at least one letter in the subject. If a
- letter is found, the subject is matched against the first alternative;
- otherwise it is matched against the second. This pattern matches
- strings in one of the two forms dd-aaa-dd or dd-dd-dd, where aaa are
+ The condition is a positive lookahead assertion that matches an
+ optional sequence of non-letters followed by a letter. In other words,
+ it tests for the presence of at least one letter in the subject. If a
+ letter is found, the subject is matched against the first alternative;
+ otherwise it is matched against the second. This pattern matches
+ strings in one of the two forms dd-aaa-dd or dd-dd-dd, where aaa are
letters and dd are digits.
@@ -6535,41 +6876,41 @@ COMMENTS
There are two ways of including comments in patterns that are processed
by PCRE. In both cases, the start of the comment must not be in a char-
acter class, nor in the middle of any other sequence of related charac-
- ters such as (?: or a subpattern name or number. The characters that
+ ters such as (?: or a subpattern name or number. The characters that
make up a comment play no part in the pattern matching.
- The sequence (?# marks the start of a comment that continues up to the
- next closing parenthesis. Nested parentheses are not permitted. If the
+ The sequence (?# marks the start of a comment that continues up to the
+ next closing parenthesis. Nested parentheses are not permitted. If the
PCRE_EXTENDED option is set, an unescaped # character also introduces a
- comment, which in this case continues to immediately after the next
- newline character or character sequence in the pattern. Which charac-
+ comment, which in this case continues to immediately after the next
+ newline character or character sequence in the pattern. Which charac-
ters are interpreted as newlines is controlled by the options passed to
- a compiling function or by a special sequence at the start of the pat-
+ a compiling function or by a special sequence at the start of the pat-
tern, as described in the section entitled "Newline conventions" above.
Note that the end of this type of comment is a literal newline sequence
- in the pattern; escape sequences that happen to represent a newline do
- not count. For example, consider this pattern when PCRE_EXTENDED is
+ in the pattern; escape sequences that happen to represent a newline do
+ not count. For example, consider this pattern when PCRE_EXTENDED is
set, and the default newline convention is in force:
abc #comment \n still comment
- On encountering the # character, pcre_compile() skips along, looking
- for a newline in the pattern. The sequence \n is still literal at this
- stage, so it does not terminate the comment. Only an actual character
+ On encountering the # character, pcre_compile() skips along, looking
+ for a newline in the pattern. The sequence \n is still literal at this
+ stage, so it does not terminate the comment. Only an actual character
with the code value 0x0a (the default newline) does so.
RECURSIVE PATTERNS
- Consider the problem of matching a string in parentheses, allowing for
- unlimited nested parentheses. Without the use of recursion, the best
- that can be done is to use a pattern that matches up to some fixed
- depth of nesting. It is not possible to handle an arbitrary nesting
+ Consider the problem of matching a string in parentheses, allowing for
+ unlimited nested parentheses. Without the use of recursion, the best
+ that can be done is to use a pattern that matches up to some fixed
+ depth of nesting. It is not possible to handle an arbitrary nesting
depth.
For some time, Perl has provided a facility that allows regular expres-
- sions to recurse (amongst other things). It does this by interpolating
- Perl code in the expression at run time, and the code can refer to the
+ sions to recurse (amongst other things). It does this by interpolating
+ Perl code in the expression at run time, and the code can refer to the
expression itself. A Perl pattern using code interpolation to solve the
parentheses problem can be created like this:
@@ -6579,201 +6920,201 @@ RECURSIVE PATTERNS
refers recursively to the pattern in which it appears.
Obviously, PCRE cannot support the interpolation of Perl code. Instead,
- it supports special syntax for recursion of the entire pattern, and
- also for individual subpattern recursion. After its introduction in
- PCRE and Python, this kind of recursion was subsequently introduced
+ it supports special syntax for recursion of the entire pattern, and
+ also for individual subpattern recursion. After its introduction in
+ PCRE and Python, this kind of recursion was subsequently introduced
into Perl at release 5.10.
- A special item that consists of (? followed by a number greater than
- zero and a closing parenthesis is a recursive subroutine call of the
- subpattern of the given number, provided that it occurs inside that
- subpattern. (If not, it is a non-recursive subroutine call, which is
- described in the next section.) The special item (?R) or (?0) is a
+ A special item that consists of (? followed by a number greater than
+ zero and a closing parenthesis is a recursive subroutine call of the
+ subpattern of the given number, provided that it occurs inside that
+ subpattern. (If not, it is a non-recursive subroutine call, which is
+ described in the next section.) The special item (?R) or (?0) is a
recursive call of the entire regular expression.
- This PCRE pattern solves the nested parentheses problem (assume the
+ This PCRE pattern solves the nested parentheses problem (assume the
PCRE_EXTENDED option is set so that white space is ignored):
\( ( [^()]++ | (?R) )* \)
- First it matches an opening parenthesis. Then it matches any number of
- substrings which can either be a sequence of non-parentheses, or a
- recursive match of the pattern itself (that is, a correctly parenthe-
+ First it matches an opening parenthesis. Then it matches any number of
+ substrings which can either be a sequence of non-parentheses, or a
+ recursive match of the pattern itself (that is, a correctly parenthe-
sized substring). Finally there is a closing parenthesis. Note the use
of a possessive quantifier to avoid backtracking into sequences of non-
parentheses.
- If this were part of a larger pattern, you would not want to recurse
+ If this were part of a larger pattern, you would not want to recurse
the entire pattern, so instead you could use this:
( \( ( [^()]++ | (?1) )* \) )
- We have put the pattern into parentheses, and caused the recursion to
+ We have put the pattern into parentheses, and caused the recursion to
refer to them instead of the whole pattern.
- In a larger pattern, keeping track of parenthesis numbers can be
- tricky. This is made easier by the use of relative references. Instead
+ In a larger pattern, keeping track of parenthesis numbers can be
+ tricky. This is made easier by the use of relative references. Instead
of (?1) in the pattern above you can write (?-2) to refer to the second
- most recently opened parentheses preceding the recursion. In other
- words, a negative number counts capturing parentheses leftwards from
+ most recently opened parentheses preceding the recursion. In other
+ words, a negative number counts capturing parentheses leftwards from
the point at which it is encountered.
- It is also possible to refer to subsequently opened parentheses, by
- writing references such as (?+2). However, these cannot be recursive
- because the reference is not inside the parentheses that are refer-
- enced. They are always non-recursive subroutine calls, as described in
+ It is also possible to refer to subsequently opened parentheses, by
+ writing references such as (?+2). However, these cannot be recursive
+ because the reference is not inside the parentheses that are refer-
+ enced. They are always non-recursive subroutine calls, as described in
the next section.
- An alternative approach is to use named parentheses instead. The Perl
- syntax for this is (?&name); PCRE's earlier syntax (?P>name) is also
+ An alternative approach is to use named parentheses instead. The Perl
+ syntax for this is (?&name); PCRE's earlier syntax (?P>name) is also
supported. We could rewrite the above example as follows:
(?<pn> \( ( [^()]++ | (?&pn) )* \) )
- If there is more than one subpattern with the same name, the earliest
+ If there is more than one subpattern with the same name, the earliest
one is used.
- This particular example pattern that we have been looking at contains
+ This particular example pattern that we have been looking at contains
nested unlimited repeats, and so the use of a possessive quantifier for
matching strings of non-parentheses is important when applying the pat-
- tern to strings that do not match. For example, when this pattern is
+ tern to strings that do not match. For example, when this pattern is
applied to
(aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa()
- it yields "no match" quickly. However, if a possessive quantifier is
- not used, the match runs for a very long time indeed because there are
- so many different ways the + and * repeats can carve up the subject,
+ it yields "no match" quickly. However, if a possessive quantifier is
+ not used, the match runs for a very long time indeed because there are
+ so many different ways the + and * repeats can carve up the subject,
and all have to be tested before failure can be reported.
- At the end of a match, the values of capturing parentheses are those
- from the outermost level. If you want to obtain intermediate values, a
- callout function can be used (see below and the pcrecallout documenta-
+ At the end of a match, the values of capturing parentheses are those
+ from the outermost level. If you want to obtain intermediate values, a
+ callout function can be used (see below and the pcrecallout documenta-
tion). If the pattern above is matched against
(ab(cd)ef)
- the value for the inner capturing parentheses (numbered 2) is "ef",
- which is the last value taken on at the top level. If a capturing sub-
- pattern is not matched at the top level, its final captured value is
- unset, even if it was (temporarily) set at a deeper level during the
+ the value for the inner capturing parentheses (numbered 2) is "ef",
+ which is the last value taken on at the top level. If a capturing sub-
+ pattern is not matched at the top level, its final captured value is
+ unset, even if it was (temporarily) set at a deeper level during the
matching process.
- If there are more than 15 capturing parentheses in a pattern, PCRE has
- to obtain extra memory to store data during a recursion, which it does
+ If there are more than 15 capturing parentheses in a pattern, PCRE has
+ to obtain extra memory to store data during a recursion, which it does
by using pcre_malloc, freeing it via pcre_free afterwards. If no memory
can be obtained, the match fails with the PCRE_ERROR_NOMEMORY error.
- Do not confuse the (?R) item with the condition (R), which tests for
- recursion. Consider this pattern, which matches text in angle brack-
- ets, allowing for arbitrary nesting. Only digits are allowed in nested
- brackets (that is, when recursing), whereas any characters are permit-
+ Do not confuse the (?R) item with the condition (R), which tests for
+ recursion. Consider this pattern, which matches text in angle brack-
+ ets, allowing for arbitrary nesting. Only digits are allowed in nested
+ brackets (that is, when recursing), whereas any characters are permit-
ted at the outer level.
< (?: (?(R) \d++ | [^<>]*+) | (?R)) * >
- In this pattern, (?(R) is the start of a conditional subpattern, with
- two different alternatives for the recursive and non-recursive cases.
+ In this pattern, (?(R) is the start of a conditional subpattern, with
+ two different alternatives for the recursive and non-recursive cases.
The (?R) item is the actual recursive call.
Differences in recursion processing between PCRE and Perl
- Recursion processing in PCRE differs from Perl in two important ways.
- In PCRE (like Python, but unlike Perl), a recursive subpattern call is
+ Recursion processing in PCRE differs from Perl in two important ways.
+ In PCRE (like Python, but unlike Perl), a recursive subpattern call is
always treated as an atomic group. That is, once it has matched some of
the subject string, it is never re-entered, even if it contains untried
- alternatives and there is a subsequent matching failure. This can be
- illustrated by the following pattern, which purports to match a palin-
- dromic string that contains an odd number of characters (for example,
+ alternatives and there is a subsequent matching failure. This can be
+ illustrated by the following pattern, which purports to match a palin-
+ dromic string that contains an odd number of characters (for example,
"a", "aba", "abcba", "abcdcba"):
^(.|(.)(?1)\2)$
The idea is that it either matches a single character, or two identical
- characters surrounding a sub-palindrome. In Perl, this pattern works;
- in PCRE it does not if the pattern is longer than three characters.
+ characters surrounding a sub-palindrome. In Perl, this pattern works;
+ in PCRE it does not if the pattern is longer than three characters.
Consider the subject string "abcba":
- At the top level, the first character is matched, but as it is not at
+ At the top level, the first character is matched, but as it is not at
the end of the string, the first alternative fails; the second alterna-
tive is taken and the recursion kicks in. The recursive call to subpat-
- tern 1 successfully matches the next character ("b"). (Note that the
+ tern 1 successfully matches the next character ("b"). (Note that the
beginning and end of line tests are not part of the recursion).
- Back at the top level, the next character ("c") is compared with what
- subpattern 2 matched, which was "a". This fails. Because the recursion
- is treated as an atomic group, there are now no backtracking points,
- and so the entire match fails. (Perl is able, at this point, to re-
- enter the recursion and try the second alternative.) However, if the
+ Back at the top level, the next character ("c") is compared with what
+ subpattern 2 matched, which was "a". This fails. Because the recursion
+ is treated as an atomic group, there are now no backtracking points,
+ and so the entire match fails. (Perl is able, at this point, to re-
+ enter the recursion and try the second alternative.) However, if the
pattern is written with the alternatives in the other order, things are
different:
^((.)(?1)\2|.)$
- This time, the recursing alternative is tried first, and continues to
- recurse until it runs out of characters, at which point the recursion
- fails. But this time we do have another alternative to try at the
- higher level. That is the big difference: in the previous case the
+ This time, the recursing alternative is tried first, and continues to
+ recurse until it runs out of characters, at which point the recursion
+ fails. But this time we do have another alternative to try at the
+ higher level. That is the big difference: in the previous case the
remaining alternative is at a deeper recursion level, which PCRE cannot
use.
- To change the pattern so that it matches all palindromic strings, not
- just those with an odd number of characters, it is tempting to change
+ To change the pattern so that it matches all palindromic strings, not
+ just those with an odd number of characters, it is tempting to change
the pattern to this:
^((.)(?1)\2|.?)$
- Again, this works in Perl, but not in PCRE, and for the same reason.
- When a deeper recursion has matched a single character, it cannot be
- entered again in order to match an empty string. The solution is to
- separate the two cases, and write out the odd and even cases as alter-
+ Again, this works in Perl, but not in PCRE, and for the same reason.
+ When a deeper recursion has matched a single character, it cannot be
+ entered again in order to match an empty string. The solution is to
+ separate the two cases, and write out the odd and even cases as alter-
natives at the higher level:
^(?:((.)(?1)\2|)|((.)(?3)\4|.))
- If you want to match typical palindromic phrases, the pattern has to
+ If you want to match typical palindromic phrases, the pattern has to
ignore all non-word characters, which can be done like this:
^\W*+(?:((.)\W*+(?1)\W*+\2|)|((.)\W*+(?3)\W*+\4|\W*+.\W*+))\W*+$
If run with the PCRE_CASELESS option, this pattern matches phrases such
as "A man, a plan, a canal: Panama!" and it works well in both PCRE and
- Perl. Note the use of the possessive quantifier *+ to avoid backtrack-
- ing into sequences of non-word characters. Without this, PCRE takes a
- great deal longer (ten times or more) to match typical phrases, and
+ Perl. Note the use of the possessive quantifier *+ to avoid backtrack-
+ ing into sequences of non-word characters. Without this, PCRE takes a
+ great deal longer (ten times or more) to match typical phrases, and
Perl takes so long that you think it has gone into a loop.
- WARNING: The palindrome-matching patterns above work only if the sub-
- ject string does not start with a palindrome that is shorter than the
- entire string. For example, although "abcba" is correctly matched, if
- the subject is "ababa", PCRE finds the palindrome "aba" at the start,
- then fails at top level because the end of the string does not follow.
- Once again, it cannot jump back into the recursion to try other alter-
+ WARNING: The palindrome-matching patterns above work only if the sub-
+ ject string does not start with a palindrome that is shorter than the
+ entire string. For example, although "abcba" is correctly matched, if
+ the subject is "ababa", PCRE finds the palindrome "aba" at the start,
+ then fails at top level because the end of the string does not follow.
+ Once again, it cannot jump back into the recursion to try other alter-
natives, so the entire match fails.
- The second way in which PCRE and Perl differ in their recursion pro-
- cessing is in the handling of captured values. In Perl, when a subpat-
- tern is called recursively or as a subpattern (see the next section),
- it has no access to any values that were captured outside the recur-
- sion, whereas in PCRE these values can be referenced. Consider this
+ The second way in which PCRE and Perl differ in their recursion pro-
+ cessing is in the handling of captured values. In Perl, when a subpat-
+ tern is called recursively or as a subpattern (see the next section),
+ it has no access to any values that were captured outside the recur-
+ sion, whereas in PCRE these values can be referenced. Consider this
pattern:
^(.)(\1|a(?2))
- In PCRE, this pattern matches "bab". The first capturing parentheses
- match "b", then in the second group, when the back reference \1 fails
- to match "b", the second alternative matches "a" and then recurses. In
- the recursion, \1 does now match "b" and so the whole match succeeds.
- In Perl, the pattern fails to match because inside the recursive call
+ In PCRE, this pattern matches "bab". The first capturing parentheses
+ match "b", then in the second group, when the back reference \1 fails
+ to match "b", the second alternative matches "a" and then recurses. In
+ the recursion, \1 does now match "b" and so the whole match succeeds.
+ In Perl, the pattern fails to match because inside the recursive call
\1 cannot access the externally set value.
SUBPATTERNS AS SUBROUTINES
- If the syntax for a recursive subpattern call (either by number or by
- name) is used outside the parentheses to which it refers, it operates
- like a subroutine in a programming language. The called subpattern may
- be defined before or after the reference. A numbered reference can be
+ If the syntax for a recursive subpattern call (either by number or by
+ name) is used outside the parentheses to which it refers, it operates
+ like a subroutine in a programming language. The called subpattern may
+ be defined before or after the reference. A numbered reference can be
absolute or relative, as in these examples:
(...(absolute)...)...(?2)...
@@ -6784,190 +7125,203 @@ SUBPATTERNS AS SUBROUTINES
(sens|respons)e and \1ibility
- matches "sense and sensibility" and "response and responsibility", but
+ matches "sense and sensibility" and "response and responsibility", but
not "sense and responsibility". If instead the pattern
(sens|respons)e and (?1)ibility
- is used, it does match "sense and responsibility" as well as the other
- two strings. Another example is given in the discussion of DEFINE
+ is used, it does match "sense and responsibility" as well as the other
+ two strings. Another example is given in the discussion of DEFINE
above.
- All subroutine calls, whether recursive or not, are always treated as
- atomic groups. That is, once a subroutine has matched some of the sub-
+ All subroutine calls, whether recursive or not, are always treated as
+ atomic groups. That is, once a subroutine has matched some of the sub-
ject string, it is never re-entered, even if it contains untried alter-
- natives and there is a subsequent matching failure. Any capturing
- parentheses that are set during the subroutine call revert to their
+ natives and there is a subsequent matching failure. Any capturing
+ parentheses that are set during the subroutine call revert to their
previous values afterwards.
- Processing options such as case-independence are fixed when a subpat-
- tern is defined, so if it is used as a subroutine, such options cannot
+ Processing options such as case-independence are fixed when a subpat-
+ tern is defined, so if it is used as a subroutine, such options cannot
be changed for different calls. For example, consider this pattern:
(abc)(?i:(?-1))
- It matches "abcabc". It does not match "abcABC" because the change of
+ It matches "abcabc". It does not match "abcABC" because the change of
processing option does not affect the called subpattern.
ONIGURUMA SUBROUTINE SYNTAX
- For compatibility with Oniguruma, the non-Perl syntax \g followed by a
+ For compatibility with Oniguruma, the non-Perl syntax \g followed by a
name or a number enclosed either in angle brackets or single quotes, is
- an alternative syntax for referencing a subpattern as a subroutine,
- possibly recursively. Here are two of the examples used above, rewrit-
+ an alternative syntax for referencing a subpattern as a subroutine,
+ possibly recursively. Here are two of the examples used above, rewrit-
ten using this syntax:
(?<pn> \( ( (?>[^()]+) | \g<pn> )* \) )
(sens|respons)e and \g'1'ibility
- PCRE supports an extension to Oniguruma: if a number is preceded by a
+ PCRE supports an extension to Oniguruma: if a number is preceded by a
plus or a minus sign it is taken as a relative reference. For example:
(abc)(?i:\g<-1>)
- Note that \g{...} (Perl syntax) and \g<...> (Oniguruma syntax) are not
- synonymous. The former is a back reference; the latter is a subroutine
+ Note that \g{...} (Perl syntax) and \g<...> (Oniguruma syntax) are not
+ synonymous. The former is a back reference; the latter is a subroutine
call.
CALLOUTS
Perl has a feature whereby using the sequence (?{...}) causes arbitrary
- Perl code to be obeyed in the middle of matching a regular expression.
+ Perl code to be obeyed in the middle of matching a regular expression.
This makes it possible, amongst other things, to extract different sub-
strings that match the same pair of parentheses when there is a repeti-
tion.
PCRE provides a similar feature, but of course it cannot obey arbitrary
Perl code. The feature is called "callout". The caller of PCRE provides
- an external function by putting its entry point in the global variable
- pcre_callout (8-bit library) or pcre[16|32]_callout (16-bit or 32-bit
- library). By default, this variable contains NULL, which disables all
+ an external function by putting its entry point in the global variable
+ pcre_callout (8-bit library) or pcre[16|32]_callout (16-bit or 32-bit
+ library). By default, this variable contains NULL, which disables all
calling out.
- Within a regular expression, (?C) indicates the points at which the
- external function is to be called. If you want to identify different
- callout points, you can put a number less than 256 after the letter C.
- The default value is zero. For example, this pattern has two callout
+ Within a regular expression, (?C) indicates the points at which the
+ external function is to be called. If you want to identify different
+ callout points, you can put a number less than 256 after the letter C.
+ The default value is zero. For example, this pattern has two callout
points:
(?C1)abc(?C2)def
- If the PCRE_AUTO_CALLOUT flag is passed to a compiling function, call-
- outs are automatically installed before each item in the pattern. They
- are all numbered 255.
+ If the PCRE_AUTO_CALLOUT flag is passed to a compiling function, call-
+ outs are automatically installed before each item in the pattern. They
+ are all numbered 255. If there is a conditional group in the pattern
+ whose condition is an assertion, an additional callout is inserted just
+ before the condition. An explicit callout may also be set at this posi-
+ tion, as in this example:
+
+ (?(?C9)(?=a)abc|def)
+
+ Note that this applies only to assertion conditions, not to other types
+ of condition.
- During matching, when PCRE reaches a callout point, the external func-
- tion is called. It is provided with the number of the callout, the
- position in the pattern, and, optionally, one item of data originally
- supplied by the caller of the matching function. The callout function
- may cause matching to proceed, to backtrack, or to fail altogether. A
- complete description of the interface to the callout function is given
- in the pcrecallout documentation.
+ During matching, when PCRE reaches a callout point, the external func-
+ tion is called. It is provided with the number of the callout, the
+ position in the pattern, and, optionally, one item of data originally
+ supplied by the caller of the matching function. The callout function
+ may cause matching to proceed, to backtrack, or to fail altogether.
+
+ By default, PCRE implements a number of optimizations at compile time
+ and matching time, and one side-effect is that sometimes callouts are
+ skipped. If you need all possible callouts to happen, you need to set
+ options that disable the relevant optimizations. More details, and a
+ complete description of the interface to the callout function, are
+ given in the pcrecallout documentation.
BACKTRACKING CONTROL
Perl 5.10 introduced a number of "Special Backtracking Control Verbs",
- which are described in the Perl documentation as "experimental and sub-
- ject to change or removal in a future version of Perl". It goes on to
- say: "Their usage in production code should be noted to avoid problems
- during upgrades." The same remarks apply to the PCRE features described
- in this section.
-
- Since these verbs are specifically related to backtracking, most of
- them can be used only when the pattern is to be matched using one of
- the traditional matching functions, which use a backtracking algorithm.
- With the exception of (*FAIL), which behaves like a failing negative
- assertion, they cause an error if encountered by a DFA matching func-
- tion.
+ which are still described in the Perl documentation as "experimental
+ and subject to change or removal in a future version of Perl". It goes
+ on to say: "Their usage in production code should be noted to avoid
+ problems during upgrades." The same remarks apply to the PCRE features
+ described in this section.
- If any of these verbs are used in an assertion or in a subpattern that
- is called as a subroutine (whether or not recursively), their effect is
- confined to that subpattern; it does not extend to the surrounding pat-
- tern, with one exception: the name from a *(MARK), (*PRUNE), or (*THEN)
- that is encountered in a successful positive assertion is passed back
- when a match succeeds (compare capturing parentheses in assertions).
- Note that such subpatterns are processed as anchored at the point where
- they are tested. Note also that Perl's treatment of subroutines and
- assertions is different in some cases.
-
- The new verbs make use of what was previously invalid syntax: an open-
+ The new verbs make use of what was previously invalid syntax: an open-
ing parenthesis followed by an asterisk. They are generally of the form
- (*VERB) or (*VERB:NAME). Some may take either form, with differing be-
- haviour, depending on whether or not an argument is present. A name is
+ (*VERB) or (*VERB:NAME). Some may take either form, possibly behaving
+ differently depending on whether or not a name is present. A name is
any sequence of characters that does not include a closing parenthesis.
The maximum length of name is 255 in the 8-bit library and 65535 in the
- 16-bit and 32-bit library. If the name is empty, that is, if the clos-
- ing parenthesis immediately follows the colon, the effect is as if the
- colon were not there. Any number of these verbs may occur in a pattern.
+ 16-bit and 32-bit libraries. If the name is empty, that is, if the
+ closing parenthesis immediately follows the colon, the effect is as if
+ the colon were not there. Any number of these verbs may occur in a
+ pattern.
+
+ Since these verbs are specifically related to backtracking, most of
+ them can be used only when the pattern is to be matched using one of
+ the traditional matching functions, because these use a backtracking
+ algorithm. With the exception of (*FAIL), which behaves like a failing
+ negative assertion, the backtracking control verbs cause an error if
+ encountered by a DFA matching function.
+
+ The behaviour of these verbs in repeated groups, assertions, and in
+ subpatterns called as subroutines (whether or not recursively) is docu-
+ mented below.
Optimizations that affect backtracking verbs
- PCRE contains some optimizations that are used to speed up matching by
+ PCRE contains some optimizations that are used to speed up matching by
running some checks at the start of each match attempt. For example, it
- may know the minimum length of matching subject, or that a particular
- character must be present. When one of these optimizations suppresses
- the running of a match, any included backtracking verbs will not, of
+ may know the minimum length of matching subject, or that a particular
+ character must be present. When one of these optimizations bypasses the
+ running of a match, any included backtracking verbs will not, of
course, be processed. You can suppress the start-of-match optimizations
- by setting the PCRE_NO_START_OPTIMIZE option when calling pcre_com-
+ by setting the PCRE_NO_START_OPTIMIZE option when calling pcre_com-
pile() or pcre_exec(), or by starting the pattern with (*NO_START_OPT).
There is more discussion of this option in the section entitled "Option
bits for pcre_exec()" in the pcreapi documentation.
- Experiments with Perl suggest that it too has similar optimizations,
+ Experiments with Perl suggest that it too has similar optimizations,
sometimes leading to anomalous results.
Verbs that act immediately
- The following verbs act as soon as they are encountered. They may not
+ The following verbs act as soon as they are encountered. They may not
be followed by a name.
(*ACCEPT)
- This verb causes the match to end successfully, skipping the remainder
- of the pattern. However, when it is inside a subpattern that is called
- as a subroutine, only that subpattern is ended successfully. Matching
- then continues at the outer level. If (*ACCEPT) is inside capturing
- parentheses, the data so far is captured. For example:
+ This verb causes the match to end successfully, skipping the remainder
+ of the pattern. However, when it is inside a subpattern that is called
+ as a subroutine, only that subpattern is ended successfully. Matching
+ then continues at the outer level. If (*ACCEPT) in triggered in a posi-
+ tive assertion, the assertion succeeds; in a negative assertion, the
+ assertion fails.
+
+ If (*ACCEPT) is inside capturing parentheses, the data so far is cap-
+ tured. For example:
A((?:A|B(*ACCEPT)|C)D)
- This matches "AB", "AAD", or "ACD"; when it matches "AB", "B" is cap-
+ This matches "AB", "AAD", or "ACD"; when it matches "AB", "B" is cap-
tured by the outer parentheses.
(*FAIL) or (*F)
- This verb causes a matching failure, forcing backtracking to occur. It
- is equivalent to (?!) but easier to read. The Perl documentation notes
- that it is probably useful only when combined with (?{}) or (??{}).
- Those are, of course, Perl features that are not present in PCRE. The
- nearest equivalent is the callout feature, as for example in this pat-
+ This verb causes a matching failure, forcing backtracking to occur. It
+ is equivalent to (?!) but easier to read. The Perl documentation notes
+ that it is probably useful only when combined with (?{}) or (??{}).
+ Those are, of course, Perl features that are not present in PCRE. The
+ nearest equivalent is the callout feature, as for example in this pat-
tern:
a+(?C)(*FAIL)
- A match with the string "aaaa" always fails, but the callout is taken
+ A match with the string "aaaa" always fails, but the callout is taken
before each backtrack happens (in this example, 10 times).
Recording which path was taken
- There is one verb whose main purpose is to track how a match was
- arrived at, though it also has a secondary use in conjunction with
+ There is one verb whose main purpose is to track how a match was
+ arrived at, though it also has a secondary use in conjunction with
advancing the match starting point (see (*SKIP) below).
(*MARK:NAME) or (*:NAME)
- A name is always required with this verb. There may be as many
- instances of (*MARK) as you like in a pattern, and their names do not
+ A name is always required with this verb. There may be as many
+ instances of (*MARK) as you like in a pattern, and their names do not
have to be unique.
- When a match succeeds, the name of the last-encountered (*MARK) on the
- matching path is passed back to the caller as described in the section
- entitled "Extra data for pcre_exec()" in the pcreapi documentation.
- Here is an example of pcretest output, where the /K modifier requests
- the retrieval and outputting of (*MARK) data:
+ When a match succeeds, the name of the last-encountered (*MARK:NAME),
+ (*PRUNE:NAME), or (*THEN:NAME) on the matching path is passed back to
+ the caller as described in the section entitled "Extra data for
+ pcre_exec()" in the pcreapi documentation. Here is an example of
+ pcretest output, where the /K modifier requests the retrieval and out-
+ putting of (*MARK) data:
re> /X(*MARK:A)Y|X(*MARK:B)Z/K
data> XY
@@ -6982,57 +7336,67 @@ BACKTRACKING CONTROL
efficient way of obtaining this information than putting each alterna-
tive in its own capturing parentheses.
- If (*MARK) is encountered in a positive assertion, its name is recorded
- and passed back if it is the last-encountered. This does not happen for
- negative assertions.
+ If a verb with a name is encountered in a positive assertion that is
+ true, the name is recorded and passed back if it is the last-encoun-
+ tered. This does not happen for negative assertions or failing positive
+ assertions.
- After a partial match or a failed match, the name of the last encoun-
- tered (*MARK) in the entire match process is returned. For example:
+ After a partial match or a failed match, the last encountered name in
+ the entire match process is returned. For example:
re> /X(*MARK:A)Y|X(*MARK:B)Z/K
data> XP
No match, mark = B
- Note that in this unanchored example the mark is retained from the
+ Note that in this unanchored example the mark is retained from the
match attempt that started at the letter "X" in the subject. Subsequent
match attempts starting at "P" and then with an empty string do not get
as far as the (*MARK) item, but nevertheless do not reset it.
- If you are interested in (*MARK) values after failed matches, you
- should probably set the PCRE_NO_START_OPTIMIZE option (see above) to
+ If you are interested in (*MARK) values after failed matches, you
+ should probably set the PCRE_NO_START_OPTIMIZE option (see above) to
ensure that the match is always attempted.
Verbs that act after backtracking
The following verbs do nothing when they are encountered. Matching con-
- tinues with what follows, but if there is no subsequent match, causing
- a backtrack to the verb, a failure is forced. That is, backtracking
- cannot pass to the left of the verb. However, when one of these verbs
- appears inside an atomic group, its effect is confined to that group,
- because once the group has been matched, there is never any backtrack-
- ing into it. In this situation, backtracking can "jump back" to the
- left of the entire atomic group. (Remember also, as stated above, that
- this localization also applies in subroutine calls and assertions.)
+ tinues with what follows, but if there is no subsequent match, causing
+ a backtrack to the verb, a failure is forced. That is, backtracking
+ cannot pass to the left of the verb. However, when one of these verbs
+ appears inside an atomic group or an assertion that is true, its effect
+ is confined to that group, because once the group has been matched,
+ there is never any backtracking into it. In this situation, backtrack-
+ ing can "jump back" to the left of the entire atomic group or asser-
+ tion. (Remember also, as stated above, that this localization also
+ applies in subroutine calls.)
These verbs differ in exactly what kind of failure occurs when back-
- tracking reaches them.
+ tracking reaches them. The behaviour described below is what happens
+ when the verb is not in a subroutine or an assertion. Subsequent sec-
+ tions cover these special cases.
(*COMMIT)
This verb, which may not be followed by a name, causes the whole match
- to fail outright if the rest of the pattern does not match. Even if the
- pattern is unanchored, no further attempts to find a match by advancing
- the starting point take place. Once (*COMMIT) has been passed,
- pcre_exec() is committed to finding a match at the current starting
- point, or not at all. For example:
+ to fail outright if there is a later matching failure that causes back-
+ tracking to reach it. Even if the pattern is unanchored, no further
+ attempts to find a match by advancing the starting point take place. If
+ (*COMMIT) is the only backtracking verb that is encountered, once it
+ has been passed pcre_exec() is committed to finding a match at the cur-
+ rent starting point, or not at all. For example:
a+(*COMMIT)b
- This matches "xxaab" but not "aacaab". It can be thought of as a kind
+ This matches "xxaab" but not "aacaab". It can be thought of as a kind
of dynamic anchor, or "I've started, so I must finish." The name of the
- most recently passed (*MARK) in the path is passed back when (*COMMIT)
+ most recently passed (*MARK) in the path is passed back when (*COMMIT)
forces a match failure.
+ If there is more than one backtracking verb in a pattern, a different
+ one that follows (*COMMIT) may be triggered first, so merely passing
+ (*COMMIT) during a match does not always guarantee that a match must be
+ at this starting point.
+
Note that (*COMMIT) at the start of a pattern is not the same as an
anchor, unless PCRE's start-of-match optimizations are turned off, as
shown in this pcretest example:
@@ -7052,66 +7416,80 @@ BACKTRACKING CONTROL
(*PRUNE) or (*PRUNE:NAME)
This verb causes the match to fail at the current starting position in
- the subject if the rest of the pattern does not match. If the pattern
- is unanchored, the normal "bumpalong" advance to the next starting
- character then happens. Backtracking can occur as usual to the left of
- (*PRUNE), before it is reached, or when matching to the right of
- (*PRUNE), but if there is no match to the right, backtracking cannot
- cross (*PRUNE). In simple cases, the use of (*PRUNE) is just an alter-
- native to an atomic group or possessive quantifier, but there are some
- uses of (*PRUNE) that cannot be expressed in any other way. The behav-
- iour of (*PRUNE:NAME) is the same as (*MARK:NAME)(*PRUNE). In an
- anchored pattern (*PRUNE) has the same effect as (*COMMIT).
+ the subject if there is a later matching failure that causes backtrack-
+ ing to reach it. If the pattern is unanchored, the normal "bumpalong"
+ advance to the next starting character then happens. Backtracking can
+ occur as usual to the left of (*PRUNE), before it is reached, or when
+ matching to the right of (*PRUNE), but if there is no match to the
+ right, backtracking cannot cross (*PRUNE). In simple cases, the use of
+ (*PRUNE) is just an alternative to an atomic group or possessive quan-
+ tifier, but there are some uses of (*PRUNE) that cannot be expressed in
+ any other way. In an anchored pattern (*PRUNE) has the same effect as
+ (*COMMIT).
+
+ The behaviour of (*PRUNE:NAME) is the not the same as
+ (*MARK:NAME)(*PRUNE). It is like (*MARK:NAME) in that the name is
+ remembered for passing back to the caller. However, (*SKIP:NAME)
+ searches only for names set with (*MARK).
(*SKIP)
- This verb, when given without a name, is like (*PRUNE), except that if
- the pattern is unanchored, the "bumpalong" advance is not to the next
+ This verb, when given without a name, is like (*PRUNE), except that if
+ the pattern is unanchored, the "bumpalong" advance is not to the next
character, but to the position in the subject where (*SKIP) was encoun-
- tered. (*SKIP) signifies that whatever text was matched leading up to
+ tered. (*SKIP) signifies that whatever text was matched leading up to
it cannot be part of a successful match. Consider:
a+(*SKIP)b
- If the subject is "aaaac...", after the first match attempt fails
- (starting at the first character in the string), the starting point
+ If the subject is "aaaac...", after the first match attempt fails
+ (starting at the first character in the string), the starting point
skips on to start the next attempt at "c". Note that a possessive quan-
- tifer does not have the same effect as this example; although it would
- suppress backtracking during the first match attempt, the second
- attempt would start at the second character instead of skipping on to
+ tifer does not have the same effect as this example; although it would
+ suppress backtracking during the first match attempt, the second
+ attempt would start at the second character instead of skipping on to
"c".
(*SKIP:NAME)
- When (*SKIP) has an associated name, its behaviour is modified. If the
- following pattern fails to match, the previous path through the pattern
- is searched for the most recent (*MARK) that has the same name. If one
- is found, the "bumpalong" advance is to the subject position that cor-
- responds to that (*MARK) instead of to where (*SKIP) was encountered.
- If no (*MARK) with a matching name is found, the (*SKIP) is ignored.
+ When (*SKIP) has an associated name, its behaviour is modified. When it
+ is triggered, the previous path through the pattern is searched for the
+ most recent (*MARK) that has the same name. If one is found, the
+ "bumpalong" advance is to the subject position that corresponds to that
+ (*MARK) instead of to where (*SKIP) was encountered. If no (*MARK) with
+ a matching name is found, the (*SKIP) is ignored.
+
+ Note that (*SKIP:NAME) searches only for names set by (*MARK:NAME). It
+ ignores names that are set by (*PRUNE:NAME) or (*THEN:NAME).
(*THEN) or (*THEN:NAME)
- This verb causes a skip to the next innermost alternative if the rest
- of the pattern does not match. That is, it cancels pending backtrack-
- ing, but only within the current alternative. Its name comes from the
- observation that it can be used for a pattern-based if-then-else block:
+ This verb causes a skip to the next innermost alternative when back-
+ tracking reaches it. That is, it cancels any further backtracking
+ within the current alternative. Its name comes from the observation
+ that it can be used for a pattern-based if-then-else block:
( COND1 (*THEN) FOO | COND2 (*THEN) BAR | COND3 (*THEN) BAZ ) ...
If the COND1 pattern matches, FOO is tried (and possibly further items
after the end of the group if FOO succeeds); on failure, the matcher
skips to the second alternative and tries COND2, without backtracking
- into COND1. The behaviour of (*THEN:NAME) is exactly the same as
- (*MARK:NAME)(*THEN). If (*THEN) is not inside an alternation, it acts
- like (*PRUNE).
-
- Note that a subpattern that does not contain a | character is just a
- part of the enclosing alternative; it is not a nested alternation with
- only one alternative. The effect of (*THEN) extends beyond such a sub-
- pattern to the enclosing alternative. Consider this pattern, where A,
- B, etc. are complex pattern fragments that do not contain any | charac-
- ters at this level:
+ into COND1. If that succeeds and BAR fails, COND3 is tried. If subse-
+ quently BAZ fails, there are no more alternatives, so there is a back-
+ track to whatever came before the entire group. If (*THEN) is not
+ inside an alternation, it acts like (*PRUNE).
+
+ The behaviour of (*THEN:NAME) is the not the same as
+ (*MARK:NAME)(*THEN). It is like (*MARK:NAME) in that the name is
+ remembered for passing back to the caller. However, (*SKIP:NAME)
+ searches only for names set with (*MARK).
+
+ A subpattern that does not contain a | character is just a part of the
+ enclosing alternative; it is not a nested alternation with only one
+ alternative. The effect of (*THEN) extends beyond such a subpattern to
+ the enclosing alternative. Consider this pattern, where A, B, etc. are
+ complex pattern fragments that do not contain any | characters at this
+ level:
A (B(*THEN)C) | D
@@ -7127,7 +7505,7 @@ BACKTRACKING CONTROL
tern to fail because there are no more alternatives to try. In this
case, matching does now backtrack into A.
- Note also that a conditional subpattern is not considered as having two
+ Note that a conditional subpattern is not considered as having two
alternatives, because only one is ever used. In other words, the |
character in a conditional subpattern has a different meaning. Ignoring
white space, consider:
@@ -7151,16 +7529,78 @@ BACKTRACKING CONTROL
the advance may be more than one character. (*COMMIT) is the strongest,
causing the entire match to fail.
- If more than one such verb is present in a pattern, the "strongest" one
- wins. For example, consider this pattern, where A, B, etc. are complex
- pattern fragments:
+ More than one backtracking verb
+
+ If more than one backtracking verb is present in a pattern, the one
+ that is backtracked onto first acts. For example, consider this pat-
+ tern, where A, B, etc. are complex pattern fragments:
+
+ (A(*COMMIT)B(*THEN)C|ABD)
+
+ If A matches but B fails, the backtrack to (*COMMIT) causes the entire
+ match to fail. However, if A and B match, but C fails, the backtrack to
+ (*THEN) causes the next alternative (ABD) to be tried. This behaviour
+ is consistent, but is not always the same as Perl's. It means that if
+ two or more backtracking verbs appear in succession, all the the last
+ of them has no effect. Consider this example:
+
+ ...(*COMMIT)(*PRUNE)...
+
+ If there is a matching failure to the right, backtracking onto (*PRUNE)
+ causes it to be triggered, and its action is taken. There can never be
+ a backtrack onto (*COMMIT).
+
+ Backtracking verbs in repeated groups
+
+ PCRE differs from Perl in its handling of backtracking verbs in
+ repeated groups. For example, consider:
+
+ /(a(*COMMIT)b)+ac/
+
+ If the subject is "abac", Perl matches, but PCRE fails because the
+ (*COMMIT) in the second repeat of the group acts.
+
+ Backtracking verbs in assertions
+
+ (*FAIL) in an assertion has its normal effect: it forces an immediate
+ backtrack.
+
+ (*ACCEPT) in a positive assertion causes the assertion to succeed with-
+ out any further processing. In a negative assertion, (*ACCEPT) causes
+ the assertion to fail without any further processing.
- (A(*COMMIT)B(*THEN)C|D)
+ The other backtracking verbs are not treated specially if they appear
+ in a positive assertion. In particular, (*THEN) skips to the next
+ alternative in the innermost enclosing group that has alternations,
+ whether or not this is within the assertion.
- Once A has matched, PCRE is committed to this match, at the current
- starting position. If subsequently B matches, but C does not, the nor-
- mal (*THEN) action of trying the next alternative (that is, D) does not
- happen because (*COMMIT) overrides.
+ Negative assertions are, however, different, in order to ensure that
+ changing a positive assertion into a negative assertion changes its
+ result. Backtracking into (*COMMIT), (*SKIP), or (*PRUNE) causes a neg-
+ ative assertion to be true, without considering any further alternative
+ branches in the assertion. Backtracking into (*THEN) causes it to skip
+ to the next enclosing alternative within the assertion (the normal be-
+ haviour), but if the assertion does not have such an alternative,
+ (*THEN) behaves like (*PRUNE).
+
+ Backtracking verbs in subroutines
+
+ These behaviours occur whether or not the subpattern is called recur-
+ sively. Perl's treatment of subroutines is different in some cases.
+
+ (*FAIL) in a subpattern called as a subroutine has its normal effect:
+ it forces an immediate backtrack.
+
+ (*ACCEPT) in a subpattern called as a subroutine causes the subroutine
+ match to succeed without any further processing. Matching then contin-
+ ues after the subroutine call.
+
+ (*COMMIT), (*SKIP), and (*PRUNE) in a subpattern called as a subroutine
+ cause the subroutine match to fail.
+
+ (*THEN) skips to the next alternative in the innermost enclosing group
+ within the subpattern that has alternatives. If there is no such group
+ within the subpattern, (*THEN) causes the subroutine match to fail.
SEE ALSO
@@ -7178,18 +7618,18 @@ AUTHOR
REVISION
- Last updated: 11 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 03 December 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRESYNTAX(3) PCRESYNTAX(3)
+PCRESYNTAX(3) Library Functions Manual PCRESYNTAX(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE REGULAR EXPRESSION SYNTAX SUMMARY
The full syntax and semantics of the regular expressions that are sup-
@@ -7212,10 +7652,15 @@ CHARACTERS
\n newline (hex 0A)
\r carriage return (hex 0D)
\t tab (hex 09)
+ \0dd character with octal code 0dd
\ddd character with octal code ddd, or backreference
+ \o{ddd..} character with octal code ddd..
\xhh character with hex code hh
\x{hhh..} character with hex code hhh..
+ Note that \0dd is always an octal code, and that \8 and \9 are the lit-
+ eral characters "8" and "9".
+
CHARACTER TYPES
@@ -7238,9 +7683,12 @@ CHARACTER TYPES
\W a "non-word" character
\X a Unicode extended grapheme cluster
- In PCRE, by default, \d, \D, \s, \S, \w, and \W recognize only ASCII
- characters, even in a UTF mode. However, this can be changed by setting
- the PCRE_UCP option.
+ By default, \d, \s, and \w match only ASCII characters, even in UTF-8
+ mode or in the 16- bit and 32-bit libraries. However, if locale-spe-
+ cific matching is happening, \s and \w may also match characters with
+ code points in the range 128-255. If the PCRE_UCP option is set, the
+ behaviour of these escape sequences is changed to use Unicode proper-
+ ties and they match many more characters.
GENERAL CATEGORY PROPERTIES FOR \p and \P
@@ -7295,27 +7743,32 @@ PCRE SPECIAL CATEGORY PROPERTIES FOR \p and \P
Xan Alphanumeric: union of properties L and N
Xps POSIX space: property Z or tab, NL, VT, FF, CR
- Xsp Perl space: property Z or tab, NL, FF, CR
+ Xsp Perl space: property Z or tab, NL, VT, FF, CR
+ Xuc Univerally-named character: one that can be
+ represented by a Universal Character Name
Xwd Perl word: property Xan or underscore
+ Perl and POSIX space are now the same. Perl added VT to its space char-
+ acter set at release 5.18 and PCRE changed at release 8.34.
+
SCRIPT NAMES FOR \p AND \P
- Arabic, Armenian, Avestan, Balinese, Bamum, Batak, Bengali, Bopomofo,
- Brahmi, Braille, Buginese, Buhid, Canadian_Aboriginal, Carian, Chakma,
- Cham, Cherokee, Common, Coptic, Cuneiform, Cypriot, Cyrillic, Deseret,
- Devanagari, Egyptian_Hieroglyphs, Ethiopic, Georgian, Glagolitic,
- Gothic, Greek, Gujarati, Gurmukhi, Han, Hangul, Hanunoo, Hebrew, Hira-
- gana, Imperial_Aramaic, Inherited, Inscriptional_Pahlavi, Inscrip-
- tional_Parthian, Javanese, Kaithi, Kannada, Katakana, Kayah_Li,
- Kharoshthi, Khmer, Lao, Latin, Lepcha, Limbu, Linear_B, Lisu, Lycian,
+ Arabic, Armenian, Avestan, Balinese, Bamum, Batak, Bengali, Bopomofo,
+ Brahmi, Braille, Buginese, Buhid, Canadian_Aboriginal, Carian, Chakma,
+ Cham, Cherokee, Common, Coptic, Cuneiform, Cypriot, Cyrillic, Deseret,
+ Devanagari, Egyptian_Hieroglyphs, Ethiopic, Georgian, Glagolitic,
+ Gothic, Greek, Gujarati, Gurmukhi, Han, Hangul, Hanunoo, Hebrew, Hira-
+ gana, Imperial_Aramaic, Inherited, Inscriptional_Pahlavi, Inscrip-
+ tional_Parthian, Javanese, Kaithi, Kannada, Katakana, Kayah_Li,
+ Kharoshthi, Khmer, Lao, Latin, Lepcha, Limbu, Linear_B, Lisu, Lycian,
Lydian, Malayalam, Mandaic, Meetei_Mayek, Meroitic_Cursive,
- Meroitic_Hieroglyphs, Miao, Mongolian, Myanmar, New_Tai_Lue, Nko,
- Ogham, Old_Italic, Old_Persian, Old_South_Arabian, Old_Turkic,
- Ol_Chiki, Oriya, Osmanya, Phags_Pa, Phoenician, Rejang, Runic, Samari-
- tan, Saurashtra, Sharada, Shavian, Sinhala, Sora_Sompeng, Sundanese,
- Syloti_Nagri, Syriac, Tagalog, Tagbanwa, Tai_Le, Tai_Tham, Tai_Viet,
- Takri, Tamil, Telugu, Thaana, Thai, Tibetan, Tifinagh, Ugaritic, Vai,
+ Meroitic_Hieroglyphs, Miao, Mongolian, Myanmar, New_Tai_Lue, Nko,
+ Ogham, Old_Italic, Old_Persian, Old_South_Arabian, Old_Turkic,
+ Ol_Chiki, Oriya, Osmanya, Phags_Pa, Phoenician, Rejang, Runic, Samari-
+ tan, Saurashtra, Sharada, Shavian, Sinhala, Sora_Sompeng, Sundanese,
+ Syloti_Nagri, Syriac, Tagalog, Tagbanwa, Tai_Le, Tai_Tham, Tai_Viet,
+ Takri, Tamil, Telugu, Thaana, Thai, Tibetan, Tifinagh, Ugaritic, Vai,
Yi.
@@ -7342,8 +7795,8 @@ CHARACTER CLASSES
word same as \w
xdigit hexadecimal digit
- In PCRE, POSIX character set names recognize only ASCII characters by
- default, but some of them use Unicode properties if PCRE_UCP is set.
+ In PCRE, POSIX character set names recognize only ASCII characters by
+ default, but some of them use Unicode properties if PCRE_UCP is set.
You can use \Q...\E inside a character class.
@@ -7424,9 +7877,11 @@ OPTION SETTING
(?x) extended (ignore white space)
(?-...) unset option(s)
- The following are recognized only at the start of a pattern or after
+ The following are recognized only at the start of a pattern or after
one of the newline-setting options with similar syntax:
+ (*LIMIT_MATCH=d) set the match limit to d (decimal number)
+ (*LIMIT_RECURSION=d) set the recursion limit to d (decimal number)
(*NO_START_OPT) no start-match optimization (PCRE_NO_START_OPTIMIZE)
(*UTF8) set UTF-8 mode: 8-bit library (PCRE_UTF8)
(*UTF16) set UTF-16 mode: 16-bit library (PCRE_UTF16)
@@ -7434,6 +7889,9 @@ OPTION SETTING
(*UTF) set appropriate UTF mode for the library in use
(*UCP) set PCRE_UCP (use Unicode properties for \d etc)
+ Note that LIMIT_MATCH and LIMIT_RECURSION can only reduce the value of
+ the limits set by the caller of pcre_exec(), not increase them.
+
LOOKAHEAD AND LOOKBEHIND ASSERTIONS
@@ -7558,18 +8016,18 @@ AUTHOR
REVISION
- Last updated: 11 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREUNICODE(3) PCREUNICODE(3)
+PCREUNICODE(3) Library Functions Manual PCREUNICODE(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
UTF-8, UTF-16, UTF-32, AND UNICODE PROPERTY SUPPORT
As well as UTF-8 support, PCRE also supports UTF-16 (from release 8.30)
@@ -7632,7 +8090,9 @@ UNICODE PROPERTY SUPPORT
fication. Earlier releases of PCRE followed the rules of RFC 2279,
which allows the full range of 31-bit values (0 to 0x7FFFFFFF). The
current check allows only values in the range U+0 to U+10FFFF, exclud-
- ing the surrogate area and the non-characters.
+ ing the surrogate area. (From release 8.33 the so-called "non-charac-
+ ter" code points are no longer excluded because Unicode corrigendum #9
+ makes it clear that they should not be.)
Characters in the "Surrogate Area" of Unicode are reserved for use by
UTF-16, where they are used in pairs to encode codepoints with values
@@ -7641,10 +8101,6 @@ UNICODE PROPERTY SUPPORT
other words, the whole surrogate thing is a fudge for UTF-16 which
unfortunately messes up UTF-8 and UTF-32.)
- Also excluded are the "Non-Character" code points, which are U+FDD0 to
- U+FDEF and the last two code points in each plane, U+??FFFE and
- U+??FFFF.
-
If an invalid UTF-8 string is passed to PCRE, an error return is given.
At compile time, the only additional information is the offset to the
first byte of the failing character. The run-time functions pcre_exec()
@@ -7676,10 +8132,6 @@ UNICODE PROPERTY SUPPORT
surrogate range U+D800 to U+DFFF are independent code points. Values in
the surrogate range must be used in pairs in the correct manner.
- Excluded are the "Non-Character" code points, which are U+FDD0 to
- U+FDEF and the last two code points in each plane, U+??FFFE and
- U+??FFFF.
-
If an invalid UTF-16 string is passed to PCRE, an error return is
given. At compile time, the only additional information is the offset
to the first data unit of the failing character. The run-time functions
@@ -7701,77 +8153,76 @@ UNICODE PROPERTY SUPPORT
are passed as patterns and subjects are (by default) checked for valid-
ity on entry to the relevant functions. This check allows only values
in the range U+0 to U+10FFFF, excluding the surrogate area U+D800 to
- U+DFFF, and the "Non-Character" code points, which are U+FDD0 to U+FDEF
- and the last two characters in each plane, U+??FFFE and U+??FFFF.
+ U+DFFF.
- If an invalid UTF-32 string is passed to PCRE, an error return is
- given. At compile time, the only additional information is the offset
+ If an invalid UTF-32 string is passed to PCRE, an error return is
+ given. At compile time, the only additional information is the offset
to the first data unit of the failing character. The run-time functions
pcre32_exec() and pcre32_dfa_exec() also pass back this information, as
- well as a more detailed reason code if the caller has provided memory
+ well as a more detailed reason code if the caller has provided memory
in which to do this.
- In some situations, you may already know that your strings are valid,
- and therefore want to skip these checks in order to improve perfor-
- mance. If you set the PCRE_NO_UTF32_CHECK flag at compile time or at
+ In some situations, you may already know that your strings are valid,
+ and therefore want to skip these checks in order to improve perfor-
+ mance. If you set the PCRE_NO_UTF32_CHECK flag at compile time or at
run time, PCRE assumes that the pattern or subject it is given (respec-
tively) contains only valid UTF-32 sequences. In this case, it does not
- diagnose an invalid UTF-32 string. However, if an invalid string is
+ diagnose an invalid UTF-32 string. However, if an invalid string is
passed, the result is undefined.
General comments about UTF modes
- 1. Codepoints less than 256 can be specified in patterns by either
+ 1. Codepoints less than 256 can be specified in patterns by either
braced or unbraced hexadecimal escape sequences (for example, \x{b3} or
\xb3). Larger values have to use braced sequences.
- 2. Octal numbers up to \777 are recognized, and in UTF-8 mode they
+ 2. Octal numbers up to \777 are recognized, and in UTF-8 mode they
match two-byte characters for values greater than \177.
3. Repeat quantifiers apply to complete UTF characters, not to individ-
ual data units, for example: \x{100}{3}.
- 4. The dot metacharacter matches one UTF character instead of a single
+ 4. The dot metacharacter matches one UTF character instead of a single
data unit.
- 5. The escape sequence \C can be used to match a single byte in UTF-8
- mode, or a single 16-bit data unit in UTF-16 mode, or a single 32-bit
- data unit in UTF-32 mode, but its use can lead to some strange effects
- because it breaks up multi-unit characters (see the description of \C
- in the pcrepattern documentation). The use of \C is not supported in
- the alternative matching function pcre[16|32]_dfa_exec(), nor is it
+ 5. The escape sequence \C can be used to match a single byte in UTF-8
+ mode, or a single 16-bit data unit in UTF-16 mode, or a single 32-bit
+ data unit in UTF-32 mode, but its use can lead to some strange effects
+ because it breaks up multi-unit characters (see the description of \C
+ in the pcrepattern documentation). The use of \C is not supported in
+ the alternative matching function pcre[16|32]_dfa_exec(), nor is it
supported in UTF mode by the JIT optimization of pcre[16|32]_exec(). If
- JIT optimization is requested for a UTF pattern that contains \C, it
+ JIT optimization is requested for a UTF pattern that contains \C, it
will not succeed, and so the matching will be carried out by the normal
interpretive function.
- 6. The character escapes \b, \B, \d, \D, \s, \S, \w, and \W correctly
+ 6. The character escapes \b, \B, \d, \D, \s, \S, \w, and \W correctly
test characters of any code value, but, by default, the characters that
- PCRE recognizes as digits, spaces, or word characters remain the same
- set as in non-UTF mode, all with values less than 256. This remains
- true even when PCRE is built to include Unicode property support,
+ PCRE recognizes as digits, spaces, or word characters remain the same
+ set as in non-UTF mode, all with values less than 256. This remains
+ true even when PCRE is built to include Unicode property support,
because to do otherwise would slow down PCRE in many common cases. Note
- in particular that this applies to \b and \B, because they are defined
+ in particular that this applies to \b and \B, because they are defined
in terms of \w and \W. If you really want to test for a wider sense of,
- say, "digit", you can use explicit Unicode property tests such as
+ say, "digit", you can use explicit Unicode property tests such as
\p{Nd}. Alternatively, if you set the PCRE_UCP option, the way that the
- character escapes work is changed so that Unicode properties are used
+ character escapes work is changed so that Unicode properties are used
to determine which characters match. There are more details in the sec-
tion on generic character types in the pcrepattern documentation.
- 7. Similarly, characters that match the POSIX named character classes
+ 7. Similarly, characters that match the POSIX named character classes
are all low-valued characters, unless the PCRE_UCP option is set.
- 8. However, the horizontal and vertical white space matching escapes
- (\h, \H, \v, and \V) do match all the appropriate Unicode characters,
+ 8. However, the horizontal and vertical white space matching escapes
+ (\h, \H, \v, and \V) do match all the appropriate Unicode characters,
whether or not PCRE_UCP is set.
- 9. Case-insensitive matching applies only to characters whose values
- are less than 128, unless PCRE is built with Unicode property support.
- A few Unicode characters such as Greek sigma have more than two code-
+ 9. Case-insensitive matching applies only to characters whose values
+ are less than 128, unless PCRE is built with Unicode property support.
+ A few Unicode characters such as Greek sigma have more than two code-
points that are case-equivalent. Up to and including PCRE release 8.31,
- only one-to-one case mappings were supported, but later releases (with
- Unicode property support) do treat as case-equivalent all versions of
+ only one-to-one case mappings were supported, but later releases (with
+ Unicode property support) do treat as case-equivalent all versions of
characters such as Greek sigma.
@@ -7784,18 +8235,18 @@ AUTHOR
REVISION
- Last updated: 11 November 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 27 February 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREJIT(3) PCREJIT(3)
+PCREJIT(3) Library Functions Manual PCREJIT(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE JUST-IN-TIME COMPILER SUPPORT
Just-in-time compiling is a heavyweight optimization that can greatly
@@ -7941,15 +8392,9 @@ UNSUPPORTED OPTIONS AND PATTERN ITEMS
BOL, PCRE_NOTEOL, PCRE_NOTEMPTY, PCRE_NOTEMPTY_ATSTART, PCRE_PAR-
TIAL_HARD, and PCRE_PARTIAL_SOFT.
- The unsupported pattern items are:
-
- \C match a single byte; not supported in UTF-8 mode
- (?Cn) callouts
- (*PRUNE) )
- (*SKIP) ) backtracking control verbs
- (*THEN) )
-
- Support for some of these may be added in future.
+ The only unsupported pattern items are \C (match a single data unit)
+ when running in a UTF mode, and a callout immediately before an asser-
+ tion condition in a conditional group.
RETURN VALUES FROM JIT EXECUTION
@@ -8203,18 +8648,18 @@ AUTHOR
REVISION
- Last updated: 31 October 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 17 March 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREPARTIAL(3) PCREPARTIAL(3)
+PCREPARTIAL(3) Library Functions Manual PCREPARTIAL(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PARTIAL MATCHING IN PCRE
In normal use of PCRE, if the subject string that is passed to a match-
@@ -8273,7 +8718,7 @@ PARTIAL MATCHING USING pcre_exec() OR pcre[16|32]_exec()
A partial match occurs during a call to pcre_exec() or
pcre[16|32]_exec() when the end of the subject string is reached suc-
cessfully, but matching cannot continue because more characters are
- needed. However, at least one character in the subject must have been
+ needed. However, at least one character in the subject must have been
inspected. This character need not form part of the final matched
string; lookbehind assertions and the \K escape sequence provide ways
of inspecting characters before the start of a matched substring. The
@@ -8286,18 +8731,22 @@ PARTIAL MATCHING USING pcre_exec() OR pcre[16|32]_exec()
match is returned, the first slot is set to the offset of the earliest
character that was inspected. For convenience, the second offset points
to the end of the subject so that a substring can easily be identified.
+ If there are at least three slots in the offsets vector, the third slot
+ is set to the offset of the character where matching started.
- For the majority of patterns, the first offset identifies the start of
- the partially matched string. However, for patterns that contain look-
- behind assertions, or \K, or begin with \b or \B, earlier characters
- have been inspected while carrying out the match. For example:
+ For the majority of patterns, the contents of the first and third slots
+ will be the same. However, for patterns that contain lookbehind asser-
+ tions, or begin with \b or \B, characters before the one where matching
+ started may have been inspected while carrying out the match. For exam-
+ ple, consider this pattern:
/(?<=abc)123/
This pattern matches "123", but only if it is preceded by "abc". If the
- subject string is "xyzabc12", the offsets after a partial match are for
- the substring "abc12", because all these characters are needed if
- another match is tried with extra characters added to the subject.
+ subject string is "xyzabc12", the first two offsets after a partial
+ match are for the substring "abc12", because all these characters were
+ inspected. However, the third offset is set to 6, because that is the
+ offset where matching began.
What happens when a partial match is identified depends on which of the
two partial matching options are set.
@@ -8491,6 +8940,16 @@ MULTI-SEGMENT MATCHING WITH pcre_dfa_exec() OR pcre[16|32]_dfa_exec()
matched string. It is up to the calling program to do that if it needs
to.
+ That means that, for an unanchored pattern, if a continued match fails,
+ it is not possible to try again at a new starting point. All this
+ facility is capable of doing is continuing with the previous match
+ attempt. In the previous example, if the second set of data is "ug23"
+ the result is no match, even though there would be a match for "aug23"
+ if the entire string were given at once. Depending on the application,
+ this may or may not be what you want. The only way to allow for start-
+ ing again at the next character is to retain the matched part of the
+ subject and try a new complete match.
+
You can set the PCRE_PARTIAL_SOFT or PCRE_PARTIAL_HARD options with
PCRE_DFA_RESTART to continue partial matching over multiple segments.
This facility can be used to pass very long subject strings to the DFA
@@ -8523,10 +8982,9 @@ MULTI-SEGMENT MATCHING WITH pcre_exec() OR pcre[16|32]_exec()
Note: If the pattern contains lookbehind assertions, or \K, or starts
with \b or \B, the string that is returned for a partial match includes
- characters that precede the partially matched string itself, because
- these must be retained when adding on more characters for a subsequent
- matching attempt. However, in some cases you may need to retain even
- earlier characters, as discussed in the next section.
+ characters that precede the start of what would be returned for a com-
+ plete match, because it contains all the characters that were inspected
+ during the partial match.
ISSUES WITH MULTI-SEGMENT MATCHING
@@ -8535,23 +8993,44 @@ ISSUES WITH MULTI-SEGMENT MATCHING
whichever matching function is used.
1. If the pattern contains a test for the beginning of a line, you need
- to pass the PCRE_NOTBOL option when the subject string for any call
- does start at the beginning of a line. There is also a PCRE_NOTEOL
+ to pass the PCRE_NOTBOL option when the subject string for any call
+ does start at the beginning of a line. There is also a PCRE_NOTEOL
option, but in practice when doing multi-segment matching you should be
using PCRE_PARTIAL_HARD, which includes the effect of PCRE_NOTEOL.
- 2. Lookbehind assertions that have already been obeyed are catered for
+ 2. Lookbehind assertions that have already been obeyed are catered for
in the offsets that are returned for a partial match. However a lookbe-
- hind assertion later in the pattern could require even earlier charac-
- ters to be inspected. You can handle this case by using the
+ hind assertion later in the pattern could require even earlier charac-
+ ters to be inspected. You can handle this case by using the
PCRE_INFO_MAXLOOKBEHIND option of the pcre_fullinfo() or
- pcre[16|32]_fullinfo() functions to obtain the length of the largest
- lookbehind in the pattern. This length is given in characters, not
- bytes. If you always retain at least that many characters before the
- partially matched string, all should be well. (Of course, near the
+ pcre[16|32]_fullinfo() functions to obtain the length of the longest
+ lookbehind in the pattern. This length is given in characters, not
+ bytes. If you always retain at least that many characters before the
+ partially matched string, all should be well. (Of course, near the
start of the subject, fewer characters may be present; in that case all
characters should be retained.)
+ From release 8.33, there is a more accurate way of deciding which char-
+ acters to retain. Instead of subtracting the length of the longest
+ lookbehind from the earliest inspected character (offsets[0]), the
+ match start position (offsets[2]) should be used, and the next match
+ attempt started at the offsets[2] character by setting the startoffset
+ argument of pcre_exec() or pcre_dfa_exec().
+
+ For example, if the pattern "(?<=123)abc" is partially matched against
+ the string "xx123a", the three offset values returned are 2, 6, and 5.
+ This indicates that the matching process that gave a partial match
+ started at offset 5, but the characters "123a" were all inspected. The
+ maximum lookbehind for that pattern is 3, so taking that away from 5
+ shows that we need only keep "123a", and the next match attempt can be
+ started at offset 3 (that is, at "a") when further characters have been
+ added. When the match start is not the earliest inspected character,
+ pcretest shows it explicitly:
+
+ re> "(?<=123)abc"
+ data> xx123a\P\P
+ Partial match at offset 5: 123a
+
3. Because a partial match must always contain at least one character,
what might be considered a partial match of an empty string actually
gives a "no match" result. For example:
@@ -8654,18 +9133,18 @@ AUTHOR
REVISION
- Last updated: 24 June 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 02 July 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREPRECOMPILE(3) PCREPRECOMPILE(3)
+PCREPRECOMPILE(3) Library Functions Manual PCREPRECOMPILE(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
SAVING AND RE-USING PRECOMPILED PCRE PATTERNS
If you are running an application that uses a large number of regular
@@ -8758,6 +9237,10 @@ RE-USING A PRECOMPILED PATTERN
is used to pass this data, as described in the section on matching a
pattern in the pcreapi documentation.
+ Warning: The tables that pcre_exec() and pcre_dfa_exec() use must be
+ the same as those that were used when the pattern was compiled. If this
+ is not the case, the behaviour is undefined.
+
If you did not provide custom character tables when the pattern was
compiled, the pointer in the compiled pattern is NULL, which causes the
matching functions to use PCRE's internal tables. Thus, you do not need
@@ -8789,18 +9272,18 @@ AUTHOR
REVISION
- Last updated: 24 June 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 12 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCREPERFORM(3) PCREPERFORM(3)
+PCREPERFORM(3) Library Functions Manual PCREPERFORM(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE PERFORMANCE
Two aspects of performance are discussed below: memory usage and pro-
@@ -8964,14 +9447,14 @@ REVISION
------------------------------------------------------------------------------
-PCREPOSIX(3) PCREPOSIX(3)
+PCREPOSIX(3) Library Functions Manual PCREPOSIX(3)
+
NAME
PCRE - Perl-compatible regular expressions.
-
-SYNOPSIS OF POSIX API
+SYNOPSIS
#include <pcreposix.h>
@@ -8980,8 +9463,7 @@ SYNOPSIS OF POSIX API
int regexec(regex_t *preg, const char *string,
size_t nmatch, regmatch_t pmatch[], int eflags);
-
- size_t regerror(int errcode, const regex_t *preg,
+ size_t regerror(int errcode, const regex_t *preg,
char *errbuf, size_t errbuf_size);
void regfree(regex_t *preg);
@@ -9229,13 +9711,13 @@ REVISION
------------------------------------------------------------------------------
-PCRECPP(3) PCRECPP(3)
+PCRECPP(3) Library Functions Manual PCRECPP(3)
+
NAME
PCRE - Perl-compatible regular expressions.
-
SYNOPSIS OF C++ WRAPPER
#include <pcrecpp.h>
@@ -9572,13 +10054,13 @@ REVISION
------------------------------------------------------------------------------
-PCRESAMPLE(3) PCRESAMPLE(3)
+PCRESAMPLE(3) Library Functions Manual PCRESAMPLE(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE SAMPLE PROGRAM
A simple, complete demonstration program, to get you started with using
@@ -9658,51 +10140,56 @@ REVISION
Last updated: 10 January 2012
Copyright (c) 1997-2012 University of Cambridge.
------------------------------------------------------------------------------
-PCRELIMITS(3) PCRELIMITS(3)
+PCRELIMITS(3) Library Functions Manual PCRELIMITS(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
SIZE AND OTHER LIMITATIONS
There are some size limitations in PCRE but it is hoped that they will
never in practice be relevant.
The maximum length of a compiled pattern is approximately 64K data
- units (bytes for the 8-bit library, 32-bit units for the 32-bit
+ units (bytes for the 8-bit library, 16-bit units for the 16-bit
library, and 32-bit units for the 32-bit library) if PCRE is compiled
- with the default internal linkage size of 2 bytes. If you want to
- process regular expressions that are truly enormous, you can compile
- PCRE with an internal linkage size of 3 or 4 (when building the 16-bit
- or 32-bit library, 3 is rounded up to 4). See the README file in the
- source distribution and the pcrebuild documentation for details. In
- these cases the limit is substantially larger. However, the speed of
+ with the default internal linkage size, which is 2 bytes for the 8-bit
+ and 16-bit libraries, and 4 bytes for the 32-bit library. If you want
+ to process regular expressions that are truly enormous, you can compile
+ PCRE with an internal linkage size of 3 or 4 (when building the 16-bit
+ or 32-bit library, 3 is rounded up to 4). See the README file in the
+ source distribution and the pcrebuild documentation for details. In
+ these cases the limit is substantially larger. However, the speed of
execution is slower.
All values in repeating quantifiers must be less than 65536.
There is no limit to the number of parenthesized subpatterns, but there
- can be no more than 65535 capturing subpatterns.
+ can be no more than 65535 capturing subpatterns. There is, however, a
+ limit to the depth of nesting of parenthesized subpatterns of all
+ kinds. This is imposed in order to limit the amount of system stack
+ used at compile time. The limit can be specified when PCRE is built;
+ the default is 250.
There is a limit to the number of forward references to subsequent sub-
- patterns of around 200,000. Repeated forward references with fixed
- upper limits, for example, (?2){0,100} when subpattern number 2 is to
- the right, are included in the count. There is no limit to the number
+ patterns of around 200,000. Repeated forward references with fixed
+ upper limits, for example, (?2){0,100} when subpattern number 2 is to
+ the right, are included in the count. There is no limit to the number
of backward references.
The maximum length of name for a named subpattern is 32 characters, and
the maximum number of named subpatterns is 10000.
- The maximum length of a name in a (*MARK), (*PRUNE), (*SKIP), or
- (*THEN) verb is 255 for the 8-bit library and 65535 for the 16-bit and
- 32-bit library.
+ The maximum length of a name in a (*MARK), (*PRUNE), (*SKIP), or
+ (*THEN) verb is 255 for the 8-bit library and 65535 for the 16-bit and
+ 32-bit libraries.
- The maximum length of a subject string is the largest positive number
- that an integer variable can hold. However, when using the traditional
+ The maximum length of a subject string is the largest positive number
+ that an integer variable can hold. However, when using the traditional
matching function, PCRE uses recursion to handle subpatterns and indef-
- inite repetition. This means that the available stack space may limit
+ inite repetition. This means that the available stack space may limit
the size of a subject string that can be processed by certain patterns.
For a discussion of stack issues, see the pcrestack documentation.
@@ -9716,18 +10203,18 @@ AUTHOR
REVISION
- Last updated: 04 May 2012
- Copyright (c) 1997-2012 University of Cambridge.
+ Last updated: 05 November 2013
+ Copyright (c) 1997-2013 University of Cambridge.
------------------------------------------------------------------------------
-PCRESTACK(3) PCRESTACK(3)
+PCRESTACK(3) Library Functions Manual PCRESTACK(3)
+
NAME
PCRE - Perl-compatible regular expressions
-
PCRE DISCUSSION OF STACK USAGE
When you call pcre[16|32]_exec(), it makes use of an internal function
diff --git a/ext/pcre/pcrelib/pcre.h b/ext/pcre/pcrelib/pcre.h
index a6aa4e934b..c85f36b6bc 100644
--- a/ext/pcre/pcrelib/pcre.h
+++ b/ext/pcre/pcrelib/pcre.h
@@ -5,7 +5,7 @@
/* This is the public header file for the PCRE library, to be #included by
applications that call the PCRE functions.
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -42,9 +42,9 @@ POSSIBILITY OF SUCH DAMAGE.
/* The current PCRE version information. */
#define PCRE_MAJOR 8
-#define PCRE_MINOR 32
+#define PCRE_MINOR 34
#define PCRE_PRERELEASE
-#define PCRE_DATE 2012-11-30
+#define PCRE_DATE 2013-12-15
/* When an application links to a PCRE DLL in Windows, the symbols that are
imported have to be identified as such. When building PCRE, the appropriate
@@ -96,11 +96,14 @@ extern "C" {
#endif
/* Public options. Some are compile-time only, some are run-time only, and some
-are both, so we keep them all distinct. However, almost all the bits in the
-options word are now used. In the long run, we may have to re-use some of the
-compile-time only bits for runtime options, or vice versa. Any of the
-compile-time options may be inspected during studying (and therefore JIT
-compiling).
+are both. Most of the compile-time options are saved with the compiled regex so
+that they can be inspected during studying (and therefore JIT compiling). Note
+that pcre_study() has its own set of options. Originally, all the options
+defined here used distinct bits. However, almost all the bits in a 32-bit word
+are now used, so in order to conserve them, option bits that were previously
+only recognized at matching time (i.e. by pcre_exec() or pcre_dfa_exec()) may
+also be used for compile-time options that affect only compiling and are not
+relevant for studying or JIT compiling.
Some options for pcre_compile() change its behaviour but do not affect the
behaviour of the execution functions. Other options are passed through to the
@@ -142,8 +145,15 @@ with J. */
#define PCRE_AUTO_CALLOUT 0x00004000 /* C1 */
#define PCRE_PARTIAL_SOFT 0x00008000 /* E D J ) Synonyms */
#define PCRE_PARTIAL 0x00008000 /* E D J ) */
-#define PCRE_DFA_SHORTEST 0x00010000 /* D */
-#define PCRE_DFA_RESTART 0x00020000 /* D */
+
+/* This pair use the same bit. */
+#define PCRE_NEVER_UTF 0x00010000 /* C1 ) Overlaid */
+#define PCRE_DFA_SHORTEST 0x00010000 /* D ) Overlaid */
+
+/* This pair use the same bit. */
+#define PCRE_NO_AUTO_POSSESS 0x00020000 /* C1 ) Overlaid */
+#define PCRE_DFA_RESTART 0x00020000 /* D ) Overlaid */
+
#define PCRE_FIRSTLINE 0x00040000 /* C3 */
#define PCRE_DUPNAMES 0x00080000 /* C1 */
#define PCRE_NEWLINE_CR 0x00100000 /* C3 E D */
@@ -199,6 +209,7 @@ with J. */
#define PCRE_ERROR_DFA_BADRESTART (-30)
#define PCRE_ERROR_JIT_BADOPTION (-31)
#define PCRE_ERROR_BADLENGTH (-32)
+#define PCRE_ERROR_UNSET (-33)
/* Specific error codes for UTF-8 validity checks */
@@ -224,7 +235,7 @@ with J. */
#define PCRE_UTF8_ERR19 19
#define PCRE_UTF8_ERR20 20
#define PCRE_UTF8_ERR21 21
-#define PCRE_UTF8_ERR22 22
+#define PCRE_UTF8_ERR22 22 /* Unused (was non-character) */
/* Specific error codes for UTF-16 validity checks */
@@ -232,13 +243,13 @@ with J. */
#define PCRE_UTF16_ERR1 1
#define PCRE_UTF16_ERR2 2
#define PCRE_UTF16_ERR3 3
-#define PCRE_UTF16_ERR4 4
+#define PCRE_UTF16_ERR4 4 /* Unused (was non-character) */
/* Specific error codes for UTF-32 validity checks */
#define PCRE_UTF32_ERR0 0
#define PCRE_UTF32_ERR1 1
-#define PCRE_UTF32_ERR2 2
+#define PCRE_UTF32_ERR2 2 /* Unused (was non-character) */
#define PCRE_UTF32_ERR3 3
/* Request types for pcre_fullinfo() */
@@ -263,10 +274,13 @@ with J. */
#define PCRE_INFO_JIT 16
#define PCRE_INFO_JITSIZE 17
#define PCRE_INFO_MAXLOOKBEHIND 18
-#define PCRE_INFO_FIRSTCHARACTER 19
-#define PCRE_INFO_FIRSTCHARACTERFLAGS 20
+#define PCRE_INFO_FIRSTCHARACTER 19
+#define PCRE_INFO_FIRSTCHARACTERFLAGS 20
#define PCRE_INFO_REQUIREDCHAR 21
-#define PCRE_INFO_REQUIREDCHARFLAGS 22
+#define PCRE_INFO_REQUIREDCHARFLAGS 22
+#define PCRE_INFO_MATCHLIMIT 23
+#define PCRE_INFO_RECURSIONLIMIT 24
+#define PCRE_INFO_MATCH_EMPTY 25
/* Request types for pcre_config(). Do not re-arrange, in order to remain
compatible. */
@@ -284,6 +298,7 @@ compatible. */
#define PCRE_CONFIG_UTF16 10
#define PCRE_CONFIG_JITTARGET 11
#define PCRE_CONFIG_UTF32 12
+#define PCRE_CONFIG_PARENS_LIMIT 13
/* Request types for pcre_study(). Do not re-arrange, in order to remain
compatible. */
@@ -645,6 +660,9 @@ PCRE_EXP_DECL void pcre16_assign_jit_stack(pcre16_extra *,
pcre16_jit_callback, void *);
PCRE_EXP_DECL void pcre32_assign_jit_stack(pcre32_extra *,
pcre32_jit_callback, void *);
+PCRE_EXP_DECL void pcre_jit_free_unused_memory(void);
+PCRE_EXP_DECL void pcre16_jit_free_unused_memory(void);
+PCRE_EXP_DECL void pcre32_jit_free_unused_memory(void);
#ifdef __cplusplus
} /* extern "C" */
diff --git a/ext/pcre/pcrelib/pcre_chartables.c b/ext/pcre/pcrelib/pcre_chartables.c
index 2a39e9ff33..1e20ec29d0 100644
--- a/ext/pcre/pcrelib/pcre_chartables.c
+++ b/ext/pcre/pcrelib/pcre_chartables.c
@@ -163,7 +163,7 @@ graph, print, punct, and cntrl. Other classes are built from combinations. */
*/
0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /* 0- 7 */
- 0x00,0x01,0x01,0x00,0x01,0x01,0x00,0x00, /* 8- 15 */
+ 0x00,0x01,0x01,0x01,0x01,0x01,0x00,0x00, /* 8- 15 */
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /* 16- 23 */
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /* 24- 31 */
0x01,0x00,0x00,0x00,0x80,0x00,0x00,0x00, /* - ' */
diff --git a/ext/pcre/pcrelib/pcre_compile.c b/ext/pcre/pcrelib/pcre_compile.c
index 4997b3b1ec..c170c47a00 100644
--- a/ext/pcre/pcrelib/pcre_compile.c
+++ b/ext/pcre/pcrelib/pcre_compile.c
@@ -6,7 +6,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -115,6 +115,13 @@ kicks in at the same number of forward references in all cases. */
#define COMPILE_WORK_SIZE (2048*LINK_SIZE)
#define COMPILE_WORK_SIZE_MAX (100*COMPILE_WORK_SIZE)
+/* This value determines the size of the initial vector that is used for
+remembering named groups during the pre-compile. It is allocated on the stack,
+but if it is too small, it is expanded using malloc(), in a similar way to the
+workspace. The value is the number of slots in the list. */
+
+#define NAMED_GROUP_LIST_SIZE 20
+
/* The overrun tests check for a slightly smaller size so that they detect the
overrun before it actually does run off the end of the data block. */
@@ -253,11 +260,25 @@ static const verbitem verbs[] = {
static const int verbcount = sizeof(verbs)/sizeof(verbitem);
+/* Substitutes for [[:<:]] and [[:>:]], which mean start and end of word in
+another regex library. */
+
+static const pcre_uchar sub_start_of_word[] = {
+ CHAR_BACKSLASH, CHAR_b, CHAR_LEFT_PARENTHESIS, CHAR_QUESTION_MARK,
+ CHAR_EQUALS_SIGN, CHAR_BACKSLASH, CHAR_w, CHAR_RIGHT_PARENTHESIS, '\0' };
+
+static const pcre_uchar sub_end_of_word[] = {
+ CHAR_BACKSLASH, CHAR_b, CHAR_LEFT_PARENTHESIS, CHAR_QUESTION_MARK,
+ CHAR_LESS_THAN_SIGN, CHAR_EQUALS_SIGN, CHAR_BACKSLASH, CHAR_w,
+ CHAR_RIGHT_PARENTHESIS, '\0' };
+
+
/* Tables of names of POSIX character classes and their lengths. The names are
now all in a single string, to reduce the number of relocations when a shared
library is dynamically loaded. The list of lengths is terminated by a zero
length entry. The first three must be alpha, lower, upper, as this is assumed
-for handling case independence. */
+for handling case independence. The indices for graph, print, and punct are
+needed, so identify them. */
static const char posix_names[] =
STRING_alpha0 STRING_lower0 STRING_upper0 STRING_alnum0
@@ -268,6 +289,11 @@ static const char posix_names[] =
static const pcre_uint8 posix_name_lengths[] = {
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 4, 6, 0 };
+#define PC_GRAPH 8
+#define PC_PRINT 9
+#define PC_PUNCT 10
+
+
/* Table of class bit maps for each POSIX class. Each class is formed from a
base map, with an optional addition or removal of another map. Then, for some
classes, there is some additional tweaking: for [:blank:] the vertical space
@@ -295,9 +321,8 @@ static const int posix_class_maps[] = {
cbit_xdigit,-1, 0 /* xdigit */
};
-/* Table of substitutes for \d etc when PCRE_UCP is set. The POSIX class
-substitutes must be in the order of the names, defined above, and there are
-both positive and negative cases. NULL means no substitute. */
+/* Table of substitutes for \d etc when PCRE_UCP is set. They are replaced by
+Unicode property escapes. */
#ifdef SUPPORT_UCP
static const pcre_uchar string_PNd[] = {
@@ -322,12 +347,18 @@ static const pcre_uchar string_pXwd[] = {
static const pcre_uchar *substitutes[] = {
string_PNd, /* \D */
string_pNd, /* \d */
- string_PXsp, /* \S */ /* NOTE: Xsp is Perl space */
- string_pXsp, /* \s */
+ string_PXsp, /* \S */ /* Xsp is Perl space, but from 8.34, Perl */
+ string_pXsp, /* \s */ /* space and POSIX space are the same. */
string_PXwd, /* \W */
string_pXwd /* \w */
};
+/* The POSIX class substitutes must be in the order of the POSIX class names,
+defined above, and there are both positive and negative cases. NULL means no
+general substitute of a Unicode property escape (\p or \P). However, for some
+POSIX classes (e.g. graph, print, punct) a special property code is compiled
+directly. */
+
static const pcre_uchar string_pL[] = {
CHAR_BACKSLASH, CHAR_p, CHAR_LEFT_CURLY_BRACKET,
CHAR_L, CHAR_RIGHT_CURLY_BRACKET, '\0' };
@@ -375,8 +406,8 @@ static const pcre_uchar *posix_substitutes[] = {
NULL, /* graph */
NULL, /* print */
NULL, /* punct */
- string_pXps, /* space */ /* NOTE: Xps is POSIX space */
- string_pXwd, /* word */
+ string_pXps, /* space */ /* Xps is POSIX space, but from 8.34 */
+ string_pXwd, /* word */ /* Perl and POSIX space are the same */
NULL, /* xdigit */
/* Negated cases */
string_PL, /* ^alpha */
@@ -390,8 +421,8 @@ static const pcre_uchar *posix_substitutes[] = {
NULL, /* ^graph */
NULL, /* ^print */
NULL, /* ^punct */
- string_PXps, /* ^space */ /* NOTE: Xps is POSIX space */
- string_PXwd, /* ^word */
+ string_PXps, /* ^space */ /* Xps is POSIX space, but from 8.34 */
+ string_PXwd, /* ^word */ /* Perl and POSIX space are the same */
NULL /* ^xdigit */
};
#define POSIX_SUBSIZE (sizeof(posix_substitutes) / sizeof(pcre_uchar *))
@@ -455,7 +486,7 @@ static const char error_texts[] =
"POSIX collating elements are not supported\0"
"this version of PCRE is compiled without UTF support\0"
"spare error\0" /** DEAD **/
- "character value in \\x{...} sequence is too large\0"
+ "character value in \\x{} or \\o{} is too large\0"
/* 35 */
"invalid condition (?(0)\0"
"\\C not allowed in lookbehind assertion\0"
@@ -487,7 +518,7 @@ static const char error_texts[] =
"a numbered reference must not be zero\0"
"an argument is not allowed for (*ACCEPT), (*FAIL), or (*COMMIT)\0"
/* 60 */
- "(*VERB) not recognized\0"
+ "(*VERB) not recognized or malformed\0"
"number is too big\0"
"subpattern name expected\0"
"digit expected after (?+\0"
@@ -508,6 +539,14 @@ static const char error_texts[] =
"name is too long in (*MARK), (*PRUNE), (*SKIP), or (*THEN)\0"
"character value in \\u.... sequence is too large\0"
"invalid UTF-32 string\0"
+ "setting UTF is disabled by the application\0"
+ "non-hex character in \\x{} (closing brace missing?)\0"
+ /* 80 */
+ "non-octal character in \\o{} (closing brace missing?)\0"
+ "missing opening brace after \\o\0"
+ "parentheses are too deeply nested\0"
+ "invalid range in character class\0"
+ "group name must start with a non-digit\0"
;
/* Table to identify digits and hex digits. This is used when compiling
@@ -647,6 +686,183 @@ static const pcre_uint8 ebcdic_chartab[] = { /* chartable partial dup */
#endif
+/* This table is used to check whether auto-possessification is possible
+between adjacent character-type opcodes. The left-hand (repeated) opcode is
+used to select the row, and the right-hand opcode is use to select the column.
+A value of 1 means that auto-possessification is OK. For example, the second
+value in the first row means that \D+\d can be turned into \D++\d.
+
+The Unicode property types (\P and \p) have to be present to fill out the table
+because of what their opcode values are, but the table values should always be
+zero because property types are handled separately in the code. The last four
+columns apply to items that cannot be repeated, so there is no need to have
+rows for them. Note that OP_DIGIT etc. are generated only when PCRE_UCP is
+*not* set. When it is set, \d etc. are converted into OP_(NOT_)PROP codes. */
+
+#define APTROWS (LAST_AUTOTAB_LEFT_OP - FIRST_AUTOTAB_OP + 1)
+#define APTCOLS (LAST_AUTOTAB_RIGHT_OP - FIRST_AUTOTAB_OP + 1)
+
+static const pcre_uint8 autoposstab[APTROWS][APTCOLS] = {
+/* \D \d \S \s \W \w . .+ \C \P \p \R \H \h \V \v \X \Z \z $ $M */
+ { 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* \D */
+ { 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1 }, /* \d */
+ { 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1 }, /* \S */
+ { 0, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* \s */
+ { 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* \W */
+ { 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1 }, /* \w */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* . */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* .+ */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 }, /* \C */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, /* \P */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, /* \p */
+ { 0, 1, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0 }, /* \R */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0 }, /* \H */
+ { 0, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0 }, /* \h */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0 }, /* \V */
+ { 0, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0 }, /* \v */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0 } /* \X */
+};
+
+
+/* This table is used to check whether auto-possessification is possible
+between adjacent Unicode property opcodes (OP_PROP and OP_NOTPROP). The
+left-hand (repeated) opcode is used to select the row, and the right-hand
+opcode is used to select the column. The values are as follows:
+
+ 0 Always return FALSE (never auto-possessify)
+ 1 Character groups are distinct (possessify if both are OP_PROP)
+ 2 Check character categories in the same group (general or particular)
+ 3 TRUE if the two opcodes are not the same (PROP vs NOTPROP)
+
+ 4 Check left general category vs right particular category
+ 5 Check right general category vs left particular category
+
+ 6 Left alphanum vs right general category
+ 7 Left space vs right general category
+ 8 Left word vs right general category
+
+ 9 Right alphanum vs left general category
+ 10 Right space vs left general category
+ 11 Right word vs left general category
+
+ 12 Left alphanum vs right particular category
+ 13 Left space vs right particular category
+ 14 Left word vs right particular category
+
+ 15 Right alphanum vs left particular category
+ 16 Right space vs left particular category
+ 17 Right word vs left particular category
+*/
+
+static const pcre_uint8 propposstab[PT_TABSIZE][PT_TABSIZE] = {
+/* ANY LAMP GC PC SC ALNUM SPACE PXSPACE WORD CLIST UCNC */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, /* PT_ANY */
+ { 0, 3, 0, 0, 0, 3, 1, 1, 0, 0, 0 }, /* PT_LAMP */
+ { 0, 0, 2, 4, 0, 9, 10, 10, 11, 0, 0 }, /* PT_GC */
+ { 0, 0, 5, 2, 0, 15, 16, 16, 17, 0, 0 }, /* PT_PC */
+ { 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0 }, /* PT_SC */
+ { 0, 3, 6, 12, 0, 3, 1, 1, 0, 0, 0 }, /* PT_ALNUM */
+ { 0, 1, 7, 13, 0, 1, 3, 3, 1, 0, 0 }, /* PT_SPACE */
+ { 0, 1, 7, 13, 0, 1, 3, 3, 1, 0, 0 }, /* PT_PXSPACE */
+ { 0, 0, 8, 14, 0, 0, 1, 1, 3, 0, 0 }, /* PT_WORD */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, /* PT_CLIST */
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3 } /* PT_UCNC */
+};
+
+/* This table is used to check whether auto-possessification is possible
+between adjacent Unicode property opcodes (OP_PROP and OP_NOTPROP) when one
+specifies a general category and the other specifies a particular category. The
+row is selected by the general category and the column by the particular
+category. The value is 1 if the particular category is not part of the general
+category. */
+
+static const pcre_uint8 catposstab[7][30] = {
+/* Cc Cf Cn Co Cs Ll Lm Lo Lt Lu Mc Me Mn Nd Nl No Pc Pd Pe Pf Pi Po Ps Sc Sk Sm So Zl Zp Zs */
+ { 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, /* C */
+ { 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, /* L */
+ { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, /* M */
+ { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }, /* N */
+ { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1 }, /* P */
+ { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1 }, /* S */
+ { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0 } /* Z */
+};
+
+/* This table is used when checking ALNUM, (PX)SPACE, SPACE, and WORD against
+a general or particular category. The properties in each row are those
+that apply to the character set in question. Duplication means that a little
+unnecessary work is done when checking, but this keeps things much simpler
+because they can all use the same code. For more details see the comment where
+this table is used.
+
+Note: SPACE and PXSPACE used to be different because Perl excluded VT from
+"space", but from Perl 5.18 it's included, so both categories are treated the
+same here. */
+
+static const pcre_uint8 posspropstab[3][4] = {
+ { ucp_L, ucp_N, ucp_N, ucp_Nl }, /* ALNUM, 3rd and 4th values redundant */
+ { ucp_Z, ucp_Z, ucp_C, ucp_Cc }, /* SPACE and PXSPACE, 2nd value redundant */
+ { ucp_L, ucp_N, ucp_P, ucp_Po } /* WORD */
+};
+
+/* This table is used when converting repeating opcodes into possessified
+versions as a result of an explicit possessive quantifier such as ++. A zero
+value means there is no possessified version - in those cases the item in
+question must be wrapped in ONCE brackets. The table is truncated at OP_CALLOUT
+because all relevant opcodes are less than that. */
+
+static const pcre_uint8 opcode_possessify[] = {
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 0 - 15 */
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 16 - 31 */
+
+ 0, /* NOTI */
+ OP_POSSTAR, 0, /* STAR, MINSTAR */
+ OP_POSPLUS, 0, /* PLUS, MINPLUS */
+ OP_POSQUERY, 0, /* QUERY, MINQUERY */
+ OP_POSUPTO, 0, /* UPTO, MINUPTO */
+ 0, /* EXACT */
+ 0, 0, 0, 0, /* POS{STAR,PLUS,QUERY,UPTO} */
+
+ OP_POSSTARI, 0, /* STARI, MINSTARI */
+ OP_POSPLUSI, 0, /* PLUSI, MINPLUSI */
+ OP_POSQUERYI, 0, /* QUERYI, MINQUERYI */
+ OP_POSUPTOI, 0, /* UPTOI, MINUPTOI */
+ 0, /* EXACTI */
+ 0, 0, 0, 0, /* POS{STARI,PLUSI,QUERYI,UPTOI} */
+
+ OP_NOTPOSSTAR, 0, /* NOTSTAR, NOTMINSTAR */
+ OP_NOTPOSPLUS, 0, /* NOTPLUS, NOTMINPLUS */
+ OP_NOTPOSQUERY, 0, /* NOTQUERY, NOTMINQUERY */
+ OP_NOTPOSUPTO, 0, /* NOTUPTO, NOTMINUPTO */
+ 0, /* NOTEXACT */
+ 0, 0, 0, 0, /* NOTPOS{STAR,PLUS,QUERY,UPTO} */
+
+ OP_NOTPOSSTARI, 0, /* NOTSTARI, NOTMINSTARI */
+ OP_NOTPOSPLUSI, 0, /* NOTPLUSI, NOTMINPLUSI */
+ OP_NOTPOSQUERYI, 0, /* NOTQUERYI, NOTMINQUERYI */
+ OP_NOTPOSUPTOI, 0, /* NOTUPTOI, NOTMINUPTOI */
+ 0, /* NOTEXACTI */
+ 0, 0, 0, 0, /* NOTPOS{STARI,PLUSI,QUERYI,UPTOI} */
+
+ OP_TYPEPOSSTAR, 0, /* TYPESTAR, TYPEMINSTAR */
+ OP_TYPEPOSPLUS, 0, /* TYPEPLUS, TYPEMINPLUS */
+ OP_TYPEPOSQUERY, 0, /* TYPEQUERY, TYPEMINQUERY */
+ OP_TYPEPOSUPTO, 0, /* TYPEUPTO, TYPEMINUPTO */
+ 0, /* TYPEEXACT */
+ 0, 0, 0, 0, /* TYPEPOS{STAR,PLUS,QUERY,UPTO} */
+
+ OP_CRPOSSTAR, 0, /* CRSTAR, CRMINSTAR */
+ OP_CRPOSPLUS, 0, /* CRPLUS, CRMINPLUS */
+ OP_CRPOSQUERY, 0, /* CRQUERY, CRMINQUERY */
+ OP_CRPOSRANGE, 0, /* CRRANGE, CRMINRANGE */
+ 0, 0, 0, 0, /* CRPOS{STAR,PLUS,QUERY,RANGE} */
+
+ 0, 0, 0, /* CLASS, NCLASS, XCLASS */
+ 0, 0, /* REF, REFI */
+ 0, 0, /* DNREF, DNREFI */
+ 0, 0 /* RECURSE, CALLOUT */
+};
+
+
/*************************************************
* Find an error text *
@@ -674,6 +890,7 @@ return s;
}
+
/*************************************************
* Expand the workspace *
*************************************************/
@@ -751,16 +968,15 @@ return (*p == CHAR_RIGHT_CURLY_BRACKET);
*************************************************/
/* This function is called when a \ has been encountered. It either returns a
-positive value for a simple escape such as \n, or 0 for a data character
-which will be placed in chptr. A backreference to group n is returned as
-negative n. When UTF-8 is enabled, a positive value greater than 255 may
-be returned in chptr.
-On entry,ptr is pointing at the \. On exit, it is on the final character of the
-escape sequence.
+positive value for a simple escape such as \n, or 0 for a data character which
+will be placed in chptr. A backreference to group n is returned as negative n.
+When UTF-8 is enabled, a positive value greater than 255 may be returned in
+chptr. On entry, ptr is pointing at the \. On exit, it is on the final
+character of the escape sequence.
Arguments:
ptrptr points to the pattern position pointer
- chptr points to the data character
+ chptr points to a returned data character
errorcodeptr points to the errorcode variable
bracount number of previous extracting brackets
options the options bits
@@ -797,7 +1013,8 @@ Otherwise further processing may be required. */
#ifndef EBCDIC /* ASCII/UTF-8 coding */
/* Not alphanumeric */
else if (c < CHAR_0 || c > CHAR_z) {}
-else if ((i = escapes[c - CHAR_0]) != 0) { if (i > 0) c = (pcre_uint32)i; else escape = -i; }
+else if ((i = escapes[c - CHAR_0]) != 0)
+ { if (i > 0) c = (pcre_uint32)i; else escape = -i; }
#else /* EBCDIC coding */
/* Not alphanumeric */
@@ -847,11 +1064,11 @@ else
}
#if defined COMPILE_PCRE8
- if (c > (utf ? 0x10ffff : 0xff))
+ if (c > (utf ? 0x10ffffU : 0xffU))
#elif defined COMPILE_PCRE16
- if (c > (utf ? 0x10ffff : 0xffff))
+ if (c > (utf ? 0x10ffffU : 0xffffU))
#elif defined COMPILE_PCRE32
- if (utf && c > 0x10ffff)
+ if (utf && c > 0x10ffffU)
#endif
{
*errorcodeptr = ERR76;
@@ -963,16 +1180,20 @@ else
break;
/* The handling of escape sequences consisting of a string of digits
- starting with one that is not zero is not straightforward. By experiment,
- the way Perl works seems to be as follows:
+ starting with one that is not zero is not straightforward. Perl has changed
+ over the years. Nowadays \g{} for backreferences and \o{} for octal are
+ recommended to avoid the ambiguities in the old syntax.
Outside a character class, the digits are read as a decimal number. If the
- number is less than 10, or if there are that many previous extracting
- left brackets, then it is a back reference. Otherwise, up to three octal
- digits are read to form an escaped byte. Thus \123 is likely to be octal
- 123 (cf \0123, which is octal 012 followed by the literal 3). If the octal
- value is greater than 377, the least significant 8 bits are taken. Inside a
- character class, \ followed by a digit is always an octal number. */
+ number is less than 8 (used to be 10), or if there are that many previous
+ extracting left brackets, then it is a back reference. Otherwise, up to
+ three octal digits are read to form an escaped byte. Thus \123 is likely to
+ be octal 123 (cf \0123, which is octal 012 followed by the literal 3). If
+ the octal value is greater than 377, the least significant 8 bits are
+ taken. \8 and \9 are treated as the literal characters 8 and 9.
+
+ Inside a character class, \ followed by a digit is always either a literal
+ 8 or 9 or an octal number. */
case CHAR_1: case CHAR_2: case CHAR_3: case CHAR_4: case CHAR_5:
case CHAR_6: case CHAR_7: case CHAR_8: case CHAR_9:
@@ -999,7 +1220,7 @@ else
*errorcodeptr = ERR61;
break;
}
- if (s < 10 || s <= bracount)
+ if (s < 8 || s <= bracount) /* Check for back reference */
{
escape = -s;
break;
@@ -1007,16 +1228,14 @@ else
ptr = oldptr; /* Put the pointer back and fall through */
}
- /* Handle an octal number following \. If the first digit is 8 or 9, Perl
- generates a binary zero byte and treats the digit as a following literal.
- Thus we have to pull back the pointer by one. */
+ /* Handle a digit following \ when the number is not a back reference. If
+ the first digit is 8 or 9, Perl used to generate a binary zero byte and
+ then treat the digit as a following literal. At least by Perl 5.18 this
+ changed so as not to insert the binary zero. */
- if ((c = *ptr) >= CHAR_8)
- {
- ptr--;
- c = 0;
- break;
- }
+ if ((c = *ptr) >= CHAR_8) break;
+
+ /* Fall through with a digit less than 8 */
/* \0 always starts an octal number, but we may drop through to here with a
larger first octal digit. The original code used just to take the least
@@ -1033,15 +1252,50 @@ else
#endif
break;
- /* \x is complicated. \x{ddd} is a character number which can be greater
- than 0xff in utf or non-8bit mode, but only if the ddd are hex digits.
- If not, { is treated as a data character. */
+ /* \o is a relatively new Perl feature, supporting a more general way of
+ specifying character codes in octal. The only supported form is \o{ddd}. */
+
+ case CHAR_o:
+ if (ptr[1] != CHAR_LEFT_CURLY_BRACKET) *errorcodeptr = ERR81; else
+ {
+ ptr += 2;
+ c = 0;
+ overflow = FALSE;
+ while (*ptr >= CHAR_0 && *ptr <= CHAR_7)
+ {
+ register pcre_uint32 cc = *ptr++;
+ if (c == 0 && cc == CHAR_0) continue; /* Leading zeroes */
+#ifdef COMPILE_PCRE32
+ if (c >= 0x20000000l) { overflow = TRUE; break; }
+#endif
+ c = (c << 3) + cc - CHAR_0 ;
+#if defined COMPILE_PCRE8
+ if (c > (utf ? 0x10ffffU : 0xffU)) { overflow = TRUE; break; }
+#elif defined COMPILE_PCRE16
+ if (c > (utf ? 0x10ffffU : 0xffffU)) { overflow = TRUE; break; }
+#elif defined COMPILE_PCRE32
+ if (utf && c > 0x10ffffU) { overflow = TRUE; break; }
+#endif
+ }
+ if (overflow)
+ {
+ while (*ptr >= CHAR_0 && *ptr <= CHAR_7) ptr++;
+ *errorcodeptr = ERR34;
+ }
+ else if (*ptr == CHAR_RIGHT_CURLY_BRACKET)
+ {
+ if (utf && c >= 0xd800 && c <= 0xdfff) *errorcodeptr = ERR73;
+ }
+ else *errorcodeptr = ERR80;
+ }
+ break;
+
+ /* \x is complicated. In JavaScript, \x must be followed by two hexadecimal
+ numbers. Otherwise it is a lowercase x letter. */
case CHAR_x:
if ((options & PCRE_JAVASCRIPT_COMPAT) != 0)
{
- /* In JavaScript, \x must be followed by two hexadecimal numbers.
- Otherwise it is a lowercase x letter. */
if (MAX_255(ptr[1]) && (digitab[ptr[1]] & ctype_xdigit) != 0
&& MAX_255(ptr[2]) && (digitab[ptr[2]] & ctype_xdigit) != 0)
{
@@ -1058,73 +1312,86 @@ else
#endif
}
}
- break;
- }
+ } /* End JavaScript handling */
- if (ptr[1] == CHAR_LEFT_CURLY_BRACKET)
- {
- const pcre_uchar *pt = ptr + 2;
+ /* Handle \x in Perl's style. \x{ddd} is a character number which can be
+ greater than 0xff in utf or non-8bit mode, but only if the ddd are hex
+ digits. If not, { used to be treated as a data character. However, Perl
+ seems to read hex digits up to the first non-such, and ignore the rest, so
+ that, for example \x{zz} matches a binary zero. This seems crazy, so PCRE
+ now gives an error. */
- c = 0;
- overflow = FALSE;
- while (MAX_255(*pt) && (digitab[*pt] & ctype_xdigit) != 0)
+ else
+ {
+ if (ptr[1] == CHAR_LEFT_CURLY_BRACKET)
{
- register pcre_uint32 cc = *pt++;
- if (c == 0 && cc == CHAR_0) continue; /* Leading zeroes */
+ ptr += 2;
+ c = 0;
+ overflow = FALSE;
+ while (MAX_255(*ptr) && (digitab[*ptr] & ctype_xdigit) != 0)
+ {
+ register pcre_uint32 cc = *ptr++;
+ if (c == 0 && cc == CHAR_0) continue; /* Leading zeroes */
#ifdef COMPILE_PCRE32
- if (c >= 0x10000000l) { overflow = TRUE; break; }
+ if (c >= 0x10000000l) { overflow = TRUE; break; }
#endif
#ifndef EBCDIC /* ASCII/UTF-8 coding */
- if (cc >= CHAR_a) cc -= 32; /* Convert to upper case */
- c = (c << 4) + cc - ((cc < CHAR_A)? CHAR_0 : (CHAR_A - 10));
+ if (cc >= CHAR_a) cc -= 32; /* Convert to upper case */
+ c = (c << 4) + cc - ((cc < CHAR_A)? CHAR_0 : (CHAR_A - 10));
#else /* EBCDIC coding */
- if (cc >= CHAR_a && cc <= CHAR_z) cc += 64; /* Convert to upper case */
- c = (c << 4) + cc - ((cc >= CHAR_0)? CHAR_0 : (CHAR_A - 10));
+ if (cc >= CHAR_a && cc <= CHAR_z) cc += 64; /* Convert to upper case */
+ c = (c << 4) + cc - ((cc >= CHAR_0)? CHAR_0 : (CHAR_A - 10));
#endif
#if defined COMPILE_PCRE8
- if (c > (utf ? 0x10ffff : 0xff)) { overflow = TRUE; break; }
+ if (c > (utf ? 0x10ffffU : 0xffU)) { overflow = TRUE; break; }
#elif defined COMPILE_PCRE16
- if (c > (utf ? 0x10ffff : 0xffff)) { overflow = TRUE; break; }
+ if (c > (utf ? 0x10ffffU : 0xffffU)) { overflow = TRUE; break; }
#elif defined COMPILE_PCRE32
- if (utf && c > 0x10ffff) { overflow = TRUE; break; }
+ if (utf && c > 0x10ffffU) { overflow = TRUE; break; }
#endif
- }
+ }
- if (overflow)
- {
- while (MAX_255(*pt) && (digitab[*pt] & ctype_xdigit) != 0) pt++;
- *errorcodeptr = ERR34;
- }
+ if (overflow)
+ {
+ while (MAX_255(*ptr) && (digitab[*ptr] & ctype_xdigit) != 0) ptr++;
+ *errorcodeptr = ERR34;
+ }
- if (*pt == CHAR_RIGHT_CURLY_BRACKET)
- {
- if (utf && c >= 0xd800 && c <= 0xdfff) *errorcodeptr = ERR73;
- ptr = pt;
- break;
- }
+ else if (*ptr == CHAR_RIGHT_CURLY_BRACKET)
+ {
+ if (utf && c >= 0xd800 && c <= 0xdfff) *errorcodeptr = ERR73;
+ }
- /* If the sequence of hex digits does not end with '}', then we don't
- recognize this construct; fall through to the normal \x handling. */
- }
+ /* If the sequence of hex digits does not end with '}', give an error.
+ We used just to recognize this construct and fall through to the normal
+ \x handling, but nowadays Perl gives an error, which seems much more
+ sensible, so we do too. */
- /* Read just a single-byte hex-defined char */
+ else *errorcodeptr = ERR79;
+ } /* End of \x{} processing */
- c = 0;
- while (i++ < 2 && MAX_255(ptr[1]) && (digitab[ptr[1]] & ctype_xdigit) != 0)
- {
- pcre_uint32 cc; /* Some compilers don't like */
- cc = *(++ptr); /* ++ in initializers */
+ /* Read a single-byte hex-defined char (up to two hex digits after \x) */
+
+ else
+ {
+ c = 0;
+ while (i++ < 2 && MAX_255(ptr[1]) && (digitab[ptr[1]] & ctype_xdigit) != 0)
+ {
+ pcre_uint32 cc; /* Some compilers don't like */
+ cc = *(++ptr); /* ++ in initializers */
#ifndef EBCDIC /* ASCII/UTF-8 coding */
- if (cc >= CHAR_a) cc -= 32; /* Convert to upper case */
- c = c * 16 + cc - ((cc < CHAR_A)? CHAR_0 : (CHAR_A - 10));
+ if (cc >= CHAR_a) cc -= 32; /* Convert to upper case */
+ c = c * 16 + cc - ((cc < CHAR_A)? CHAR_0 : (CHAR_A - 10));
#else /* EBCDIC coding */
- if (cc <= CHAR_z) cc += 64; /* Convert to upper case */
- c = c * 16 + cc - ((cc >= CHAR_0)? CHAR_0 : (CHAR_A - 10));
+ if (cc <= CHAR_z) cc += 64; /* Convert to upper case */
+ c = c * 16 + cc - ((cc >= CHAR_0)? CHAR_0 : (CHAR_A - 10));
#endif
- }
+ }
+ } /* End of \xdd handling */
+ } /* End of Perl-style \x handling */
break;
/* For \c, a following letter is upper-cased; then the 0x40 bit is flipped.
@@ -1190,6 +1457,8 @@ if ((options & PCRE_UCP) != 0 && escape >= ESC_D && escape <= ESC_w)
return escape;
}
+
+
#ifdef SUPPORT_UCP
/*************************************************
* Handle \P and \p *
@@ -1287,7 +1556,6 @@ return FALSE;
-
/*************************************************
* Read repeat counts *
*************************************************/
@@ -1356,302 +1624,6 @@ return p;
/*************************************************
-* Subroutine for finding forward reference *
-*************************************************/
-
-/* This recursive function is called only from find_parens() below. The
-top-level call starts at the beginning of the pattern. All other calls must
-start at a parenthesis. It scans along a pattern's text looking for capturing
-subpatterns, and counting them. If it finds a named pattern that matches the
-name it is given, it returns its number. Alternatively, if the name is NULL, it
-returns when it reaches a given numbered subpattern. Recursion is used to keep
-track of subpatterns that reset the capturing group numbers - the (?| feature.
-
-This function was originally called only from the second pass, in which we know
-that if (?< or (?' or (?P< is encountered, the name will be correctly
-terminated because that is checked in the first pass. There is now one call to
-this function in the first pass, to check for a recursive back reference by
-name (so that we can make the whole group atomic). In this case, we need check
-only up to the current position in the pattern, and that is still OK because
-and previous occurrences will have been checked. To make this work, the test
-for "end of pattern" is a check against cd->end_pattern in the main loop,
-instead of looking for a binary zero. This means that the special first-pass
-call can adjust cd->end_pattern temporarily. (Checks for binary zero while
-processing items within the loop are OK, because afterwards the main loop will
-terminate.)
-
-Arguments:
- ptrptr address of the current character pointer (updated)
- cd compile background data
- name name to seek, or NULL if seeking a numbered subpattern
- lorn name length, or subpattern number if name is NULL
- xmode TRUE if we are in /x mode
- utf TRUE if we are in UTF-8 / UTF-16 / UTF-32 mode
- count pointer to the current capturing subpattern number (updated)
-
-Returns: the number of the named subpattern, or -1 if not found
-*/
-
-static int
-find_parens_sub(pcre_uchar **ptrptr, compile_data *cd, const pcre_uchar *name, int lorn,
- BOOL xmode, BOOL utf, int *count)
-{
-pcre_uchar *ptr = *ptrptr;
-int start_count = *count;
-int hwm_count = start_count;
-BOOL dup_parens = FALSE;
-
-/* If the first character is a parenthesis, check on the type of group we are
-dealing with. The very first call may not start with a parenthesis. */
-
-if (ptr[0] == CHAR_LEFT_PARENTHESIS)
- {
- /* Handle specials such as (*SKIP) or (*UTF8) etc. */
-
- if (ptr[1] == CHAR_ASTERISK) ptr += 2;
-
- /* Handle a normal, unnamed capturing parenthesis. */
-
- else if (ptr[1] != CHAR_QUESTION_MARK)
- {
- *count += 1;
- if (name == NULL && *count == lorn) return *count;
- ptr++;
- }
-
- /* All cases now have (? at the start. Remember when we are in a group
- where the parenthesis numbers are duplicated. */
-
- else if (ptr[2] == CHAR_VERTICAL_LINE)
- {
- ptr += 3;
- dup_parens = TRUE;
- }
-
- /* Handle comments; all characters are allowed until a ket is reached. */
-
- else if (ptr[2] == CHAR_NUMBER_SIGN)
- {
- for (ptr += 3; *ptr != CHAR_NULL; ptr++)
- if (*ptr == CHAR_RIGHT_PARENTHESIS) break;
- goto FAIL_EXIT;
- }
-
- /* Handle a condition. If it is an assertion, just carry on so that it
- is processed as normal. If not, skip to the closing parenthesis of the
- condition (there can't be any nested parens). */
-
- else if (ptr[2] == CHAR_LEFT_PARENTHESIS)
- {
- ptr += 2;
- if (ptr[1] != CHAR_QUESTION_MARK)
- {
- while (*ptr != CHAR_NULL && *ptr != CHAR_RIGHT_PARENTHESIS) ptr++;
- if (*ptr != CHAR_NULL) ptr++;
- }
- }
-
- /* Start with (? but not a condition. */
-
- else
- {
- ptr += 2;
- if (*ptr == CHAR_P) ptr++; /* Allow optional P */
-
- /* We have to disambiguate (?<! and (?<= from (?<name> for named groups */
-
- if ((*ptr == CHAR_LESS_THAN_SIGN && ptr[1] != CHAR_EXCLAMATION_MARK &&
- ptr[1] != CHAR_EQUALS_SIGN) || *ptr == CHAR_APOSTROPHE)
- {
- pcre_uchar term;
- const pcre_uchar *thisname;
- *count += 1;
- if (name == NULL && *count == lorn) return *count;
- term = *ptr++;
- if (term == CHAR_LESS_THAN_SIGN) term = CHAR_GREATER_THAN_SIGN;
- thisname = ptr;
- while (*ptr != term) ptr++;
- if (name != NULL && lorn == (int)(ptr - thisname) &&
- STRNCMP_UC_UC(name, thisname, (unsigned int)lorn) == 0)
- return *count;
- term++;
- }
- }
- }
-
-/* Past any initial parenthesis handling, scan for parentheses or vertical
-bars. Stop if we get to cd->end_pattern. Note that this is important for the
-first-pass call when this value is temporarily adjusted to stop at the current
-position. So DO NOT change this to a test for binary zero. */
-
-for (; ptr < cd->end_pattern; ptr++)
- {
- /* Skip over backslashed characters and also entire \Q...\E */
-
- if (*ptr == CHAR_BACKSLASH)
- {
- if (*(++ptr) == CHAR_NULL) goto FAIL_EXIT;
- if (*ptr == CHAR_Q) for (;;)
- {
- while (*(++ptr) != CHAR_NULL && *ptr != CHAR_BACKSLASH) {};
- if (*ptr == CHAR_NULL) goto FAIL_EXIT;
- if (*(++ptr) == CHAR_E) break;
- }
- continue;
- }
-
- /* Skip over character classes; this logic must be similar to the way they
- are handled for real. If the first character is '^', skip it. Also, if the
- first few characters (either before or after ^) are \Q\E or \E we skip them
- too. This makes for compatibility with Perl. Note the use of STR macros to
- encode "Q\\E" so that it works in UTF-8 on EBCDIC platforms. */
-
- if (*ptr == CHAR_LEFT_SQUARE_BRACKET)
- {
- BOOL negate_class = FALSE;
- for (;;)
- {
- if (ptr[1] == CHAR_BACKSLASH)
- {
- if (ptr[2] == CHAR_E)
- ptr+= 2;
- else if (STRNCMP_UC_C8(ptr + 2,
- STR_Q STR_BACKSLASH STR_E, 3) == 0)
- ptr += 4;
- else
- break;
- }
- else if (!negate_class && ptr[1] == CHAR_CIRCUMFLEX_ACCENT)
- {
- negate_class = TRUE;
- ptr++;
- }
- else break;
- }
-
- /* If the next character is ']', it is a data character that must be
- skipped, except in JavaScript compatibility mode. */
-
- if (ptr[1] == CHAR_RIGHT_SQUARE_BRACKET &&
- (cd->external_options & PCRE_JAVASCRIPT_COMPAT) == 0)
- ptr++;
-
- while (*(++ptr) != CHAR_RIGHT_SQUARE_BRACKET)
- {
- if (*ptr == CHAR_NULL) return -1;
- if (*ptr == CHAR_BACKSLASH)
- {
- if (*(++ptr) == CHAR_NULL) goto FAIL_EXIT;
- if (*ptr == CHAR_Q) for (;;)
- {
- while (*(++ptr) != CHAR_NULL && *ptr != CHAR_BACKSLASH) {};
- if (*ptr == CHAR_NULL) goto FAIL_EXIT;
- if (*(++ptr) == CHAR_E) break;
- }
- continue;
- }
- }
- continue;
- }
-
- /* Skip comments in /x mode */
-
- if (xmode && *ptr == CHAR_NUMBER_SIGN)
- {
- ptr++;
- while (*ptr != CHAR_NULL)
- {
- if (IS_NEWLINE(ptr)) { ptr += cd->nllen - 1; break; }
- ptr++;
-#ifdef SUPPORT_UTF
- if (utf) FORWARDCHAR(ptr);
-#endif
- }
- if (*ptr == CHAR_NULL) goto FAIL_EXIT;
- continue;
- }
-
- /* Check for the special metacharacters */
-
- if (*ptr == CHAR_LEFT_PARENTHESIS)
- {
- int rc = find_parens_sub(&ptr, cd, name, lorn, xmode, utf, count);
- if (rc > 0) return rc;
- if (*ptr == CHAR_NULL) goto FAIL_EXIT;
- }
-
- else if (*ptr == CHAR_RIGHT_PARENTHESIS)
- {
- if (dup_parens && *count < hwm_count) *count = hwm_count;
- goto FAIL_EXIT;
- }
-
- else if (*ptr == CHAR_VERTICAL_LINE && dup_parens)
- {
- if (*count > hwm_count) hwm_count = *count;
- *count = start_count;
- }
- }
-
-FAIL_EXIT:
-*ptrptr = ptr;
-return -1;
-}
-
-
-
-
-/*************************************************
-* Find forward referenced subpattern *
-*************************************************/
-
-/* This function scans along a pattern's text looking for capturing
-subpatterns, and counting them. If it finds a named pattern that matches the
-name it is given, it returns its number. Alternatively, if the name is NULL, it
-returns when it reaches a given numbered subpattern. This is used for forward
-references to subpatterns. We used to be able to start this scan from the
-current compiling point, using the current count value from cd->bracount, and
-do it all in a single loop, but the addition of the possibility of duplicate
-subpattern numbers means that we have to scan from the very start, in order to
-take account of such duplicates, and to use a recursive function to keep track
-of the different types of group.
-
-Arguments:
- cd compile background data
- name name to seek, or NULL if seeking a numbered subpattern
- lorn name length, or subpattern number if name is NULL
- xmode TRUE if we are in /x mode
- utf TRUE if we are in UTF-8 / UTF-16 / UTF-32 mode
-
-Returns: the number of the found subpattern, or -1 if not found
-*/
-
-static int
-find_parens(compile_data *cd, const pcre_uchar *name, int lorn, BOOL xmode,
- BOOL utf)
-{
-pcre_uchar *ptr = (pcre_uchar *)cd->start_pattern;
-int count = 0;
-int rc;
-
-/* If the pattern does not start with an opening parenthesis, the first call
-to find_parens_sub() will scan right to the end (if necessary). However, if it
-does start with a parenthesis, find_parens_sub() will return when it hits the
-matching closing parens. That is why we have to have a loop. */
-
-for (;;)
- {
- rc = find_parens_sub(&ptr, cd, name, lorn, xmode, utf, &count);
- if (rc > 0 || *ptr++ == CHAR_NULL) break;
- }
-
-return rc;
-}
-
-
-
-
-/*************************************************
* Find first significant op code *
*************************************************/
@@ -1690,9 +1662,9 @@ for (;;)
case OP_CALLOUT:
case OP_CREF:
- case OP_NCREF:
+ case OP_DNCREF:
case OP_RREF:
- case OP_NRREF:
+ case OP_DNRREF:
case OP_DEF:
code += PRIV(OP_lengths)[*code];
break;
@@ -1706,7 +1678,6 @@ for (;;)
-
/*************************************************
* Find the fixed length of a branch *
*************************************************/
@@ -1830,13 +1801,13 @@ for (;;)
case OP_COMMIT:
case OP_CREF:
case OP_DEF:
+ case OP_DNCREF:
+ case OP_DNRREF:
case OP_DOLL:
case OP_DOLLM:
case OP_EOD:
case OP_EODN:
case OP_FAIL:
- case OP_NCREF:
- case OP_NRREF:
case OP_NOT_WORD_BOUNDARY:
case OP_PRUNE:
case OP_REVERSE:
@@ -1931,16 +1902,20 @@ for (;;)
switch (*cc)
{
- case OP_CRPLUS:
- case OP_CRMINPLUS:
case OP_CRSTAR:
case OP_CRMINSTAR:
+ case OP_CRPLUS:
+ case OP_CRMINPLUS:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSPLUS:
+ case OP_CRPOSQUERY:
return -1;
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
if (GET2(cc,1) != GET2(cc,1+IMM2_SIZE)) return -1;
branchlength += (int)GET2(cc,1);
cc += 1 + 2 * IMM2_SIZE;
@@ -2009,6 +1984,8 @@ for (;;)
case OP_QUERYI:
case OP_REF:
case OP_REFI:
+ case OP_DNREF:
+ case OP_DNREFI:
case OP_SBRA:
case OP_SBRAPOS:
case OP_SCBRA:
@@ -2045,7 +2022,6 @@ for (;;)
-
/*************************************************
* Scan compiled regex for specific bracket *
*************************************************/
@@ -2129,9 +2105,6 @@ for (;;)
case OP_MARK:
case OP_PRUNE_ARG:
case OP_SKIP_ARG:
- code += code[1];
- break;
-
case OP_THEN_ARG:
code += code[1];
break;
@@ -2249,9 +2222,6 @@ for (;;)
case OP_MARK:
case OP_PRUNE_ARG:
case OP_SKIP_ARG:
- code += code[1];
- break;
-
case OP_THEN_ARG:
code += code[1];
break;
@@ -2353,15 +2323,23 @@ Arguments:
endcode points to where to stop
utf TRUE if in UTF-8 / UTF-16 / UTF-32 mode
cd contains pointers to tables etc.
+ recurses chain of recurse_check to catch mutual recursion
Returns: TRUE if what is matched could be empty
*/
+typedef struct recurse_check {
+ struct recurse_check *prev;
+ const pcre_uchar *group;
+} recurse_check;
+
static BOOL
could_be_empty_branch(const pcre_uchar *code, const pcre_uchar *endcode,
- BOOL utf, compile_data *cd)
+ BOOL utf, compile_data *cd, recurse_check *recurses)
{
register pcre_uchar c;
+recurse_check this_recurse;
+
for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
code < endcode;
code = first_significant_code(code + PRIV(OP_lengths)[c], TRUE))
@@ -2389,25 +2367,50 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
if (c == OP_RECURSE)
{
- const pcre_uchar *scode;
+ const pcre_uchar *scode = cd->start_code + GET(code, 1);
BOOL empty_branch;
- /* Test for forward reference */
+ /* Test for forward reference or uncompleted reference. This is disabled
+ when called to scan a completed pattern by setting cd->start_workspace to
+ NULL. */
- for (scode = cd->start_workspace; scode < cd->hwm; scode += LINK_SIZE)
- if ((int)GET(scode, 0) == (int)(code + 1 - cd->start_code)) return TRUE;
+ if (cd->start_workspace != NULL)
+ {
+ const pcre_uchar *tcode;
+ for (tcode = cd->start_workspace; tcode < cd->hwm; tcode += LINK_SIZE)
+ if ((int)GET(tcode, 0) == (int)(code + 1 - cd->start_code)) return TRUE;
+ if (GET(scode, 1) == 0) return TRUE; /* Unclosed */
+ }
- /* Not a forward reference, test for completed backward reference */
+ /* If we are scanning a completed pattern, there are no forward references
+ and all groups are complete. We need to detect whether this is a recursive
+ call, as otherwise there will be an infinite loop. If it is a recursion,
+ just skip over it. Simple recursions are easily detected. For mutual
+ recursions we keep a chain on the stack. */
- empty_branch = FALSE;
- scode = cd->start_code + GET(code, 1);
- if (GET(scode, 1) == 0) return TRUE; /* Unclosed */
+ else
+ {
+ recurse_check *r = recurses;
+ const pcre_uchar *endgroup = scode;
- /* Completed backwards reference */
+ do endgroup += GET(endgroup, 1); while (*endgroup == OP_ALT);
+ if (code >= scode && code <= endgroup) continue; /* Simple recursion */
+
+ for (r = recurses; r != NULL; r = r->prev)
+ if (r->group == scode) break;
+ if (r != NULL) continue; /* Mutual recursion */
+ }
+
+ /* Completed reference; scan the referenced group, remembering it on the
+ stack chain to detect mutual recursions. */
+
+ empty_branch = FALSE;
+ this_recurse.prev = recurses;
+ this_recurse.group = scode;
do
{
- if (could_be_empty_branch(scode, endcode, utf, cd))
+ if (could_be_empty_branch(scode, endcode, utf, cd, &this_recurse))
{
empty_branch = TRUE;
break;
@@ -2463,7 +2466,7 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
empty_branch = FALSE;
do
{
- if (!empty_branch && could_be_empty_branch(code, endcode, utf, cd))
+ if (!empty_branch && could_be_empty_branch(code, endcode, utf, cd, NULL))
empty_branch = TRUE;
code += GET(code, 1);
}
@@ -2505,15 +2508,19 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
case OP_CRMINSTAR:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSQUERY:
break;
default: /* Non-repeat => class must match */
case OP_CRPLUS: /* These repeats aren't empty */
case OP_CRMINPLUS:
+ case OP_CRPOSPLUS:
return FALSE;
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
if (GET2(ccode, 1) > 0) return FALSE; /* Minimum > 0 */
break;
}
@@ -2521,34 +2528,57 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
/* Opcodes that must match a character */
+ case OP_ANY:
+ case OP_ALLANY:
+ case OP_ANYBYTE:
+
case OP_PROP:
case OP_NOTPROP:
+ case OP_ANYNL:
+
+ case OP_NOT_HSPACE:
+ case OP_HSPACE:
+ case OP_NOT_VSPACE:
+ case OP_VSPACE:
case OP_EXTUNI:
+
case OP_NOT_DIGIT:
case OP_DIGIT:
case OP_NOT_WHITESPACE:
case OP_WHITESPACE:
case OP_NOT_WORDCHAR:
case OP_WORDCHAR:
- case OP_ANY:
- case OP_ALLANY:
- case OP_ANYBYTE:
+
case OP_CHAR:
case OP_CHARI:
case OP_NOT:
case OP_NOTI:
+
case OP_PLUS:
+ case OP_PLUSI:
case OP_MINPLUS:
- case OP_POSPLUS:
- case OP_EXACT:
+ case OP_MINPLUSI:
+
case OP_NOTPLUS:
+ case OP_NOTPLUSI:
case OP_NOTMINPLUS:
+ case OP_NOTMINPLUSI:
+
+ case OP_POSPLUS:
+ case OP_POSPLUSI:
case OP_NOTPOSPLUS:
+ case OP_NOTPOSPLUSI:
+
+ case OP_EXACT:
+ case OP_EXACTI:
case OP_NOTEXACT:
+ case OP_NOTEXACTI:
+
case OP_TYPEPLUS:
case OP_TYPEMINPLUS:
case OP_TYPEPOSPLUS:
case OP_TYPEEXACT:
+
return FALSE;
/* These are going to continue, as they may be empty, but we have to
@@ -2582,30 +2612,58 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
return TRUE;
/* In UTF-8 mode, STAR, MINSTAR, POSSTAR, QUERY, MINQUERY, POSQUERY, UPTO,
- MINUPTO, and POSUPTO may be followed by a multibyte character */
+ MINUPTO, and POSUPTO and their caseless and negative versions may be
+ followed by a multibyte character. */
#if defined SUPPORT_UTF && !defined COMPILE_PCRE32
case OP_STAR:
case OP_STARI:
+ case OP_NOTSTAR:
+ case OP_NOTSTARI:
+
case OP_MINSTAR:
case OP_MINSTARI:
+ case OP_NOTMINSTAR:
+ case OP_NOTMINSTARI:
+
case OP_POSSTAR:
case OP_POSSTARI:
+ case OP_NOTPOSSTAR:
+ case OP_NOTPOSSTARI:
+
case OP_QUERY:
case OP_QUERYI:
+ case OP_NOTQUERY:
+ case OP_NOTQUERYI:
+
case OP_MINQUERY:
case OP_MINQUERYI:
+ case OP_NOTMINQUERY:
+ case OP_NOTMINQUERYI:
+
case OP_POSQUERY:
case OP_POSQUERYI:
+ case OP_NOTPOSQUERY:
+ case OP_NOTPOSQUERYI:
+
if (utf && HAS_EXTRALEN(code[1])) code += GET_EXTRALEN(code[1]);
break;
case OP_UPTO:
case OP_UPTOI:
+ case OP_NOTUPTO:
+ case OP_NOTUPTOI:
+
case OP_MINUPTO:
case OP_MINUPTOI:
+ case OP_NOTMINUPTO:
+ case OP_NOTMINUPTOI:
+
case OP_POSUPTO:
case OP_POSUPTOI:
+ case OP_NOTPOSUPTO:
+ case OP_NOTPOSUPTOI:
+
if (utf && HAS_EXTRALEN(code[1 + IMM2_SIZE])) code += GET_EXTRALEN(code[1 + IMM2_SIZE]);
break;
#endif
@@ -2616,9 +2674,6 @@ for (code = first_significant_code(code + PRIV(OP_lengths)[*code], TRUE);
case OP_MARK:
case OP_PRUNE_ARG:
case OP_SKIP_ARG:
- code += code[1];
- break;
-
case OP_THEN_ARG:
code += code[1];
break;
@@ -2662,7 +2717,7 @@ could_be_empty(const pcre_uchar *code, const pcre_uchar *endcode,
{
while (bcptr != NULL && bcptr->current_branch >= code)
{
- if (!could_be_empty_branch(bcptr->current_branch, endcode, utf, cd))
+ if (!could_be_empty_branch(bcptr->current_branch, endcode, utf, cd, NULL))
return FALSE;
bcptr = bcptr->outer;
}
@@ -2672,6 +2727,1072 @@ return TRUE;
/*************************************************
+* Base opcode of repeated opcodes *
+*************************************************/
+
+/* Returns the base opcode for repeated single character type opcodes. If the
+opcode is not a repeated character type, it returns with the original value.
+
+Arguments: c opcode
+Returns: base opcode for the type
+*/
+
+static pcre_uchar
+get_repeat_base(pcre_uchar c)
+{
+return (c > OP_TYPEPOSUPTO)? c :
+ (c >= OP_TYPESTAR)? OP_TYPESTAR :
+ (c >= OP_NOTSTARI)? OP_NOTSTARI :
+ (c >= OP_NOTSTAR)? OP_NOTSTAR :
+ (c >= OP_STARI)? OP_STARI :
+ OP_STAR;
+}
+
+
+
+#ifdef SUPPORT_UCP
+/*************************************************
+* Check a character and a property *
+*************************************************/
+
+/* This function is called by check_auto_possessive() when a property item
+is adjacent to a fixed character.
+
+Arguments:
+ c the character
+ ptype the property type
+ pdata the data for the type
+ negated TRUE if it's a negated property (\P or \p{^)
+
+Returns: TRUE if auto-possessifying is OK
+*/
+
+static BOOL
+check_char_prop(pcre_uint32 c, unsigned int ptype, unsigned int pdata,
+ BOOL negated)
+{
+const pcre_uint32 *p;
+const ucd_record *prop = GET_UCD(c);
+
+switch(ptype)
+ {
+ case PT_LAMP:
+ return (prop->chartype == ucp_Lu ||
+ prop->chartype == ucp_Ll ||
+ prop->chartype == ucp_Lt) == negated;
+
+ case PT_GC:
+ return (pdata == PRIV(ucp_gentype)[prop->chartype]) == negated;
+
+ case PT_PC:
+ return (pdata == prop->chartype) == negated;
+
+ case PT_SC:
+ return (pdata == prop->script) == negated;
+
+ /* These are specials */
+
+ case PT_ALNUM:
+ return (PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
+ PRIV(ucp_gentype)[prop->chartype] == ucp_N) == negated;
+
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included, which
+ means that Perl space and POSIX space are now identical. PCRE was changed
+ at release 8.34. */
+
+ case PT_SPACE: /* Perl space */
+ case PT_PXSPACE: /* POSIX space */
+ switch(c)
+ {
+ HSPACE_CASES:
+ VSPACE_CASES:
+ return negated;
+
+ default:
+ return (PRIV(ucp_gentype)[prop->chartype] == ucp_Z) == negated;
+ }
+ break; /* Control never reaches here */
+
+ case PT_WORD:
+ return (PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
+ PRIV(ucp_gentype)[prop->chartype] == ucp_N ||
+ c == CHAR_UNDERSCORE) == negated;
+
+ case PT_CLIST:
+ p = PRIV(ucd_caseless_sets) + prop->caseset;
+ for (;;)
+ {
+ if (c < *p) return !negated;
+ if (c == *p++) return negated;
+ }
+ break; /* Control never reaches here */
+ }
+
+return FALSE;
+}
+#endif /* SUPPORT_UCP */
+
+
+
+/*************************************************
+* Fill the character property list *
+*************************************************/
+
+/* Checks whether the code points to an opcode that can take part in auto-
+possessification, and if so, fills a list with its properties.
+
+Arguments:
+ code points to start of expression
+ utf TRUE if in UTF-8 / UTF-16 / UTF-32 mode
+ fcc points to case-flipping table
+ list points to output list
+ list[0] will be filled with the opcode
+ list[1] will be non-zero if this opcode
+ can match an empty character string
+ list[2..7] depends on the opcode
+
+Returns: points to the start of the next opcode if *code is accepted
+ NULL if *code is not accepted
+*/
+
+static const pcre_uchar *
+get_chr_property_list(const pcre_uchar *code, BOOL utf,
+ const pcre_uint8 *fcc, pcre_uint32 *list)
+{
+pcre_uchar c = *code;
+pcre_uchar base;
+const pcre_uchar *end;
+pcre_uint32 chr;
+
+#ifdef SUPPORT_UCP
+pcre_uint32 *clist_dest;
+const pcre_uint32 *clist_src;
+#else
+utf = utf; /* Suppress "unused parameter" compiler warning */
+#endif
+
+list[0] = c;
+list[1] = FALSE;
+code++;
+
+if (c >= OP_STAR && c <= OP_TYPEPOSUPTO)
+ {
+ base = get_repeat_base(c);
+ c -= (base - OP_STAR);
+
+ if (c == OP_UPTO || c == OP_MINUPTO || c == OP_EXACT || c == OP_POSUPTO)
+ code += IMM2_SIZE;
+
+ list[1] = (c != OP_PLUS && c != OP_MINPLUS && c != OP_EXACT && c != OP_POSPLUS);
+
+ switch(base)
+ {
+ case OP_STAR:
+ list[0] = OP_CHAR;
+ break;
+
+ case OP_STARI:
+ list[0] = OP_CHARI;
+ break;
+
+ case OP_NOTSTAR:
+ list[0] = OP_NOT;
+ break;
+
+ case OP_NOTSTARI:
+ list[0] = OP_NOTI;
+ break;
+
+ case OP_TYPESTAR:
+ list[0] = *code;
+ code++;
+ break;
+ }
+ c = list[0];
+ }
+
+switch(c)
+ {
+ case OP_NOT_DIGIT:
+ case OP_DIGIT:
+ case OP_NOT_WHITESPACE:
+ case OP_WHITESPACE:
+ case OP_NOT_WORDCHAR:
+ case OP_WORDCHAR:
+ case OP_ANY:
+ case OP_ALLANY:
+ case OP_ANYNL:
+ case OP_NOT_HSPACE:
+ case OP_HSPACE:
+ case OP_NOT_VSPACE:
+ case OP_VSPACE:
+ case OP_EXTUNI:
+ case OP_EODN:
+ case OP_EOD:
+ case OP_DOLL:
+ case OP_DOLLM:
+ return code;
+
+ case OP_CHAR:
+ case OP_NOT:
+ GETCHARINCTEST(chr, code);
+ list[2] = chr;
+ list[3] = NOTACHAR;
+ return code;
+
+ case OP_CHARI:
+ case OP_NOTI:
+ list[0] = (c == OP_CHARI) ? OP_CHAR : OP_NOT;
+ GETCHARINCTEST(chr, code);
+ list[2] = chr;
+
+#ifdef SUPPORT_UCP
+ if (chr < 128 || (chr < 256 && !utf))
+ list[3] = fcc[chr];
+ else
+ list[3] = UCD_OTHERCASE(chr);
+#elif defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ list[3] = (chr < 256) ? fcc[chr] : chr;
+#else
+ list[3] = fcc[chr];
+#endif
+
+ /* The othercase might be the same value. */
+
+ if (chr == list[3])
+ list[3] = NOTACHAR;
+ else
+ list[4] = NOTACHAR;
+ return code;
+
+#ifdef SUPPORT_UCP
+ case OP_PROP:
+ case OP_NOTPROP:
+ if (code[0] != PT_CLIST)
+ {
+ list[2] = code[0];
+ list[3] = code[1];
+ return code + 2;
+ }
+
+ /* Convert only if we have enough space. */
+
+ clist_src = PRIV(ucd_caseless_sets) + code[1];
+ clist_dest = list + 2;
+ code += 2;
+
+ do {
+ if (clist_dest >= list + 8)
+ {
+ /* Early return if there is not enough space. This should never
+ happen, since all clists are shorter than 5 character now. */
+ list[2] = code[0];
+ list[3] = code[1];
+ return code;
+ }
+ *clist_dest++ = *clist_src;
+ }
+ while(*clist_src++ != NOTACHAR);
+
+ /* All characters are stored. The terminating NOTACHAR
+ is copied form the clist itself. */
+
+ list[0] = (c == OP_PROP) ? OP_CHAR : OP_NOT;
+ return code;
+#endif
+
+ case OP_NCLASS:
+ case OP_CLASS:
+#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ case OP_XCLASS:
+ if (c == OP_XCLASS)
+ end = code + GET(code, 0) - 1;
+ else
+#endif
+ end = code + 32 / sizeof(pcre_uchar);
+
+ switch(*end)
+ {
+ case OP_CRSTAR:
+ case OP_CRMINSTAR:
+ case OP_CRQUERY:
+ case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSQUERY:
+ list[1] = TRUE;
+ end++;
+ break;
+
+ case OP_CRPLUS:
+ case OP_CRMINPLUS:
+ case OP_CRPOSPLUS:
+ end++;
+ break;
+
+ case OP_CRRANGE:
+ case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
+ list[1] = (GET2(end, 1) == 0);
+ end += 1 + 2 * IMM2_SIZE;
+ break;
+ }
+ list[2] = end - code;
+ return end;
+ }
+return NULL; /* Opcode not accepted */
+}
+
+
+
+/*************************************************
+* Scan further character sets for match *
+*************************************************/
+
+/* Checks whether the base and the current opcode have a common character, in
+which case the base cannot be possessified.
+
+Arguments:
+ code points to the byte code
+ utf TRUE in UTF-8 / UTF-16 / UTF-32 mode
+ cd static compile data
+ base_list the data list of the base opcode
+
+Returns: TRUE if the auto-possessification is possible
+*/
+
+static BOOL
+compare_opcodes(const pcre_uchar *code, BOOL utf, const compile_data *cd,
+ const pcre_uint32 *base_list, const pcre_uchar *base_end)
+{
+pcre_uchar c;
+pcre_uint32 list[8];
+const pcre_uint32 *chr_ptr;
+const pcre_uint32 *ochr_ptr;
+const pcre_uint32 *list_ptr;
+const pcre_uchar *next_code;
+const pcre_uint8 *class_bitset;
+const pcre_uint32 *set1, *set2, *set_end;
+pcre_uint32 chr;
+BOOL accepted, invert_bits;
+
+/* Note: the base_list[1] contains whether the current opcode has greedy
+(represented by a non-zero value) quantifier. This is a different from
+other character type lists, which stores here that the character iterator
+matches to an empty string (also represented by a non-zero value). */
+
+for(;;)
+ {
+ /* All operations move the code pointer forward.
+ Therefore infinite recursions are not possible. */
+
+ c = *code;
+
+ /* Skip over callouts */
+
+ if (c == OP_CALLOUT)
+ {
+ code += PRIV(OP_lengths)[c];
+ continue;
+ }
+
+ if (c == OP_ALT)
+ {
+ do code += GET(code, 1); while (*code == OP_ALT);
+ c = *code;
+ }
+
+ switch(c)
+ {
+ case OP_END:
+ case OP_KETRPOS:
+ /* TRUE only in greedy case. The non-greedy case could be replaced by
+ an OP_EXACT, but it is probably not worth it. (And note that OP_EXACT
+ uses more memory, which we cannot get at this stage.) */
+
+ return base_list[1] != 0;
+
+ case OP_KET:
+ /* If the bracket is capturing, and referenced by an OP_RECURSE, or
+ it is an atomic sub-pattern (assert, once, etc.) the non-greedy case
+ cannot be converted to a possessive form. */
+
+ if (base_list[1] == 0) return FALSE;
+
+ switch(*(code - GET(code, 1)))
+ {
+ case OP_ASSERT:
+ case OP_ASSERT_NOT:
+ case OP_ASSERTBACK:
+ case OP_ASSERTBACK_NOT:
+ case OP_ONCE:
+ case OP_ONCE_NC:
+ /* Atomic sub-patterns and assertions can always auto-possessify their
+ last iterator. */
+ return TRUE;
+ }
+
+ code += PRIV(OP_lengths)[c];
+ continue;
+
+ case OP_ONCE:
+ case OP_ONCE_NC:
+ case OP_BRA:
+ case OP_CBRA:
+ next_code = code + GET(code, 1);
+ code += PRIV(OP_lengths)[c];
+
+ while (*next_code == OP_ALT)
+ {
+ if (!compare_opcodes(code, utf, cd, base_list, base_end)) return FALSE;
+ code = next_code + 1 + LINK_SIZE;
+ next_code += GET(next_code, 1);
+ }
+ continue;
+
+ case OP_BRAZERO:
+ case OP_BRAMINZERO:
+
+ next_code = code + 1;
+ if (*next_code != OP_BRA && *next_code != OP_CBRA
+ && *next_code != OP_ONCE && *next_code != OP_ONCE_NC) return FALSE;
+
+ do next_code += GET(next_code, 1); while (*next_code == OP_ALT);
+
+ /* The bracket content will be checked by the
+ OP_BRA/OP_CBRA case above. */
+ next_code += 1 + LINK_SIZE;
+ if (!compare_opcodes(next_code, utf, cd, base_list, base_end))
+ return FALSE;
+
+ code += PRIV(OP_lengths)[c];
+ continue;
+ }
+
+ /* Check for a supported opcode, and load its properties. */
+
+ code = get_chr_property_list(code, utf, cd->fcc, list);
+ if (code == NULL) return FALSE; /* Unsupported */
+
+ /* If either opcode is a small character list, set pointers for comparing
+ characters from that list with another list, or with a property. */
+
+ if (base_list[0] == OP_CHAR)
+ {
+ chr_ptr = base_list + 2;
+ list_ptr = list;
+ }
+ else if (list[0] == OP_CHAR)
+ {
+ chr_ptr = list + 2;
+ list_ptr = base_list;
+ }
+
+ /* Character bitsets can also be compared to certain opcodes. */
+
+ else if (base_list[0] == OP_CLASS || list[0] == OP_CLASS
+#ifdef COMPILE_PCRE8
+ /* In 8 bit, non-UTF mode, OP_CLASS and OP_NCLASS are the same. */
+ || (!utf && (base_list[0] == OP_NCLASS || list[0] == OP_NCLASS))
+#endif
+ )
+ {
+#ifdef COMPILE_PCRE8
+ if (base_list[0] == OP_CLASS || (!utf && base_list[0] == OP_NCLASS))
+#else
+ if (base_list[0] == OP_CLASS)
+#endif
+ {
+ set1 = (pcre_uint32 *)(base_end - base_list[2]);
+ list_ptr = list;
+ }
+ else
+ {
+ set1 = (pcre_uint32 *)(code - list[2]);
+ list_ptr = base_list;
+ }
+
+ invert_bits = FALSE;
+ switch(list_ptr[0])
+ {
+ case OP_CLASS:
+ case OP_NCLASS:
+ set2 = (pcre_uint32 *)
+ ((list_ptr == list ? code : base_end) - list_ptr[2]);
+ break;
+
+ /* OP_XCLASS cannot be supported here, because its bitset
+ is not necessarily complete. E.g: [a-\0x{200}] is stored
+ as a character range, and the appropriate bits are not set. */
+
+ case OP_NOT_DIGIT:
+ invert_bits = TRUE;
+ /* Fall through */
+ case OP_DIGIT:
+ set2 = (pcre_uint32 *)(cd->cbits + cbit_digit);
+ break;
+
+ case OP_NOT_WHITESPACE:
+ invert_bits = TRUE;
+ /* Fall through */
+ case OP_WHITESPACE:
+ set2 = (pcre_uint32 *)(cd->cbits + cbit_space);
+ break;
+
+ case OP_NOT_WORDCHAR:
+ invert_bits = TRUE;
+ /* Fall through */
+ case OP_WORDCHAR:
+ set2 = (pcre_uint32 *)(cd->cbits + cbit_word);
+ break;
+
+ default:
+ return FALSE;
+ }
+
+ /* Compare 4 bytes to improve speed. */
+ set_end = set1 + (32 / 4);
+ if (invert_bits)
+ {
+ do
+ {
+ if ((*set1++ & ~(*set2++)) != 0) return FALSE;
+ }
+ while (set1 < set_end);
+ }
+ else
+ {
+ do
+ {
+ if ((*set1++ & *set2++) != 0) return FALSE;
+ }
+ while (set1 < set_end);
+ }
+
+ if (list[1] == 0) return TRUE;
+ /* Might be an empty repeat. */
+ continue;
+ }
+
+ /* Some property combinations also acceptable. Unicode property opcodes are
+ processed specially; the rest can be handled with a lookup table. */
+
+ else
+ {
+ pcre_uint32 leftop, rightop;
+
+ leftop = base_list[0];
+ rightop = list[0];
+
+#ifdef SUPPORT_UCP
+ accepted = FALSE; /* Always set in non-unicode case. */
+ if (leftop == OP_PROP || leftop == OP_NOTPROP)
+ {
+ if (rightop == OP_EOD)
+ accepted = TRUE;
+ else if (rightop == OP_PROP || rightop == OP_NOTPROP)
+ {
+ int n;
+ const pcre_uint8 *p;
+ BOOL same = leftop == rightop;
+ BOOL lisprop = leftop == OP_PROP;
+ BOOL risprop = rightop == OP_PROP;
+ BOOL bothprop = lisprop && risprop;
+
+ /* There's a table that specifies how each combination is to be
+ processed:
+ 0 Always return FALSE (never auto-possessify)
+ 1 Character groups are distinct (possessify if both are OP_PROP)
+ 2 Check character categories in the same group (general or particular)
+ 3 Return TRUE if the two opcodes are not the same
+ ... see comments below
+ */
+
+ n = propposstab[base_list[2]][list[2]];
+ switch(n)
+ {
+ case 0: break;
+ case 1: accepted = bothprop; break;
+ case 2: accepted = (base_list[3] == list[3]) != same; break;
+ case 3: accepted = !same; break;
+
+ case 4: /* Left general category, right particular category */
+ accepted = risprop && catposstab[base_list[3]][list[3]] == same;
+ break;
+
+ case 5: /* Right general category, left particular category */
+ accepted = lisprop && catposstab[list[3]][base_list[3]] == same;
+ break;
+
+ /* This code is logically tricky. Think hard before fiddling with it.
+ The posspropstab table has four entries per row. Each row relates to
+ one of PCRE's special properties such as ALNUM or SPACE or WORD.
+ Only WORD actually needs all four entries, but using repeats for the
+ others means they can all use the same code below.
+
+ The first two entries in each row are Unicode general categories, and
+ apply always, because all the characters they include are part of the
+ PCRE character set. The third and fourth entries are a general and a
+ particular category, respectively, that include one or more relevant
+ characters. One or the other is used, depending on whether the check
+ is for a general or a particular category. However, in both cases the
+ category contains more characters than the specials that are defined
+ for the property being tested against. Therefore, it cannot be used
+ in a NOTPROP case.
+
+ Example: the row for WORD contains ucp_L, ucp_N, ucp_P, ucp_Po.
+ Underscore is covered by ucp_P or ucp_Po. */
+
+ case 6: /* Left alphanum vs right general category */
+ case 7: /* Left space vs right general category */
+ case 8: /* Left word vs right general category */
+ p = posspropstab[n-6];
+ accepted = risprop && lisprop ==
+ (list[3] != p[0] &&
+ list[3] != p[1] &&
+ (list[3] != p[2] || !lisprop));
+ break;
+
+ case 9: /* Right alphanum vs left general category */
+ case 10: /* Right space vs left general category */
+ case 11: /* Right word vs left general category */
+ p = posspropstab[n-9];
+ accepted = lisprop && risprop ==
+ (base_list[3] != p[0] &&
+ base_list[3] != p[1] &&
+ (base_list[3] != p[2] || !risprop));
+ break;
+
+ case 12: /* Left alphanum vs right particular category */
+ case 13: /* Left space vs right particular category */
+ case 14: /* Left word vs right particular category */
+ p = posspropstab[n-12];
+ accepted = risprop && lisprop ==
+ (catposstab[p[0]][list[3]] &&
+ catposstab[p[1]][list[3]] &&
+ (list[3] != p[3] || !lisprop));
+ break;
+
+ case 15: /* Right alphanum vs left particular category */
+ case 16: /* Right space vs left particular category */
+ case 17: /* Right word vs left particular category */
+ p = posspropstab[n-15];
+ accepted = lisprop && risprop ==
+ (catposstab[p[0]][base_list[3]] &&
+ catposstab[p[1]][base_list[3]] &&
+ (base_list[3] != p[3] || !risprop));
+ break;
+ }
+ }
+ }
+
+ else
+#endif /* SUPPORT_UCP */
+
+ accepted = leftop >= FIRST_AUTOTAB_OP && leftop <= LAST_AUTOTAB_LEFT_OP &&
+ rightop >= FIRST_AUTOTAB_OP && rightop <= LAST_AUTOTAB_RIGHT_OP &&
+ autoposstab[leftop - FIRST_AUTOTAB_OP][rightop - FIRST_AUTOTAB_OP];
+
+ if (!accepted)
+ return FALSE;
+
+ if (list[1] == 0) return TRUE;
+ /* Might be an empty repeat. */
+ continue;
+ }
+
+ /* Control reaches here only if one of the items is a small character list.
+ All characters are checked against the other side. */
+
+ do
+ {
+ chr = *chr_ptr;
+
+ switch(list_ptr[0])
+ {
+ case OP_CHAR:
+ ochr_ptr = list_ptr + 2;
+ do
+ {
+ if (chr == *ochr_ptr) return FALSE;
+ ochr_ptr++;
+ }
+ while(*ochr_ptr != NOTACHAR);
+ break;
+
+ case OP_NOT:
+ ochr_ptr = list_ptr + 2;
+ do
+ {
+ if (chr == *ochr_ptr)
+ break;
+ ochr_ptr++;
+ }
+ while(*ochr_ptr != NOTACHAR);
+ if (*ochr_ptr == NOTACHAR) return FALSE; /* Not found */
+ break;
+
+ /* Note that OP_DIGIT etc. are generated only when PCRE_UCP is *not*
+ set. When it is set, \d etc. are converted into OP_(NOT_)PROP codes. */
+
+ case OP_DIGIT:
+ if (chr < 256 && (cd->ctypes[chr] & ctype_digit) != 0) return FALSE;
+ break;
+
+ case OP_NOT_DIGIT:
+ if (chr > 255 || (cd->ctypes[chr] & ctype_digit) == 0) return FALSE;
+ break;
+
+ case OP_WHITESPACE:
+ if (chr < 256 && (cd->ctypes[chr] & ctype_space) != 0) return FALSE;
+ break;
+
+ case OP_NOT_WHITESPACE:
+ if (chr > 255 || (cd->ctypes[chr] & ctype_space) == 0) return FALSE;
+ break;
+
+ case OP_WORDCHAR:
+ if (chr < 255 && (cd->ctypes[chr] & ctype_word) != 0) return FALSE;
+ break;
+
+ case OP_NOT_WORDCHAR:
+ if (chr > 255 || (cd->ctypes[chr] & ctype_word) == 0) return FALSE;
+ break;
+
+ case OP_HSPACE:
+ switch(chr)
+ {
+ HSPACE_CASES: return FALSE;
+ default: break;
+ }
+ break;
+
+ case OP_NOT_HSPACE:
+ switch(chr)
+ {
+ HSPACE_CASES: break;
+ default: return FALSE;
+ }
+ break;
+
+ case OP_ANYNL:
+ case OP_VSPACE:
+ switch(chr)
+ {
+ VSPACE_CASES: return FALSE;
+ default: break;
+ }
+ break;
+
+ case OP_NOT_VSPACE:
+ switch(chr)
+ {
+ VSPACE_CASES: break;
+ default: return FALSE;
+ }
+ break;
+
+ case OP_DOLL:
+ case OP_EODN:
+ switch (chr)
+ {
+ case CHAR_CR:
+ case CHAR_LF:
+ case CHAR_VT:
+ case CHAR_FF:
+ case CHAR_NEL:
+#ifndef EBCDIC
+ case 0x2028:
+ case 0x2029:
+#endif /* Not EBCDIC */
+ return FALSE;
+ }
+ break;
+
+ case OP_EOD: /* Can always possessify before \z */
+ break;
+
+#ifdef SUPPORT_UCP
+ case OP_PROP:
+ case OP_NOTPROP:
+ if (!check_char_prop(chr, list_ptr[2], list_ptr[3],
+ list_ptr[0] == OP_NOTPROP))
+ return FALSE;
+ break;
+#endif
+
+ case OP_NCLASS:
+ if (chr > 255) return FALSE;
+ /* Fall through */
+
+ case OP_CLASS:
+ if (chr > 255) break;
+ class_bitset = (pcre_uint8 *)
+ ((list_ptr == list ? code : base_end) - list_ptr[2]);
+ if ((class_bitset[chr >> 3] & (1 << (chr & 7))) != 0) return FALSE;
+ break;
+
+#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ case OP_XCLASS:
+ if (PRIV(xclass)(chr, (list_ptr == list ? code : base_end) -
+ list_ptr[2] + LINK_SIZE, utf)) return FALSE;
+ break;
+#endif
+
+ default:
+ return FALSE;
+ }
+
+ chr_ptr++;
+ }
+ while(*chr_ptr != NOTACHAR);
+
+ /* At least one character must be matched from this opcode. */
+
+ if (list[1] == 0) return TRUE;
+ }
+
+return FALSE;
+}
+
+
+
+/*************************************************
+* Scan compiled regex for auto-possession *
+*************************************************/
+
+/* Replaces single character iterations with their possessive alternatives
+if appropriate. This function modifies the compiled opcode!
+
+Arguments:
+ code points to start of the byte code
+ utf TRUE in UTF-8 / UTF-16 / UTF-32 mode
+ cd static compile data
+
+Returns: nothing
+*/
+
+static void
+auto_possessify(pcre_uchar *code, BOOL utf, const compile_data *cd)
+{
+register pcre_uchar c;
+const pcre_uchar *end;
+pcre_uchar *repeat_opcode;
+pcre_uint32 list[8];
+
+for (;;)
+ {
+ c = *code;
+
+ if (c >= OP_STAR && c <= OP_TYPEPOSUPTO)
+ {
+ c -= get_repeat_base(c) - OP_STAR;
+ end = (c <= OP_MINUPTO) ?
+ get_chr_property_list(code, utf, cd->fcc, list) : NULL;
+ list[1] = c == OP_STAR || c == OP_PLUS || c == OP_QUERY || c == OP_UPTO;
+
+ if (end != NULL && compare_opcodes(end, utf, cd, list, end))
+ {
+ switch(c)
+ {
+ case OP_STAR:
+ *code += OP_POSSTAR - OP_STAR;
+ break;
+
+ case OP_MINSTAR:
+ *code += OP_POSSTAR - OP_MINSTAR;
+ break;
+
+ case OP_PLUS:
+ *code += OP_POSPLUS - OP_PLUS;
+ break;
+
+ case OP_MINPLUS:
+ *code += OP_POSPLUS - OP_MINPLUS;
+ break;
+
+ case OP_QUERY:
+ *code += OP_POSQUERY - OP_QUERY;
+ break;
+
+ case OP_MINQUERY:
+ *code += OP_POSQUERY - OP_MINQUERY;
+ break;
+
+ case OP_UPTO:
+ *code += OP_POSUPTO - OP_UPTO;
+ break;
+
+ case OP_MINUPTO:
+ *code += OP_MINUPTO - OP_UPTO;
+ break;
+ }
+ }
+ c = *code;
+ }
+ else if (c == OP_CLASS || c == OP_NCLASS || c == OP_XCLASS)
+ {
+#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ if (c == OP_XCLASS)
+ repeat_opcode = code + GET(code, 1);
+ else
+#endif
+ repeat_opcode = code + 1 + (32 / sizeof(pcre_uchar));
+
+ c = *repeat_opcode;
+ if (c >= OP_CRSTAR && c <= OP_CRMINRANGE)
+ {
+ /* end must not be NULL. */
+ end = get_chr_property_list(code, utf, cd->fcc, list);
+
+ list[1] = (c & 1) == 0;
+
+ if (compare_opcodes(end, utf, cd, list, end))
+ {
+ switch (c)
+ {
+ case OP_CRSTAR:
+ case OP_CRMINSTAR:
+ *repeat_opcode = OP_CRPOSSTAR;
+ break;
+
+ case OP_CRPLUS:
+ case OP_CRMINPLUS:
+ *repeat_opcode = OP_CRPOSPLUS;
+ break;
+
+ case OP_CRQUERY:
+ case OP_CRMINQUERY:
+ *repeat_opcode = OP_CRPOSQUERY;
+ break;
+
+ case OP_CRRANGE:
+ case OP_CRMINRANGE:
+ *repeat_opcode = OP_CRPOSRANGE;
+ break;
+ }
+ }
+ }
+ c = *code;
+ }
+
+ switch(c)
+ {
+ case OP_END:
+ return;
+
+ case OP_TYPESTAR:
+ case OP_TYPEMINSTAR:
+ case OP_TYPEPLUS:
+ case OP_TYPEMINPLUS:
+ case OP_TYPEQUERY:
+ case OP_TYPEMINQUERY:
+ case OP_TYPEPOSSTAR:
+ case OP_TYPEPOSPLUS:
+ case OP_TYPEPOSQUERY:
+ if (code[1] == OP_PROP || code[1] == OP_NOTPROP) code += 2;
+ break;
+
+ case OP_TYPEUPTO:
+ case OP_TYPEMINUPTO:
+ case OP_TYPEEXACT:
+ case OP_TYPEPOSUPTO:
+ if (code[1 + IMM2_SIZE] == OP_PROP || code[1 + IMM2_SIZE] == OP_NOTPROP)
+ code += 2;
+ break;
+
+#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ case OP_XCLASS:
+ code += GET(code, 1);
+ break;
+#endif
+
+ case OP_MARK:
+ case OP_PRUNE_ARG:
+ case OP_SKIP_ARG:
+ case OP_THEN_ARG:
+ code += code[1];
+ break;
+ }
+
+ /* Add in the fixed length from the table */
+
+ code += PRIV(OP_lengths)[c];
+
+ /* In UTF-8 mode, opcodes that are followed by a character may be followed by
+ a multi-byte character. The length in the table is a minimum, so we have to
+ arrange to skip the extra bytes. */
+
+#if defined SUPPORT_UTF && !defined COMPILE_PCRE32
+ if (utf) switch(c)
+ {
+ case OP_CHAR:
+ case OP_CHARI:
+ case OP_NOT:
+ case OP_NOTI:
+ case OP_STAR:
+ case OP_MINSTAR:
+ case OP_PLUS:
+ case OP_MINPLUS:
+ case OP_QUERY:
+ case OP_MINQUERY:
+ case OP_UPTO:
+ case OP_MINUPTO:
+ case OP_EXACT:
+ case OP_POSSTAR:
+ case OP_POSPLUS:
+ case OP_POSQUERY:
+ case OP_POSUPTO:
+ case OP_STARI:
+ case OP_MINSTARI:
+ case OP_PLUSI:
+ case OP_MINPLUSI:
+ case OP_QUERYI:
+ case OP_MINQUERYI:
+ case OP_UPTOI:
+ case OP_MINUPTOI:
+ case OP_EXACTI:
+ case OP_POSSTARI:
+ case OP_POSPLUSI:
+ case OP_POSQUERYI:
+ case OP_POSUPTOI:
+ case OP_NOTSTAR:
+ case OP_NOTMINSTAR:
+ case OP_NOTPLUS:
+ case OP_NOTMINPLUS:
+ case OP_NOTQUERY:
+ case OP_NOTMINQUERY:
+ case OP_NOTUPTO:
+ case OP_NOTMINUPTO:
+ case OP_NOTEXACT:
+ case OP_NOTPOSSTAR:
+ case OP_NOTPOSPLUS:
+ case OP_NOTPOSQUERY:
+ case OP_NOTPOSUPTO:
+ case OP_NOTSTARI:
+ case OP_NOTMINSTARI:
+ case OP_NOTPLUSI:
+ case OP_NOTMINPLUSI:
+ case OP_NOTQUERYI:
+ case OP_NOTMINQUERYI:
+ case OP_NOTUPTOI:
+ case OP_NOTMINUPTOI:
+ case OP_NOTEXACTI:
+ case OP_NOTPOSSTARI:
+ case OP_NOTPOSPLUSI:
+ case OP_NOTPOSQUERYI:
+ case OP_NOTPOSUPTOI:
+ if (HAS_EXTRALEN(code[-1])) code += GET_EXTRALEN(code[-1]);
+ break;
+ }
+#else
+ (void)(utf); /* Keep compiler happy by referencing function argument */
+#endif
+ }
+}
+
+
+
+/*************************************************
* Check for POSIX class syntax *
*************************************************/
@@ -2692,7 +3813,7 @@ class, but [abc[:x\]pqr:]] is (so that an error can be generated). The code
below handles the special case of \], but does not try to do any other escape
processing. This makes it different from Perl for cases such as [:l\ower:]
where Perl recognizes it as the POSIX class "lower" but PCRE does not recognize
-"l\ower". This is a lesser evil that not diagnosing bad classes when Perl does,
+"l\ower". This is a lesser evil than not diagnosing bad classes when Perl does,
I think.
A user pointed out that PCRE was rejecting [:a[:digit:]] whereas Perl was not.
@@ -2954,476 +4075,11 @@ for (++c; c <= d; c++)
*cptr = c; /* Rest of input range */
return 0;
}
-
-
-
-/*************************************************
-* Check a character and a property *
-*************************************************/
-
-/* This function is called by check_auto_possessive() when a property item
-is adjacent to a fixed character.
-
-Arguments:
- c the character
- ptype the property type
- pdata the data for the type
- negated TRUE if it's a negated property (\P or \p{^)
-
-Returns: TRUE if auto-possessifying is OK
-*/
-
-static BOOL
-check_char_prop(pcre_uint32 c, unsigned int ptype, unsigned int pdata, BOOL negated)
-{
-#ifdef SUPPORT_UCP
-const pcre_uint32 *p;
-#endif
-
-const ucd_record *prop = GET_UCD(c);
-
-switch(ptype)
- {
- case PT_LAMP:
- return (prop->chartype == ucp_Lu ||
- prop->chartype == ucp_Ll ||
- prop->chartype == ucp_Lt) == negated;
-
- case PT_GC:
- return (pdata == PRIV(ucp_gentype)[prop->chartype]) == negated;
-
- case PT_PC:
- return (pdata == prop->chartype) == negated;
-
- case PT_SC:
- return (pdata == prop->script) == negated;
-
- /* These are specials */
-
- case PT_ALNUM:
- return (PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
- PRIV(ucp_gentype)[prop->chartype] == ucp_N) == negated;
-
- case PT_SPACE: /* Perl space */
- return (PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_FF || c == CHAR_CR)
- == negated;
-
- case PT_PXSPACE: /* POSIX space */
- return (PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_VT ||
- c == CHAR_FF || c == CHAR_CR)
- == negated;
-
- case PT_WORD:
- return (PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
- PRIV(ucp_gentype)[prop->chartype] == ucp_N ||
- c == CHAR_UNDERSCORE) == negated;
-
-#ifdef SUPPORT_UCP
- case PT_CLIST:
- p = PRIV(ucd_caseless_sets) + prop->caseset;
- for (;;)
- {
- if (c < *p) return !negated;
- if (c == *p++) return negated;
- }
- break; /* Control never reaches here */
-#endif
- }
-
-return FALSE;
-}
#endif /* SUPPORT_UCP */
/*************************************************
-* Check if auto-possessifying is possible *
-*************************************************/
-
-/* This function is called for unlimited repeats of certain items, to see
-whether the next thing could possibly match the repeated item. If not, it makes
-sense to automatically possessify the repeated item.
-
-Arguments:
- previous pointer to the repeated opcode
- utf TRUE in UTF-8 / UTF-16 / UTF-32 mode
- ptr next character in pattern
- options options bits
- cd contains pointers to tables etc.
-
-Returns: TRUE if possessifying is wanted
-*/
-
-static BOOL
-check_auto_possessive(const pcre_uchar *previous, BOOL utf,
- const pcre_uchar *ptr, int options, compile_data *cd)
-{
-pcre_uint32 c = NOTACHAR;
-pcre_uint32 next;
-int escape;
-pcre_uchar op_code = *previous++;
-
-/* Skip whitespace and comments in extended mode */
-
-if ((options & PCRE_EXTENDED) != 0)
- {
- for (;;)
- {
- while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_space) != 0) ptr++;
- if (*ptr == CHAR_NUMBER_SIGN)
- {
- ptr++;
- while (*ptr != CHAR_NULL)
- {
- if (IS_NEWLINE(ptr)) { ptr += cd->nllen; break; }
- ptr++;
-#ifdef SUPPORT_UTF
- if (utf) FORWARDCHAR(ptr);
-#endif
- }
- }
- else break;
- }
- }
-
-/* If the next item is one that we can handle, get its value. A non-negative
-value is a character, a negative value is an escape value. */
-
-if (*ptr == CHAR_BACKSLASH)
- {
- int temperrorcode = 0;
- escape = check_escape(&ptr, &next, &temperrorcode, cd->bracount, options, FALSE);
- if (temperrorcode != 0) return FALSE;
- ptr++; /* Point after the escape sequence */
- }
-else if (!MAX_255(*ptr) || (cd->ctypes[*ptr] & ctype_meta) == 0)
- {
- escape = 0;
-#ifdef SUPPORT_UTF
- if (utf) { GETCHARINC(next, ptr); } else
-#endif
- next = *ptr++;
- }
-else return FALSE;
-
-/* Skip whitespace and comments in extended mode */
-
-if ((options & PCRE_EXTENDED) != 0)
- {
- for (;;)
- {
- while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_space) != 0) ptr++;
- if (*ptr == CHAR_NUMBER_SIGN)
- {
- ptr++;
- while (*ptr != CHAR_NULL)
- {
- if (IS_NEWLINE(ptr)) { ptr += cd->nllen; break; }
- ptr++;
-#ifdef SUPPORT_UTF
- if (utf) FORWARDCHAR(ptr);
-#endif
- }
- }
- else break;
- }
- }
-
-/* If the next thing is itself optional, we have to give up. */
-
-if (*ptr == CHAR_ASTERISK || *ptr == CHAR_QUESTION_MARK ||
- STRNCMP_UC_C8(ptr, STR_LEFT_CURLY_BRACKET STR_0 STR_COMMA, 3) == 0)
- return FALSE;
-
-/* If the previous item is a character, get its value. */
-
-if (op_code == OP_CHAR || op_code == OP_CHARI ||
- op_code == OP_NOT || op_code == OP_NOTI)
- {
-#ifdef SUPPORT_UTF
- GETCHARTEST(c, previous);
-#else
- c = *previous;
-#endif
- }
-
-/* Now compare the next item with the previous opcode. First, handle cases when
-the next item is a character. */
-
-if (escape == 0)
- {
- /* For a caseless UTF match, the next character may have more than one other
- case, which maps to the special PT_CLIST property. Check this first. */
-
-#ifdef SUPPORT_UCP
- if (utf && c != NOTACHAR && (options & PCRE_CASELESS) != 0)
- {
- unsigned int ocs = UCD_CASESET(next);
- if (ocs > 0) return check_char_prop(c, PT_CLIST, ocs, op_code >= OP_NOT);
- }
-#endif
-
- switch(op_code)
- {
- case OP_CHAR:
- return c != next;
-
- /* For CHARI (caseless character) we must check the other case. If we have
- Unicode property support, we can use it to test the other case of
- high-valued characters. We know that next can have only one other case,
- because multi-other-case characters are dealt with above. */
-
- case OP_CHARI:
- if (c == next) return FALSE;
-#ifdef SUPPORT_UTF
- if (utf)
- {
- pcre_uint32 othercase;
- if (next < 128) othercase = cd->fcc[next]; else
-#ifdef SUPPORT_UCP
- othercase = UCD_OTHERCASE(next);
-#else
- othercase = NOTACHAR;
-#endif
- return c != othercase;
- }
- else
-#endif /* SUPPORT_UTF */
- return (c != TABLE_GET(next, cd->fcc, next)); /* Not UTF */
-
- case OP_NOT:
- return c == next;
-
- case OP_NOTI:
- if (c == next) return TRUE;
-#ifdef SUPPORT_UTF
- if (utf)
- {
- pcre_uint32 othercase;
- if (next < 128) othercase = cd->fcc[next]; else
-#ifdef SUPPORT_UCP
- othercase = UCD_OTHERCASE(next);
-#else
- othercase = NOTACHAR;
-#endif
- return c == othercase;
- }
- else
-#endif /* SUPPORT_UTF */
- return (c == TABLE_GET(next, cd->fcc, next)); /* Not UTF */
-
- /* Note that OP_DIGIT etc. are generated only when PCRE_UCP is *not* set.
- When it is set, \d etc. are converted into OP_(NOT_)PROP codes. */
-
- case OP_DIGIT:
- return next > 255 || (cd->ctypes[next] & ctype_digit) == 0;
-
- case OP_NOT_DIGIT:
- return next <= 255 && (cd->ctypes[next] & ctype_digit) != 0;
-
- case OP_WHITESPACE:
- return next > 255 || (cd->ctypes[next] & ctype_space) == 0;
-
- case OP_NOT_WHITESPACE:
- return next <= 255 && (cd->ctypes[next] & ctype_space) != 0;
-
- case OP_WORDCHAR:
- return next > 255 || (cd->ctypes[next] & ctype_word) == 0;
-
- case OP_NOT_WORDCHAR:
- return next <= 255 && (cd->ctypes[next] & ctype_word) != 0;
-
- case OP_HSPACE:
- case OP_NOT_HSPACE:
- switch(next)
- {
- HSPACE_CASES:
- return op_code == OP_NOT_HSPACE;
-
- default:
- return op_code != OP_NOT_HSPACE;
- }
-
- case OP_ANYNL:
- case OP_VSPACE:
- case OP_NOT_VSPACE:
- switch(next)
- {
- VSPACE_CASES:
- return op_code == OP_NOT_VSPACE;
-
- default:
- return op_code != OP_NOT_VSPACE;
- }
-
-#ifdef SUPPORT_UCP
- case OP_PROP:
- return check_char_prop(next, previous[0], previous[1], FALSE);
-
- case OP_NOTPROP:
- return check_char_prop(next, previous[0], previous[1], TRUE);
-#endif
-
- default:
- return FALSE;
- }
- }
-
-/* Handle the case when the next item is \d, \s, etc. Note that when PCRE_UCP
-is set, \d turns into ESC_du rather than ESC_d, etc., so ESC_d etc. are
-generated only when PCRE_UCP is *not* set, that is, when only ASCII
-characteristics are recognized. Similarly, the opcodes OP_DIGIT etc. are
-replaced by OP_PROP codes when PCRE_UCP is set. */
-
-switch(op_code)
- {
- case OP_CHAR:
- case OP_CHARI:
- switch(escape)
- {
- case ESC_d:
- return c > 255 || (cd->ctypes[c] & ctype_digit) == 0;
-
- case ESC_D:
- return c <= 255 && (cd->ctypes[c] & ctype_digit) != 0;
-
- case ESC_s:
- return c > 255 || (cd->ctypes[c] & ctype_space) == 0;
-
- case ESC_S:
- return c <= 255 && (cd->ctypes[c] & ctype_space) != 0;
-
- case ESC_w:
- return c > 255 || (cd->ctypes[c] & ctype_word) == 0;
-
- case ESC_W:
- return c <= 255 && (cd->ctypes[c] & ctype_word) != 0;
-
- case ESC_h:
- case ESC_H:
- switch(c)
- {
- HSPACE_CASES:
- return escape != ESC_h;
-
- default:
- return escape == ESC_h;
- }
-
- case ESC_v:
- case ESC_V:
- switch(c)
- {
- VSPACE_CASES:
- return escape != ESC_v;
-
- default:
- return escape == ESC_v;
- }
-
- /* When PCRE_UCP is set, these values get generated for \d etc. Find
- their substitutions and process them. The result will always be either
- ESC_p or ESC_P. Then fall through to process those values. */
-
-#ifdef SUPPORT_UCP
- case ESC_du:
- case ESC_DU:
- case ESC_wu:
- case ESC_WU:
- case ESC_su:
- case ESC_SU:
- {
- int temperrorcode = 0;
- ptr = substitutes[escape - ESC_DU];
- escape = check_escape(&ptr, &next, &temperrorcode, 0, options, FALSE);
- if (temperrorcode != 0) return FALSE;
- ptr++; /* For compatibility */
- }
- /* Fall through */
-
- case ESC_p:
- case ESC_P:
- {
- unsigned int ptype = 0, pdata = 0;
- int errorcodeptr;
- BOOL negated;
-
- ptr--; /* Make ptr point at the p or P */
- if (!get_ucp(&ptr, &negated, &ptype, &pdata, &errorcodeptr))
- return FALSE;
- ptr++; /* Point past the final curly ket */
-
- /* If the property item is optional, we have to give up. (When generated
- from \d etc by PCRE_UCP, this test will have been applied much earlier,
- to the original \d etc. At this point, ptr will point to a zero byte. */
-
- if (*ptr == CHAR_ASTERISK || *ptr == CHAR_QUESTION_MARK ||
- STRNCMP_UC_C8(ptr, STR_LEFT_CURLY_BRACKET STR_0 STR_COMMA, 3) == 0)
- return FALSE;
-
- /* Do the property check. */
-
- return check_char_prop(c, ptype, pdata, (escape == ESC_P) != negated);
- }
-#endif
-
- default:
- return FALSE;
- }
-
- /* In principle, support for Unicode properties should be integrated here as
- well. It means re-organizing the above code so as to get hold of the property
- values before switching on the op-code. However, I wonder how many patterns
- combine ASCII \d etc with Unicode properties? (Note that if PCRE_UCP is set,
- these op-codes are never generated.) */
-
- case OP_DIGIT:
- return escape == ESC_D || escape == ESC_s || escape == ESC_W ||
- escape == ESC_h || escape == ESC_v || escape == ESC_R;
-
- case OP_NOT_DIGIT:
- return escape == ESC_d;
-
- case OP_WHITESPACE:
- return escape == ESC_S || escape == ESC_d || escape == ESC_w;
-
- case OP_NOT_WHITESPACE:
- return escape == ESC_s || escape == ESC_h || escape == ESC_v || escape == ESC_R;
-
- case OP_HSPACE:
- return escape == ESC_S || escape == ESC_H || escape == ESC_d ||
- escape == ESC_w || escape == ESC_v || escape == ESC_R;
-
- case OP_NOT_HSPACE:
- return escape == ESC_h;
-
- /* Can't have \S in here because VT matches \S (Perl anomaly) */
- case OP_ANYNL:
- case OP_VSPACE:
- return escape == ESC_V || escape == ESC_d || escape == ESC_w;
-
- case OP_NOT_VSPACE:
- return escape == ESC_v || escape == ESC_R;
-
- case OP_WORDCHAR:
- return escape == ESC_W || escape == ESC_s || escape == ESC_h ||
- escape == ESC_v || escape == ESC_R;
-
- case OP_NOT_WORDCHAR:
- return escape == ESC_w || escape == ESC_d;
-
- default:
- return FALSE;
- }
-
-/* Control does not reach here */
-}
-
-
-
-/*************************************************
* Add a character or range to a class *
*************************************************/
@@ -3672,22 +4328,22 @@ to find out the amount of memory needed, as well as during the real compile
phase. The value of lengthptr distinguishes the two phases.
Arguments:
- optionsptr pointer to the option bits
- codeptr points to the pointer to the current code point
- ptrptr points to the current pattern pointer
- errorcodeptr points to error code variable
- firstcharptr place to put the first required character
+ optionsptr pointer to the option bits
+ codeptr points to the pointer to the current code point
+ ptrptr points to the current pattern pointer
+ errorcodeptr points to error code variable
+ firstcharptr place to put the first required character
firstcharflagsptr place to put the first character flags, or a negative number
- reqcharptr place to put the last required character
- reqcharflagsptr place to put the last required character flags, or a negative number
- bcptr points to current branch chain
- cond_depth conditional nesting depth
- cd contains pointers to tables etc.
- lengthptr NULL during the real compile phase
- points to length accumulator during pre-compile phase
-
-Returns: TRUE on success
- FALSE, with *errorcodeptr set non-zero on error
+ reqcharptr place to put the last required character
+ reqcharflagsptr place to put the last required character flags, or a negative number
+ bcptr points to current branch chain
+ cond_depth conditional nesting depth
+ cd contains pointers to tables etc.
+ lengthptr NULL during the real compile phase
+ points to length accumulator during pre-compile phase
+
+Returns: TRUE on success
+ FALSE, with *errorcodeptr set non-zero on error
*/
static BOOL
@@ -3910,58 +4566,67 @@ for (;; ptr++)
}
goto NORMAL_CHAR;
}
+ /* Control does not reach here. */
}
- /* Fill in length of a previous callout, except when the next thing is
- a quantifier. */
-
- is_quantifier =
- c == CHAR_ASTERISK || c == CHAR_PLUS || c == CHAR_QUESTION_MARK ||
- (c == CHAR_LEFT_CURLY_BRACKET && is_counted_repeat(ptr+1));
-
- if (!is_quantifier && previous_callout != NULL &&
- after_manual_callout-- <= 0)
- {
- if (lengthptr == NULL) /* Don't attempt in pre-compile phase */
- complete_callout(previous_callout, ptr, cd);
- previous_callout = NULL;
- }
-
- /* In extended mode, skip white space and comments. */
+ /* In extended mode, skip white space and comments. We need a loop in order
+ to check for more white space and more comments after a comment. */
if ((options & PCRE_EXTENDED) != 0)
{
- if (MAX_255(*ptr) && (cd->ctypes[c] & ctype_space) != 0) continue;
- if (c == CHAR_NUMBER_SIGN)
+ for (;;)
{
+ while (MAX_255(c) && (cd->ctypes[c] & ctype_space) != 0) c = *(++ptr);
+ if (c != CHAR_NUMBER_SIGN) break;
ptr++;
while (*ptr != CHAR_NULL)
{
- if (IS_NEWLINE(ptr)) { ptr += cd->nllen - 1; break; }
+ if (IS_NEWLINE(ptr)) /* For non-fixed-length newline cases, */
+ { /* IS_NEWLINE sets cd->nllen. */
+ ptr += cd->nllen;
+ break;
+ }
ptr++;
#ifdef SUPPORT_UTF
if (utf) FORWARDCHAR(ptr);
#endif
}
- if (*ptr != CHAR_NULL) continue;
-
- /* Else fall through to handle end of string */
- c = 0;
+ c = *ptr; /* Either NULL or the char after a newline */
}
}
- /* No auto callout for quantifiers. */
+ /* See if the next thing is a quantifier. */
- if ((options & PCRE_AUTO_CALLOUT) != 0 && !is_quantifier)
+ is_quantifier =
+ c == CHAR_ASTERISK || c == CHAR_PLUS || c == CHAR_QUESTION_MARK ||
+ (c == CHAR_LEFT_CURLY_BRACKET && is_counted_repeat(ptr+1));
+
+ /* Fill in length of a previous callout, except when the next thing is a
+ quantifier or when processing a property substitution string in UCP mode. */
+
+ if (!is_quantifier && previous_callout != NULL && nestptr == NULL &&
+ after_manual_callout-- <= 0)
+ {
+ if (lengthptr == NULL) /* Don't attempt in pre-compile phase */
+ complete_callout(previous_callout, ptr, cd);
+ previous_callout = NULL;
+ }
+
+ /* Create auto callout, except for quantifiers, or while processing property
+ strings that are substituted for \w etc in UCP mode. */
+
+ if ((options & PCRE_AUTO_CALLOUT) != 0 && !is_quantifier && nestptr == NULL)
{
previous_callout = code;
code = auto_callout(code, ptr, cd);
}
+ /* Process the next pattern item. */
+
switch(c)
{
/* ===================================================================*/
- case 0: /* The branch terminates at string end */
+ case CHAR_NULL: /* The branch terminates at string end */
case CHAR_VERTICAL_LINE: /* or | or ) */
case CHAR_RIGHT_PARENTHESIS:
*firstcharptr = firstchar;
@@ -4039,7 +4704,29 @@ for (;; ptr++)
}
goto NORMAL_CHAR;
+ /* In another (POSIX) regex library, the ugly syntax [[:<:]] and [[:>:]] is
+ used for "start of word" and "end of word". As these are otherwise illegal
+ sequences, we don't break anything by recognizing them. They are replaced
+ by \b(?=\w) and \b(?<=\w) respectively. Sequences like [a[:<:]] are
+ erroneous and are handled by the normal code below. */
+
case CHAR_LEFT_SQUARE_BRACKET:
+ if (STRNCMP_UC_C8(ptr+1, STRING_WEIRD_STARTWORD, 6) == 0)
+ {
+ nestptr = ptr + 7;
+ ptr = sub_start_of_word - 1;
+ continue;
+ }
+
+ if (STRNCMP_UC_C8(ptr+1, STRING_WEIRD_ENDWORD, 6) == 0)
+ {
+ nestptr = ptr + 7;
+ ptr = sub_end_of_word - 1;
+ continue;
+ }
+
+ /* Handle a real character class. */
+
previous = code;
/* PCRE supports POSIX class stuff inside a class. Perl gives an error if
@@ -4204,24 +4891,58 @@ for (;; ptr++)
posix_class = 0;
/* When PCRE_UCP is set, some of the POSIX classes are converted to
- different escape sequences that use Unicode properties. */
+ different escape sequences that use Unicode properties \p or \P. Others
+ that are not available via \p or \P generate XCL_PROP/XCL_NOTPROP
+ directly. */
#ifdef SUPPORT_UCP
if ((options & PCRE_UCP) != 0)
{
+ unsigned int ptype = 0;
int pc = posix_class + ((local_negate)? POSIX_SUBSIZE/2 : 0);
+
+ /* The posix_substitutes table specifies which POSIX classes can be
+ converted to \p or \P items. */
+
if (posix_substitutes[pc] != NULL)
{
nestptr = tempptr + 1;
ptr = posix_substitutes[pc] - 1;
continue;
}
+
+ /* There are three other classes that generate special property calls
+ that are recognized only in an XCLASS. */
+
+ else switch(posix_class)
+ {
+ case PC_GRAPH:
+ ptype = PT_PXGRAPH;
+ /* Fall through */
+ case PC_PRINT:
+ if (ptype == 0) ptype = PT_PXPRINT;
+ /* Fall through */
+ case PC_PUNCT:
+ if (ptype == 0) ptype = PT_PXPUNCT;
+ *class_uchardata++ = local_negate? XCL_NOTPROP : XCL_PROP;
+ *class_uchardata++ = ptype;
+ *class_uchardata++ = 0;
+ ptr = tempptr + 1;
+ continue;
+
+ /* For all other POSIX classes, no special action is taken in UCP
+ mode. Fall through to the non_UCP case. */
+
+ default:
+ break;
+ }
}
#endif
- /* In the non-UCP case, we build the bit map for the POSIX class in a
- chunk of local store because we may be adding and subtracting from it,
- and we don't want to subtract bits that may be in the main map already.
- At the end we or the result into the bit map that is being built. */
+ /* In the non-UCP case, or when UCP makes no difference, we build the
+ bit map for the POSIX class in a chunk of local store because we may be
+ adding and subtracting from it, and we don't want to subtract bits that
+ may be in the main map already. At the end we or the result into the
+ bit map that is being built. */
posix_class *= 3;
@@ -4277,14 +4998,12 @@ for (;; ptr++)
if (c == CHAR_BACKSLASH)
{
- escape = check_escape(&ptr, &ec, errorcodeptr, cd->bracount, options, TRUE);
-
+ escape = check_escape(&ptr, &ec, errorcodeptr, cd->bracount, options,
+ TRUE);
if (*errorcodeptr != 0) goto FAILED;
-
- if (escape == 0)
- c = ec;
+ if (escape == 0) c = ec;
else if (escape == ESC_b) c = CHAR_BS; /* \b is backspace in a class */
- else if (escape == ESC_N) /* \N is not supported in a class */
+ else if (escape == ESC_N) /* \N is not supported in a class */
{
*errorcodeptr = ERR71;
goto FAILED;
@@ -4340,21 +5059,20 @@ for (;; ptr++)
for (c = 0; c < 32; c++) classbits[c] |= ~cbits[c+cbit_word];
continue;
- /* Perl 5.004 onwards omits VT from \s, but we must preserve it
- if it was previously set by something earlier in the character
- class. Luckily, the value of CHAR_VT is 0x0b in both ASCII and
- EBCDIC, so we lazily just adjust the appropriate bit. */
+ /* Perl 5.004 onwards omitted VT from \s, but restored it at Perl
+ 5.18. Before PCRE 8.34, we had to preserve the VT bit if it was
+ previously set by something earlier in the character class.
+ Luckily, the value of CHAR_VT is 0x0b in both ASCII and EBCDIC, so
+ we could just adjust the appropriate bit. From PCRE 8.34 we no
+ longer treat \s and \S specially. */
case ESC_s:
- classbits[0] |= cbits[cbit_space];
- classbits[1] |= cbits[cbit_space+1] & ~0x08;
- for (c = 2; c < 32; c++) classbits[c] |= cbits[c+cbit_space];
+ for (c = 0; c < 32; c++) classbits[c] |= cbits[c+cbit_space];
continue;
case ESC_S:
should_flip_negation = TRUE;
for (c = 0; c < 32; c++) classbits[c] |= ~cbits[c+cbit_space];
- classbits[1] |= 0x08; /* Perl 5.004 onwards omits VT from \s */
continue;
/* The rest apply in both UCP and non-UCP cases. */
@@ -4476,26 +5194,43 @@ for (;; ptr++)
#endif
d = *ptr; /* Not UTF-8 mode */
- /* The second part of a range can be a single-character escape, but
- not any of the other escapes. Perl 5.6 treats a hyphen as a literal
- in such circumstances. */
+ /* The second part of a range can be a single-character escape
+ sequence, but not any of the other escapes. Perl treats a hyphen as a
+ literal in such circumstances. However, in Perl's warning mode, a
+ warning is given, so PCRE now faults it as it is almost certainly a
+ mistake on the user's part. */
- if (!inescq && d == CHAR_BACKSLASH)
+ if (!inescq)
{
- int descape;
- descape = check_escape(&ptr, &d, errorcodeptr, cd->bracount, options, TRUE);
- if (*errorcodeptr != 0) goto FAILED;
+ if (d == CHAR_BACKSLASH)
+ {
+ int descape;
+ descape = check_escape(&ptr, &d, errorcodeptr, cd->bracount, options, TRUE);
+ if (*errorcodeptr != 0) goto FAILED;
- /* \b is backspace; any other special means the '-' was literal. */
+ /* 0 means a character was put into d; \b is backspace; any other
+ special causes an error. */
- if (descape != 0)
- {
- if (descape == ESC_b) d = CHAR_BS; else
+ if (descape != 0)
{
- ptr = oldptr;
- goto CLASS_SINGLE_CHARACTER; /* A few lines below */
+ if (descape == ESC_b) d = CHAR_BS; else
+ {
+ *errorcodeptr = ERR83;
+ goto FAILED;
+ }
}
}
+
+ /* A hyphen followed by a POSIX class is treated in the same way. */
+
+ else if (d == CHAR_LEFT_SQUARE_BRACKET &&
+ (ptr[1] == CHAR_COLON || ptr[1] == CHAR_DOT ||
+ ptr[1] == CHAR_EQUALS_SIGN) &&
+ check_posix_syntax(ptr, &tempptr))
+ {
+ *errorcodeptr = ERR83;
+ goto FAILED;
+ }
}
/* Check that the two values are in the correct order. Optimize
@@ -4759,6 +5494,34 @@ for (;; ptr++)
tempcode = previous;
+ /* Before checking for a possessive quantifier, we must skip over
+ whitespace and comments in extended mode because Perl allows white space at
+ this point. */
+
+ if ((options & PCRE_EXTENDED) != 0)
+ {
+ const pcre_uchar *p = ptr + 1;
+ for (;;)
+ {
+ while (MAX_255(*p) && (cd->ctypes[*p] & ctype_space) != 0) p++;
+ if (*p != CHAR_NUMBER_SIGN) break;
+ p++;
+ while (*p != CHAR_NULL)
+ {
+ if (IS_NEWLINE(p)) /* For non-fixed-length newline cases, */
+ { /* IS_NEWLINE sets cd->nllen. */
+ p += cd->nllen;
+ break;
+ }
+ p++;
+#ifdef SUPPORT_UTF
+ if (utf) FORWARDCHAR(p);
+#endif
+ } /* Loop for comment characters */
+ } /* Loop for multiple comments */
+ ptr = p - 1; /* Character before the next significant one. */
+ }
+
/* If the next character is '+', we have a possessive quantifier. This
implies greediness, whatever the setting of the PCRE_UNGREEDY option.
If the next character is '?' this is a minimizing repeat, by default,
@@ -4853,19 +5616,6 @@ for (;; ptr++)
}
}
- /* If the repetition is unlimited, it pays to see if the next thing on
- the line is something that cannot possibly match this character. If so,
- automatically possessifying this item gains some performance in the case
- where the match fails. */
-
- if (!possessive_quantifier &&
- repeat_max < 0 &&
- check_auto_possessive(previous, utf, ptr + 1, options, cd))
- {
- repeat_type = 0; /* Force greedy */
- possessive_quantifier = TRUE;
- }
-
goto OUTPUT_SINGLE_REPEAT; /* Code shared with single character types */
}
@@ -4883,14 +5633,6 @@ for (;; ptr++)
op_type = OP_TYPESTAR - OP_STAR; /* Use type opcodes */
c = *previous;
- if (!possessive_quantifier &&
- repeat_max < 0 &&
- check_auto_possessive(previous, utf, ptr + 1, options, cd))
- {
- repeat_type = 0; /* Force greedy */
- possessive_quantifier = TRUE;
- }
-
OUTPUT_SINGLE_REPEAT:
if (*previous == OP_PROP || *previous == OP_NOTPROP)
{
@@ -4907,16 +5649,6 @@ for (;; ptr++)
if (repeat_max == 0) goto END_REPEAT;
- /*--------------------------------------------------------------------*/
- /* This code is obsolete from release 8.00; the restriction was finally
- removed: */
-
- /* All real repeats make it impossible to handle partial matching (maybe
- one day we will be able to remove this restriction). */
-
- /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */
- /*--------------------------------------------------------------------*/
-
/* Combine the op_type with the repeat_type */
repeat_type += op_type;
@@ -5049,13 +5781,12 @@ for (;; ptr++)
/* If previous was a character class or a back reference, we put the repeat
stuff after it, but just skip the item if the repeat was {0,0}. */
- else if (*previous == OP_CLASS ||
- *previous == OP_NCLASS ||
+ else if (*previous == OP_CLASS || *previous == OP_NCLASS ||
#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
*previous == OP_XCLASS ||
#endif
- *previous == OP_REF ||
- *previous == OP_REFI)
+ *previous == OP_REF || *previous == OP_REFI ||
+ *previous == OP_DNREF || *previous == OP_DNREFI)
{
if (repeat_max == 0)
{
@@ -5063,16 +5794,6 @@ for (;; ptr++)
goto END_REPEAT;
}
- /*--------------------------------------------------------------------*/
- /* This code is obsolete from release 8.00; the restriction was finally
- removed: */
-
- /* All real repeats make it impossible to handle partial matching (maybe
- one day we will be able to remove this restriction). */
-
- /* if (repeat_max != 1) cd->external_flags |= PCRE_NOPARTIAL; */
- /*--------------------------------------------------------------------*/
-
if (repeat_min == 0 && repeat_max == -1)
*code++ = OP_CRSTAR + repeat_type;
else if (repeat_min == 1 && repeat_max == -1)
@@ -5093,8 +5814,9 @@ for (;; ptr++)
opcodes such as BRA and CBRA, as this is the place where they get converted
into the more special varieties such as BRAPOS and SBRA. A test for >=
OP_ASSERT and <= OP_COND includes ASSERT, ASSERT_NOT, ASSERTBACK,
- ASSERTBACK_NOT, ONCE, BRA, CBRA, and COND. Originally, PCRE did not allow
- repetition of assertions, but now it does, for Perl compatibility. */
+ ASSERTBACK_NOT, ONCE, ONCE_NC, BRA, BRAPOS, CBRA, CBRAPOS, and COND.
+ Originally, PCRE did not allow repetition of assertions, but now it does,
+ for Perl compatibility. */
else if (*previous >= OP_ASSERT && *previous <= OP_COND)
{
@@ -5112,7 +5834,7 @@ for (;; ptr++)
/* There is no sense in actually repeating assertions. The only potential
use of repetition is in cases when the assertion is optional. Therefore,
if the minimum is greater than zero, just ignore the repeat. If the
- maximum is not not zero or one, set it to 1. */
+ maximum is not zero or one, set it to 1. */
if (*previous < OP_ONCE) /* Assertion */
{
@@ -5415,7 +6137,7 @@ for (;; ptr++)
pcre_uchar *scode = bracode;
do
{
- if (could_be_empty_branch(scode, ketcode, utf, cd))
+ if (could_be_empty_branch(scode, ketcode, utf, cd, NULL))
{
*bracode += OP_SBRA - OP_BRA;
break;
@@ -5485,43 +6207,105 @@ for (;; ptr++)
goto FAILED;
}
- /* If the character following a repeat is '+', or if certain optimization
- tests above succeeded, possessive_quantifier is TRUE. For some opcodes,
- there are special alternative opcodes for this case. For anything else, we
- wrap the entire repeated item inside OP_ONCE brackets. Logically, the '+'
- notation is just syntactic sugar, taken from Sun's Java package, but the
- special opcodes can optimize it.
+ /* If the character following a repeat is '+', possessive_quantifier is
+ TRUE. For some opcodes, there are special alternative opcodes for this
+ case. For anything else, we wrap the entire repeated item inside OP_ONCE
+ brackets. Logically, the '+' notation is just syntactic sugar, taken from
+ Sun's Java package, but the special opcodes can optimize it.
Some (but not all) possessively repeated subpatterns have already been
completely handled in the code just above. For them, possessive_quantifier
- is always FALSE at this stage.
-
- Note that the repeated item starts at tempcode, not at previous, which
- might be the first part of a string whose (former) last char we repeated.
-
- Possessifying an 'exact' quantifier has no effect, so we can ignore it. But
- an 'upto' may follow. We skip over an 'exact' item, and then test the
- length of what remains before proceeding. */
+ is always FALSE at this stage. Note that the repeated item starts at
+ tempcode, not at previous, which might be the first part of a string whose
+ (former) last char we repeated. */
if (possessive_quantifier)
{
int len;
- if (*tempcode == OP_TYPEEXACT)
+ /* Possessifying an EXACT quantifier has no effect, so we can ignore it.
+ However, QUERY, STAR, or UPTO may follow (for quantifiers such as {5,6},
+ {5,}, or {5,10}). We skip over an EXACT item; if the length of what
+ remains is greater than zero, there's a further opcode that can be
+ handled. If not, do nothing, leaving the EXACT alone. */
+
+ switch(*tempcode)
+ {
+ case OP_TYPEEXACT:
tempcode += PRIV(OP_lengths)[*tempcode] +
((tempcode[1 + IMM2_SIZE] == OP_PROP
|| tempcode[1 + IMM2_SIZE] == OP_NOTPROP)? 2 : 0);
+ break;
- else if (*tempcode == OP_EXACT || *tempcode == OP_NOTEXACT)
- {
+ /* CHAR opcodes are used for exacts whose count is 1. */
+
+ case OP_CHAR:
+ case OP_CHARI:
+ case OP_NOT:
+ case OP_NOTI:
+ case OP_EXACT:
+ case OP_EXACTI:
+ case OP_NOTEXACT:
+ case OP_NOTEXACTI:
tempcode += PRIV(OP_lengths)[*tempcode];
#ifdef SUPPORT_UTF
if (utf && HAS_EXTRALEN(tempcode[-1]))
tempcode += GET_EXTRALEN(tempcode[-1]);
#endif
+ break;
+
+ /* For the class opcodes, the repeat operator appears at the end;
+ adjust tempcode to point to it. */
+
+ case OP_CLASS:
+ case OP_NCLASS:
+ tempcode += 1 + 32/sizeof(pcre_uchar);
+ break;
+
+#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
+ case OP_XCLASS:
+ tempcode += GET(tempcode, 1);
+ break;
+#endif
}
+ /* If tempcode is equal to code (which points to the end of the repeated
+ item), it means we have skipped an EXACT item but there is no following
+ QUERY, STAR, or UPTO; the value of len will be 0, and we do nothing. In
+ all other cases, tempcode will be pointing to the repeat opcode, and will
+ be less than code, so the value of len will be greater than 0. */
+
len = (int)(code - tempcode);
+ if (len > 0)
+ {
+ unsigned int repcode = *tempcode;
+
+ /* There is a table for possessifying opcodes, all of which are less
+ than OP_CALLOUT. A zero entry means there is no possessified version.
+ */
+
+ if (repcode < OP_CALLOUT && opcode_possessify[repcode] > 0)
+ *tempcode = opcode_possessify[repcode];
+
+ /* For opcode without a special possessified version, wrap the item in
+ ONCE brackets. Because we are moving code along, we must ensure that any
+ pending recursive references are updated. */
+
+ else
+ {
+ *code = OP_END;
+ adjust_recurse(tempcode, 1 + LINK_SIZE, utf, cd, save_hwm);
+ memmove(tempcode + 1 + LINK_SIZE, tempcode, IN_UCHARS(len));
+ code += 1 + LINK_SIZE;
+ len += 1 + LINK_SIZE;
+ tempcode[0] = OP_ONCE;
+ *code++ = OP_KET;
+ PUTINC(code, 0, len);
+ PUT(tempcode, 1, len);
+ }
+ }
+
+#ifdef NEVER
if (len > 0) switch (*tempcode)
{
case OP_STAR: *tempcode = OP_POSSTAR; break;
@@ -5549,6 +6333,11 @@ for (;; ptr++)
case OP_TYPEQUERY: *tempcode = OP_TYPEPOSQUERY; break;
case OP_TYPEUPTO: *tempcode = OP_TYPEPOSUPTO; break;
+ case OP_CRSTAR: *tempcode = OP_CRPOSSTAR; break;
+ case OP_CRPLUS: *tempcode = OP_CRPOSPLUS; break;
+ case OP_CRQUERY: *tempcode = OP_CRPOSQUERY; break;
+ case OP_CRRANGE: *tempcode = OP_CRPOSRANGE; break;
+
/* Because we are moving code along, we must ensure that any
pending recursive references are updated. */
@@ -5564,6 +6353,7 @@ for (;; ptr++)
PUT(tempcode, 1, len);
break;
}
+#endif
}
/* In all case we no longer have a previous item. We also set the
@@ -5749,30 +6539,44 @@ for (;; ptr++)
/* ------------------------------------------------------------ */
case CHAR_LEFT_PARENTHESIS:
bravalue = OP_COND; /* Conditional group */
+ tempptr = ptr;
/* A condition can be an assertion, a number (referring to a numbered
- group), a name (referring to a named group), or 'R', referring to
- recursion. R<digits> and R&name are also permitted for recursion tests.
+ group's having been set), a name (referring to a named group), or 'R',
+ referring to recursion. R<digits> and R&name are also permitted for
+ recursion tests.
+
+ There are ways of testing a named group: (?(name)) is used by Python;
+ Perl 5.10 onwards uses (?(<name>) or (?('name')).
- There are several syntaxes for testing a named group: (?(name)) is used
- by Python; Perl 5.10 onwards uses (?(<name>) or (?('name')).
+ There is one unfortunate ambiguity, caused by history. 'R' can be the
+ recursive thing or the name 'R' (and similarly for 'R' followed by
+ digits). We look for a name first; if not found, we try the other case.
- There are two unfortunate ambiguities, caused by history. (a) 'R' can
- be the recursive thing or the name 'R' (and similarly for 'R' followed
- by digits), and (b) a number could be a name that consists of digits.
- In both cases, we look for a name first; if not found, we try the other
- cases. */
+ For compatibility with auto-callouts, we allow a callout to be
+ specified before a condition that is an assertion. First, check for the
+ syntax of a callout; if found, adjust the temporary pointer that is
+ used to check for an assertion condition. That's all that is needed! */
+
+ if (ptr[1] == CHAR_QUESTION_MARK && ptr[2] == CHAR_C)
+ {
+ for (i = 3;; i++) if (!IS_DIGIT(ptr[i])) break;
+ if (ptr[i] == CHAR_RIGHT_PARENTHESIS)
+ tempptr += i + 1;
+ }
/* For conditions that are assertions, check the syntax, and then exit
the switch. This will take control down to where bracketed groups,
including assertions, are processed. */
- if (ptr[1] == CHAR_QUESTION_MARK && (ptr[2] == CHAR_EQUALS_SIGN ||
- ptr[2] == CHAR_EXCLAMATION_MARK || ptr[2] == CHAR_LESS_THAN_SIGN))
+ if (tempptr[1] == CHAR_QUESTION_MARK &&
+ (tempptr[2] == CHAR_EQUALS_SIGN ||
+ tempptr[2] == CHAR_EXCLAMATION_MARK ||
+ tempptr[2] == CHAR_LESS_THAN_SIGN))
break;
- /* Most other conditions use OP_CREF (a couple change to OP_RREF
- below), and all need to skip 1+IMM2_SIZE bytes at the start of the group. */
+ /* Other conditions use OP_CREF/OP_DNCREF/OP_RREF/OP_DNRREF, and all
+ need to skip at least 1+IMM2_SIZE bytes at the start of the group. */
code[1+LINK_SIZE] = OP_CREF;
skipbytes = 1+IMM2_SIZE;
@@ -5780,7 +6584,8 @@ for (;; ptr++)
/* Check for a test for recursion in a named group. */
- if (ptr[1] == CHAR_R && ptr[2] == CHAR_AMPERSAND)
+ ptr++;
+ if (*ptr == CHAR_R && ptr[1] == CHAR_AMPERSAND)
{
terminator = -1;
ptr += 2;
@@ -5788,14 +6593,15 @@ for (;; ptr++)
}
/* Check for a test for a named group's having been set, using the Perl
- syntax (?(<name>) or (?('name') */
+ syntax (?(<name>) or (?('name'), and also allow for the original PCRE
+ syntax of (?(name) or for (?(+n), (?(-n), and just (?(n). */
- else if (ptr[1] == CHAR_LESS_THAN_SIGN)
+ else if (*ptr == CHAR_LESS_THAN_SIGN)
{
terminator = CHAR_GREATER_THAN_SIGN;
ptr++;
}
- else if (ptr[1] == CHAR_APOSTROPHE)
+ else if (*ptr == CHAR_APOSTROPHE)
{
terminator = CHAR_APOSTROPHE;
ptr++;
@@ -5803,35 +6609,55 @@ for (;; ptr++)
else
{
terminator = CHAR_NULL;
- if (ptr[1] == CHAR_MINUS || ptr[1] == CHAR_PLUS) refsign = *(++ptr);
+ if (*ptr == CHAR_MINUS || *ptr == CHAR_PLUS) refsign = *ptr++;
+ else if (IS_DIGIT(*ptr)) refsign = 0;
}
- /* We now expect to read a name; any thing else is an error */
+ /* Handle a number */
- if (!MAX_255(ptr[1]) || (cd->ctypes[ptr[1]] & ctype_word) == 0)
+ if (refsign >= 0)
{
- ptr += 1; /* To get the right offset */
- *errorcodeptr = ERR28;
- goto FAILED;
+ recno = 0;
+ while (IS_DIGIT(*ptr))
+ {
+ recno = recno * 10 + (int)(*ptr - CHAR_0);
+ ptr++;
+ }
}
- /* Read the name, but also get it as a number if it's all digits */
+ /* Otherwise we expect to read a name; anything else is an error. When
+ a name is one of a number of duplicates, a different opcode is used and
+ it needs more memory. Unfortunately we cannot tell whether a name is a
+ duplicate in the first pass, so we have to allow for more memory. */
- recno = 0;
- name = ++ptr;
- while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0)
+ else
{
- if (recno >= 0)
- recno = (IS_DIGIT(*ptr))? recno * 10 + (int)(*ptr - CHAR_0) : -1;
- ptr++;
+ if (IS_DIGIT(*ptr))
+ {
+ *errorcodeptr = ERR84;
+ goto FAILED;
+ }
+ if (!MAX_255(*ptr) || (cd->ctypes[*ptr] & ctype_word) == 0)
+ {
+ *errorcodeptr = ERR28; /* Assertion expected */
+ goto FAILED;
+ }
+ name = ptr++;
+ while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0)
+ {
+ ptr++;
+ }
+ namelen = (int)(ptr - name);
+ if (lengthptr != NULL) *lengthptr += IMM2_SIZE;
}
- namelen = (int)(ptr - name);
+
+ /* Check the terminator */
if ((terminator > 0 && *ptr++ != (pcre_uchar)terminator) ||
*ptr++ != CHAR_RIGHT_PARENTHESIS)
{
- ptr--; /* Error offset */
- *errorcodeptr = ERR26;
+ ptr--; /* Error offset */
+ *errorcodeptr = ERR26; /* Malformed number or name */
goto FAILED;
}
@@ -5840,18 +6666,18 @@ for (;; ptr++)
if (lengthptr != NULL) break;
/* In the real compile we do the work of looking for the actual
- reference. If the string started with "+" or "-" we require the rest to
- be digits, in which case recno will be set. */
+ reference. If refsign is not negative, it means we have a number in
+ recno. */
- if (refsign > 0)
+ if (refsign >= 0)
{
if (recno <= 0)
{
- *errorcodeptr = ERR58;
+ *errorcodeptr = ERR35;
goto FAILED;
}
- recno = (refsign == CHAR_MINUS)?
- cd->bracount - recno + 1 : recno +cd->bracount;
+ if (refsign != 0) recno = (refsign == CHAR_MINUS)?
+ cd->bracount - recno + 1 : recno + cd->bracount;
if (recno <= 0 || recno > cd->final_bracount)
{
*errorcodeptr = ERR15;
@@ -5861,11 +6687,7 @@ for (;; ptr++)
break;
}
- /* Otherwise (did not start with "+" or "-"), start by looking for the
- name. If we find a name, add one to the opcode to change OP_CREF or
- OP_RREF into OP_NCREF or OP_NRREF. These behave exactly the same,
- except they record that the reference was originally to a name. The
- information is used to check duplicate names. */
+ /* Otherwise look for the name. */
slot = cd->name_table;
for (i = 0; i < cd->names_found; i++)
@@ -5874,29 +6696,40 @@ for (;; ptr++)
slot += cd->name_entry_size;
}
- /* Found a previous named subpattern */
+ /* Found the named subpattern. If the name is duplicated, add one to
+ the opcode to change CREF/RREF into DNCREF/DNRREF and insert
+ appropriate data values. Otherwise, just insert the unique subpattern
+ number. */
if (i < cd->names_found)
{
- recno = GET2(slot, 0);
- PUT2(code, 2+LINK_SIZE, recno);
- code[1+LINK_SIZE]++;
- }
-
- /* Search the pattern for a forward reference */
-
- else if ((i = find_parens(cd, name, namelen,
- (options & PCRE_EXTENDED) != 0, utf)) > 0)
- {
- PUT2(code, 2+LINK_SIZE, i);
- code[1+LINK_SIZE]++;
+ int offset = i++;
+ int count = 1;
+ recno = GET2(slot, 0); /* Number from first found */
+ for (; i < cd->names_found; i++)
+ {
+ slot += cd->name_entry_size;
+ if (STRNCMP_UC_UC(name, slot+IMM2_SIZE, namelen) != 0) break;
+ count++;
+ }
+ if (count > 1)
+ {
+ PUT2(code, 2+LINK_SIZE, offset);
+ PUT2(code, 2+LINK_SIZE+IMM2_SIZE, count);
+ skipbytes += IMM2_SIZE;
+ code[1+LINK_SIZE]++;
+ }
+ else /* Not a duplicated name */
+ {
+ PUT2(code, 2+LINK_SIZE, recno);
+ }
}
/* If terminator == CHAR_NULL it means that the name followed directly
after the opening parenthesis [e.g. (?(abc)...] and in this case there
are some further alternatives to try. For the cases where terminator !=
- 0 [things like (?(<name>... or (?('name')... or (?(R&name)... ] we have
- now checked all the possibilities, so give an error. */
+ CHAR_NULL [things like (?(<name>... or (?('name')... or (?(R&name)... ]
+ we have now checked all the possibilities, so give an error. */
else if (terminator != CHAR_NULL)
{
@@ -5933,19 +6766,11 @@ for (;; ptr++)
skipbytes = 1;
}
- /* Check for the "name" actually being a subpattern number. We are
- in the second pass here, so final_bracount is set. */
-
- else if (recno > 0 && recno <= cd->final_bracount)
- {
- PUT2(code, 2+LINK_SIZE, recno);
- }
-
- /* Either an unidentified subpattern, or a reference to (?(0) */
+ /* Reference to an unidentified subpattern. */
else
{
- *errorcodeptr = (recno == 0)? ERR35: ERR15;
+ *errorcodeptr = ERR15;
goto FAILED;
}
break;
@@ -5958,11 +6783,18 @@ for (;; ptr++)
ptr++;
break;
+ /* Optimize (?!) to (*FAIL) unless it is quantified - which is a weird
+ thing to do, but Perl allows all assertions to be quantified, and when
+ they contain capturing parentheses there may be a potential use for
+ this feature. Not that that applies to a quantified (?!) but we allow
+ it for uniformity. */
/* ------------------------------------------------------------ */
case CHAR_EXCLAMATION_MARK: /* Negative lookahead */
ptr++;
- if (*ptr == CHAR_RIGHT_PARENTHESIS) /* Optimize (?!) */
+ if (*ptr == CHAR_RIGHT_PARENTHESIS && ptr[1] != CHAR_ASTERISK &&
+ ptr[1] != CHAR_PLUS && ptr[1] != CHAR_QUESTION_MARK &&
+ (ptr[1] != CHAR_LEFT_CURLY_BRACKET || !is_counted_repeat(ptr+2)))
{
*code++ = OP_FAIL;
previous = NULL;
@@ -6055,124 +6887,110 @@ for (;; ptr++)
/* ------------------------------------------------------------ */
DEFINE_NAME: /* Come here from (?< handling */
case CHAR_APOSTROPHE:
+ terminator = (*ptr == CHAR_LESS_THAN_SIGN)?
+ CHAR_GREATER_THAN_SIGN : CHAR_APOSTROPHE;
+ name = ++ptr;
+ if (IS_DIGIT(*ptr))
{
- terminator = (*ptr == CHAR_LESS_THAN_SIGN)?
- CHAR_GREATER_THAN_SIGN : CHAR_APOSTROPHE;
- name = ++ptr;
+ *errorcodeptr = ERR84; /* Group name must start with non-digit */
+ goto FAILED;
+ }
+ while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0) ptr++;
+ namelen = (int)(ptr - name);
- while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0) ptr++;
- namelen = (int)(ptr - name);
+ /* In the pre-compile phase, do a syntax check, remember the longest
+ name, and then remember the group in a vector, expanding it if
+ necessary. Duplicates for the same number are skipped; other duplicates
+ are checked for validity. In the actual compile, there is nothing to
+ do. */
+
+ if (lengthptr != NULL)
+ {
+ named_group *ng;
+ pcre_uint32 number = cd->bracount + 1;
- /* In the pre-compile phase, just do a syntax check. */
+ if (*ptr != (pcre_uchar)terminator)
+ {
+ *errorcodeptr = ERR42;
+ goto FAILED;
+ }
- if (lengthptr != NULL)
+ if (cd->names_found >= MAX_NAME_COUNT)
{
- if (*ptr != (pcre_uchar)terminator)
- {
- *errorcodeptr = ERR42;
- goto FAILED;
- }
- if (cd->names_found >= MAX_NAME_COUNT)
+ *errorcodeptr = ERR49;
+ goto FAILED;
+ }
+
+ if (namelen + IMM2_SIZE + 1 > cd->name_entry_size)
+ {
+ cd->name_entry_size = namelen + IMM2_SIZE + 1;
+ if (namelen > MAX_NAME_SIZE)
{
- *errorcodeptr = ERR49;
+ *errorcodeptr = ERR48;
goto FAILED;
}
- if (namelen + IMM2_SIZE + 1 > cd->name_entry_size)
+ }
+
+ /* Scan the list to check for duplicates. For duplicate names, if the
+ number is the same, break the loop, which causes the name to be
+ discarded; otherwise, if DUPNAMES is not set, give an error.
+ If it is set, allow the name with a different number, but continue
+ scanning in case this is a duplicate with the same number. For
+ non-duplicate names, give an error if the number is duplicated. */
+
+ ng = cd->named_groups;
+ for (i = 0; i < cd->names_found; i++, ng++)
+ {
+ if (namelen == ng->length &&
+ STRNCMP_UC_UC(name, ng->name, namelen) == 0)
{
- cd->name_entry_size = namelen + IMM2_SIZE + 1;
- if (namelen > MAX_NAME_SIZE)
+ if (ng->number == number) break;
+ if ((options & PCRE_DUPNAMES) == 0)
{
- *errorcodeptr = ERR48;
+ *errorcodeptr = ERR43;
goto FAILED;
}
+ cd->dupnames = TRUE; /* Duplicate names exist */
+ }
+ else if (ng->number == number)
+ {
+ *errorcodeptr = ERR65;
+ goto FAILED;
}
}
- /* In the real compile, create the entry in the table, maintaining
- alphabetical order. Duplicate names for different numbers are
- permitted only if PCRE_DUPNAMES is set. Duplicate names for the same
- number are always OK. (An existing number can be re-used if (?|
- appears in the pattern.) In either event, a duplicate name results in
- a duplicate entry in the table, even if the number is the same. This
- is because the number of names, and hence the table size, is computed
- in the pre-compile, and it affects various numbers and pointers which
- would all have to be modified, and the compiled code moved down, if
- duplicates with the same number were omitted from the table. This
- doesn't seem worth the hassle. However, *different* names for the
- same number are not permitted. */
-
- else
+ if (i >= cd->names_found) /* Not a duplicate with same number */
{
- BOOL dupname = FALSE;
- slot = cd->name_table;
+ /* Increase the list size if necessary */
- for (i = 0; i < cd->names_found; i++)
+ if (cd->names_found >= cd->named_group_list_size)
{
- int crc = memcmp(name, slot+IMM2_SIZE, IN_UCHARS(namelen));
- if (crc == 0)
- {
- if (slot[IMM2_SIZE+namelen] == 0)
- {
- if (GET2(slot, 0) != cd->bracount + 1 &&
- (options & PCRE_DUPNAMES) == 0)
- {
- *errorcodeptr = ERR43;
- goto FAILED;
- }
- else dupname = TRUE;
- }
- else crc = -1; /* Current name is a substring */
- }
-
- /* Make space in the table and break the loop for an earlier
- name. For a duplicate or later name, carry on. We do this for
- duplicates so that in the simple case (when ?(| is not used) they
- are in order of their numbers. */
+ int newsize = cd->named_group_list_size * 2;
+ named_group *newspace = (PUBL(malloc))
+ (newsize * sizeof(named_group));
- if (crc < 0)
+ if (newspace == NULL)
{
- memmove(slot + cd->name_entry_size, slot,
- IN_UCHARS((cd->names_found - i) * cd->name_entry_size));
- break;
+ *errorcodeptr = ERR21;
+ goto FAILED;
}
- /* Continue the loop for a later or duplicate name */
-
- slot += cd->name_entry_size;
- }
-
- /* For non-duplicate names, check for a duplicate number before
- adding the new name. */
-
- if (!dupname)
- {
- pcre_uchar *cslot = cd->name_table;
- for (i = 0; i < cd->names_found; i++)
- {
- if (cslot != slot)
- {
- if (GET2(cslot, 0) == cd->bracount + 1)
- {
- *errorcodeptr = ERR65;
- goto FAILED;
- }
- }
- else i--;
- cslot += cd->name_entry_size;
- }
+ memcpy(newspace, cd->named_groups,
+ cd->named_group_list_size * sizeof(named_group));
+ if (cd->named_group_list_size > NAMED_GROUP_LIST_SIZE)
+ (PUBL(free))((void *)cd->named_groups);
+ cd->named_groups = newspace;
+ cd->named_group_list_size = newsize;
}
- PUT2(slot, 0, cd->bracount + 1);
- memcpy(slot + IMM2_SIZE, name, IN_UCHARS(namelen));
- slot[IMM2_SIZE + namelen] = 0;
+ cd->named_groups[cd->names_found].name = name;
+ cd->named_groups[cd->names_found].length = namelen;
+ cd->named_groups[cd->names_found].number = number;
+ cd->names_found++;
}
}
- /* In both pre-compile and compile, count the number of names we've
- encountered. */
-
- cd->names_found++;
- ptr++; /* Move past > or ' */
+ ptr++; /* Move past > or ' in both passes. */
goto NUMBERED_GROUP;
@@ -6190,6 +7008,11 @@ for (;; ptr++)
NAMED_REF_OR_RECURSE:
name = ++ptr;
+ if (IS_DIGIT(*ptr))
+ {
+ *errorcodeptr = ERR84; /* Group name must start with non-digit */
+ goto FAILED;
+ }
while (MAX_255(*ptr) && (cd->ctypes[*ptr] & ctype_word) != 0) ptr++;
namelen = (int)(ptr - name);
@@ -6202,7 +7025,7 @@ for (;; ptr++)
if (lengthptr != NULL)
{
- const pcre_uchar *temp;
+ named_group *ng;
if (namelen == 0)
{
@@ -6220,27 +7043,29 @@ for (;; ptr++)
goto FAILED;
}
- /* The name table does not exist in the first pass, so we cannot
- do a simple search as in the code below. Instead, we have to scan the
- pattern to find the number. It is important that we scan it only as
- far as we have got because the syntax of named subpatterns has not
- been checked for the rest of the pattern, and find_parens() assumes
- correct syntax. In any case, it's a waste of resources to scan
- further. We stop the scan at the current point by temporarily
- adjusting the value of cd->endpattern. */
-
- temp = cd->end_pattern;
- cd->end_pattern = ptr;
- recno = find_parens(cd, name, namelen,
- (options & PCRE_EXTENDED) != 0, utf);
- cd->end_pattern = temp;
- if (recno < 0) recno = 0; /* Forward ref; set dummy number */
+ /* The name table does not exist in the first pass; instead we must
+ scan the list of names encountered so far in order to get the
+ number. If the name is not found, set the value to 0 for a forward
+ reference. */
+
+ ng = cd->named_groups;
+ for (i = 0; i < cd->names_found; i++, ng++)
+ {
+ if (namelen == ng->length &&
+ STRNCMP_UC_UC(name, ng->name, namelen) == 0)
+ break;
+ }
+ recno = (i < cd->names_found)? ng->number : 0;
+
+ /* Count named back references. */
+
+ if (!is_recurse) cd->namedrefcount++;
}
- /* In the real compile, seek the name in the table. We check the name
+ /* In the real compile, search the name table. We check the name
first, and then check that we have reached the end of the name in the
- table. That way, if the name that is longer than any in the table,
- the comparison will fail without reading beyond the table entry. */
+ table. That way, if the name is longer than any in the table, the
+ comparison will fail without reading beyond the table entry. */
else
{
@@ -6253,24 +7078,76 @@ for (;; ptr++)
slot += cd->name_entry_size;
}
- if (i < cd->names_found) /* Back reference */
+ if (i < cd->names_found)
{
recno = GET2(slot, 0);
}
- else if ((recno = /* Forward back reference */
- find_parens(cd, name, namelen,
- (options & PCRE_EXTENDED) != 0, utf)) <= 0)
+ else
{
*errorcodeptr = ERR15;
goto FAILED;
}
}
- /* In both phases, we can now go to the code than handles numerical
- recursion or backreferences. */
+ /* In both phases, for recursions, we can now go to the code than
+ handles numerical recursion. */
if (is_recurse) goto HANDLE_RECURSION;
- else goto HANDLE_REFERENCE;
+
+ /* In the second pass we must see if the name is duplicated. If so, we
+ generate a different opcode. */
+
+ if (lengthptr == NULL && cd->dupnames)
+ {
+ int count = 1;
+ unsigned int index = i;
+ pcre_uchar *cslot = slot + cd->name_entry_size;
+
+ for (i++; i < cd->names_found; i++)
+ {
+ if (STRCMP_UC_UC(slot + IMM2_SIZE, cslot + IMM2_SIZE) != 0) break;
+ count++;
+ cslot += cd->name_entry_size;
+ }
+
+ if (count > 1)
+ {
+ if (firstcharflags == REQ_UNSET) firstcharflags = REQ_NONE;
+ previous = code;
+ *code++ = ((options & PCRE_CASELESS) != 0)? OP_DNREFI : OP_DNREF;
+ PUT2INC(code, 0, index);
+ PUT2INC(code, 0, count);
+
+ /* Process each potentially referenced group. */
+
+ for (; slot < cslot; slot += cd->name_entry_size)
+ {
+ open_capitem *oc;
+ recno = GET2(slot, 0);
+ cd->backref_map |= (recno < 32)? (1 << recno) : 1;
+ if (recno > cd->top_backref) cd->top_backref = recno;
+
+ /* Check to see if this back reference is recursive, that it, it
+ is inside the group that it references. A flag is set so that the
+ group can be made atomic. */
+
+ for (oc = cd->open_caps; oc != NULL; oc = oc->next)
+ {
+ if (oc->number == recno)
+ {
+ oc->flag = TRUE;
+ break;
+ }
+ }
+ }
+
+ continue; /* End of back ref handling */
+ }
+ }
+
+ /* First pass, or a non-duplicated name. */
+
+ goto HANDLE_REFERENCE;
/* ------------------------------------------------------------ */
@@ -6369,8 +7246,7 @@ for (;; ptr++)
if (called == NULL)
{
- if (find_parens(cd, NULL, recno,
- (options & PCRE_EXTENDED) != 0, utf) < 0)
+ if (recno > cd->final_bracount)
{
*errorcodeptr = ERR15;
goto FAILED;
@@ -6529,10 +7405,19 @@ for (;; ptr++)
skipbytes = IMM2_SIZE;
}
- /* Process nested bracketed regex. Assertions used not to be repeatable,
- but this was changed for Perl compatibility, so all kinds can now be
- repeated. We copy code into a non-register variable (tempcode) in order to
- be able to pass its address because some compilers complain otherwise. */
+ /* Process nested bracketed regex. First check for parentheses nested too
+ deeply. */
+
+ if ((cd->parens_depth += 1) > PARENS_NEST_LIMIT)
+ {
+ *errorcodeptr = ERR82;
+ goto FAILED;
+ }
+
+ /* Assertions used not to be repeatable, but this was changed for Perl
+ compatibility, so all kinds can now be repeated. We copy code into a
+ non-register variable (tempcode) in order to be able to pass its address
+ because some compilers complain otherwise. */
previous = code; /* For handling repetition */
*code = bravalue;
@@ -6563,6 +7448,8 @@ for (;; ptr++)
))
goto FAILED;
+ cd->parens_depth -= 1;
+
/* If this was an atomic group and there are no capturing groups within it,
generate OP_ONCE_NC instead of OP_ONCE. */
@@ -6738,10 +7625,9 @@ for (;; ptr++)
case CHAR_BACKSLASH:
tempptr = ptr;
escape = check_escape(&ptr, &ec, errorcodeptr, cd->bracount, options, FALSE);
-
if (*errorcodeptr != 0) goto FAILED;
- if (escape == 0)
+ if (escape == 0) /* The escape coded a single character */
c = ec;
else
{
@@ -6778,44 +7664,31 @@ for (;; ptr++)
if (escape == ESC_g)
{
const pcre_uchar *p;
+ pcre_uint32 cf;
+
save_hwm = cd->hwm; /* Normally this is set when '(' is read */
terminator = (*(++ptr) == CHAR_LESS_THAN_SIGN)?
CHAR_GREATER_THAN_SIGN : CHAR_APOSTROPHE;
/* These two statements stop the compiler for warning about possibly
unset variables caused by the jump to HANDLE_NUMERICAL_RECURSION. In
- fact, because we actually check for a number below, the paths that
+ fact, because we do the check for a number below, the paths that
would actually be in error are never taken. */
skipbytes = 0;
reset_bracount = FALSE;
- /* Test for a name */
+ /* If it's not a signed or unsigned number, treat it as a name. */
- if (ptr[1] != CHAR_PLUS && ptr[1] != CHAR_MINUS)
+ cf = ptr[1];
+ if (cf != CHAR_PLUS && cf != CHAR_MINUS && !IS_DIGIT(cf))
{
- BOOL is_a_number = TRUE;
- for (p = ptr + 1; *p != CHAR_NULL && *p != (pcre_uchar)terminator; p++)
- {
- if (!MAX_255(*p)) { is_a_number = FALSE; break; }
- if ((cd->ctypes[*p] & ctype_digit) == 0) is_a_number = FALSE;
- if ((cd->ctypes[*p] & ctype_word) == 0) break;
- }
- if (*p != (pcre_uchar)terminator)
- {
- *errorcodeptr = ERR57;
- break;
- }
- if (is_a_number)
- {
- ptr++;
- goto HANDLE_NUMERICAL_RECURSION;
- }
is_recurse = TRUE;
goto NAMED_REF_OR_RECURSE;
}
- /* Test a signed number in angle brackets or quotes. */
+ /* Signed or unsigned number (cf = ptr[1]) is known to be plus or minus
+ or a digit. */
p = ptr + 2;
while (IS_DIGIT(*p)) p++;
@@ -6855,7 +7728,10 @@ for (;; ptr++)
open_capitem *oc;
recno = -escape;
- HANDLE_REFERENCE: /* Come here from named backref handling */
+ /* Come here from named backref handling when the reference is to a
+ single group (i.e. not to a duplicated name. */
+
+ HANDLE_REFERENCE:
if (firstcharflags == REQ_UNSET) firstcharflags = REQ_NONE;
previous = code;
*code++ = ((options & PCRE_CASELESS) != 0)? OP_REFI : OP_REF;
@@ -6907,11 +7783,12 @@ for (;; ptr++)
can obtain the OP value by negating the escape value in the default
situation when PCRE_UCP is not set. When it *is* set, we substitute
Unicode property tests. Note that \b and \B do a one-character
- lookbehind. */
+ lookbehind, and \A also behaves as if it does. */
else
{
- if ((escape == ESC_b || escape == ESC_B) && cd->max_lookbehind == 0)
+ if ((escape == ESC_b || escape == ESC_B || escape == ESC_A) &&
+ cd->max_lookbehind == 0)
cd->max_lookbehind = 1;
#ifdef SUPPORT_UCP
if (escape >= ESC_DU && escape <= ESC_wu)
@@ -6951,8 +7828,8 @@ for (;; ptr++)
/* ===================================================================*/
/* Handle a literal character. It is guaranteed not to be whitespace or #
- when the extended flag is set. If we are in UTF-8 mode, it may be a
- multi-byte literal character. */
+ when the extended flag is set. If we are in a UTF mode, it may be a
+ multi-unit literal character. */
default:
NORMAL_CHAR:
@@ -6983,7 +7860,8 @@ for (;; ptr++)
*code++ = OP_PROP;
*code++ = PT_CLIST;
*code++ = c;
- if (firstcharflags == REQ_UNSET) firstcharflags = zerofirstcharflags = REQ_NONE;
+ if (firstcharflags == REQ_UNSET)
+ firstcharflags = zerofirstcharflags = REQ_NONE;
break;
}
}
@@ -7072,24 +7950,24 @@ out the amount of memory needed, as well as during the real compile phase. The
value of lengthptr distinguishes the two phases.
Arguments:
- options option bits, including any changes for this subpattern
- codeptr -> the address of the current code pointer
- ptrptr -> the address of the current pattern pointer
- errorcodeptr -> pointer to error code variable
- lookbehind TRUE if this is a lookbehind assertion
- reset_bracount TRUE to reset the count for each branch
- skipbytes skip this many bytes at start (for brackets and OP_COND)
- cond_depth depth of nesting for conditional subpatterns
- firstcharptr place to put the first required character
+ options option bits, including any changes for this subpattern
+ codeptr -> the address of the current code pointer
+ ptrptr -> the address of the current pattern pointer
+ errorcodeptr -> pointer to error code variable
+ lookbehind TRUE if this is a lookbehind assertion
+ reset_bracount TRUE to reset the count for each branch
+ skipbytes skip this many bytes at start (for brackets and OP_COND)
+ cond_depth depth of nesting for conditional subpatterns
+ firstcharptr place to put the first required character
firstcharflagsptr place to put the first character flags, or a negative number
- reqcharptr place to put the last required character
- reqcharflagsptr place to put the last required character flags, or a negative number
- bcptr pointer to the chain of currently open branches
- cd points to the data block with tables pointers etc.
- lengthptr NULL during the real compile phase
- points to length accumulator during pre-compile phase
-
-Returns: TRUE on success
+ reqcharptr place to put the last required character
+ reqcharflagsptr place to put the last required character flags, or a negative number
+ bcptr pointer to the chain of currently open branches
+ cd points to the data block with tables pointers etc.
+ lengthptr NULL during the real compile phase
+ points to length accumulator during pre-compile phase
+
+Returns: TRUE on success
*/
static BOOL
@@ -7540,9 +8418,9 @@ do {
switch (*scode)
{
case OP_CREF:
- case OP_NCREF:
+ case OP_DNCREF:
case OP_RREF:
- case OP_NRREF:
+ case OP_DNRREF:
case OP_DEF:
return FALSE;
@@ -7626,13 +8504,14 @@ return TRUE;
discarded, because they can cause conflicts with actual literals that follow.
However, if we end up without a first char setting for an unanchored pattern,
it is worth scanning the regex to see if there is an initial asserted first
-char. If all branches start with the same asserted char, or with a bracket all
-of whose alternatives start with the same asserted char (recurse ad lib), then
-we return that char, otherwise -1.
+char. If all branches start with the same asserted char, or with a
+non-conditional bracket all of whose alternatives start with the same asserted
+char (recurse ad lib), then we return that char, with the flags set to zero or
+REQ_CASELESS; otherwise return zero with REQ_NONE in the flags.
Arguments:
code points to start of expression (the bracket)
- flags points to the first char flags, or to REQ_NONE
+ flags points to the first char flags, or to REQ_NONE
inassert TRUE if in an assertion
Returns: the fixed first char, or 0 with REQ_NONE in flags
@@ -7669,7 +8548,6 @@ do {
case OP_ASSERT:
case OP_ONCE:
case OP_ONCE_NC:
- case OP_COND:
d = find_firstassertedchar(scode, &dflags, op == OP_ASSERT);
if (dflags < 0)
return 0;
@@ -7714,6 +8592,61 @@ return c;
/*************************************************
+* Add an entry to the name/number table *
+*************************************************/
+
+/* This function is called between compiling passes to add an entry to the
+name/number table, maintaining alphabetical order. Checking for permitted
+and forbidden duplicates has already been done.
+
+Arguments:
+ cd the compile data block
+ name the name to add
+ length the length of the name
+ groupno the group number
+
+Returns: nothing
+*/
+
+static void
+add_name(compile_data *cd, const pcre_uchar *name, int length,
+ unsigned int groupno)
+{
+int i;
+pcre_uchar *slot = cd->name_table;
+
+for (i = 0; i < cd->names_found; i++)
+ {
+ int crc = memcmp(name, slot+IMM2_SIZE, IN_UCHARS(length));
+ if (crc == 0 && slot[IMM2_SIZE+length] != 0)
+ crc = -1; /* Current name is a substring */
+
+ /* Make space in the table and break the loop for an earlier name. For a
+ duplicate or later name, carry on. We do this for duplicates so that in the
+ simple case (when ?(| is not used) they are in order of their numbers. In all
+ cases they are in the order in which they appear in the pattern. */
+
+ if (crc < 0)
+ {
+ memmove(slot + cd->name_entry_size, slot,
+ IN_UCHARS((cd->names_found - i) * cd->name_entry_size));
+ break;
+ }
+
+ /* Continue the loop for a later or duplicate name */
+
+ slot += cd->name_entry_size;
+ }
+
+PUT2(slot, 0, groupno);
+memcpy(slot + IMM2_SIZE, name, IN_UCHARS(length));
+slot[IMM2_SIZE + length] = 0;
+cd->names_found++;
+}
+
+
+
+/*************************************************
* Compile a Regular Expression *
*************************************************/
@@ -7775,12 +8708,15 @@ pcre32_compile2(PCRE_SPTR32 pattern, int options, int *errorcodeptr,
{
REAL_PCRE *re;
int length = 1; /* For final END opcode */
-pcre_uint32 firstchar, reqchar;
pcre_int32 firstcharflags, reqcharflags;
+pcre_uint32 firstchar, reqchar;
+pcre_uint32 limit_match = PCRE_UINT32_MAX;
+pcre_uint32 limit_recursion = PCRE_UINT32_MAX;
int newline;
int errorcode = 0;
int skipatstart = 0;
BOOL utf;
+BOOL never_utf = FALSE;
size_t size;
pcre_uchar *code;
const pcre_uchar *codestart;
@@ -7797,6 +8733,11 @@ new memory is obtained from malloc(). */
pcre_uchar cworkspace[COMPILE_WORK_SIZE];
+/* This vector is used for remembering name groups during the pre-compile. In a
+similar way to cworkspace, it can be expanded using malloc() if necessary. */
+
+named_group named_groups[NAMED_GROUP_LIST_SIZE];
+
/* Set this early so that early errors get offset 0. */
ptr = (const pcre_uchar *)pattern;
@@ -7840,9 +8781,15 @@ if ((options & ~PUBLIC_COMPILE_OPTIONS) != 0)
goto PCRE_EARLY_ERROR_RETURN;
}
+/* If PCRE_NEVER_UTF is set, remember it. */
+
+if ((options & PCRE_NEVER_UTF) != 0) never_utf = TRUE;
+
/* Check for global one-time settings at the start of the pattern, and remember
the offset for later. */
+cd->external_flags = 0; /* Initialize here for LIMIT_MATCH/RECURSION */
+
while (ptr[skipatstart] == CHAR_LEFT_PARENTHESIS &&
ptr[skipatstart+1] == CHAR_ASTERISK)
{
@@ -7870,9 +8817,49 @@ PCRE_UTF8 == PCRE_UTF16 == PCRE_UTF32. */
{ skipatstart += 6; options |= PCRE_UTF8; continue; }
else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_UCP_RIGHTPAR, 4) == 0)
{ skipatstart += 6; options |= PCRE_UCP; continue; }
+ else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_NO_AUTO_POSSESS_RIGHTPAR, 16) == 0)
+ { skipatstart += 18; options |= PCRE_NO_AUTO_POSSESS; continue; }
else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_NO_START_OPT_RIGHTPAR, 13) == 0)
{ skipatstart += 15; options |= PCRE_NO_START_OPTIMIZE; continue; }
+ else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_LIMIT_MATCH_EQ, 12) == 0)
+ {
+ pcre_uint32 c = 0;
+ int p = skipatstart + 14;
+ while (isdigit(ptr[p]))
+ {
+ if (c > PCRE_UINT32_MAX / 10 - 1) break; /* Integer overflow */
+ c = c*10 + ptr[p++] - CHAR_0;
+ }
+ if (ptr[p++] != CHAR_RIGHT_PARENTHESIS) break;
+ if (c < limit_match)
+ {
+ limit_match = c;
+ cd->external_flags |= PCRE_MLSET;
+ }
+ skipatstart = p;
+ continue;
+ }
+
+ else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_LIMIT_RECURSION_EQ, 16) == 0)
+ {
+ pcre_uint32 c = 0;
+ int p = skipatstart + 18;
+ while (isdigit(ptr[p]))
+ {
+ if (c > PCRE_UINT32_MAX / 10 - 1) break; /* Integer overflow check */
+ c = c*10 + ptr[p++] - CHAR_0;
+ }
+ if (ptr[p++] != CHAR_RIGHT_PARENTHESIS) break;
+ if (c < limit_recursion)
+ {
+ limit_recursion = c;
+ cd->external_flags |= PCRE_RLSET;
+ }
+ skipatstart = p;
+ continue;
+ }
+
if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_CR_RIGHTPAR, 3) == 0)
{ skipatstart += 5; newnl = PCRE_NEWLINE_CR; }
else if (STRNCMP_UC_C8(ptr+skipatstart+2, STRING_LF_RIGHTPAR, 3) == 0)
@@ -7898,6 +8885,11 @@ PCRE_UTF8 == PCRE_UTF16 == PCRE_UTF32. */
/* PCRE_UTF(16|32) have the same value as PCRE_UTF8. */
utf = (options & PCRE_UTF8) != 0;
+if (utf && never_utf)
+ {
+ errorcode = ERR78;
+ goto PCRE_EARLY_ERROR_RETURN2;
+ }
/* Can't support UTF unless PCRE has been compiled to include the code. The
return of an error code from PRIV(valid_utf)() is a new feature, introduced in
@@ -8010,17 +9002,21 @@ cd->bracount = cd->final_bracount = 0;
cd->names_found = 0;
cd->name_entry_size = 0;
cd->name_table = NULL;
+cd->dupnames = FALSE;
+cd->namedrefcount = 0;
cd->start_code = cworkspace;
cd->hwm = cworkspace;
cd->start_workspace = cworkspace;
cd->workspace_size = COMPILE_WORK_SIZE;
+cd->named_groups = named_groups;
+cd->named_group_list_size = NAMED_GROUP_LIST_SIZE;
cd->start_pattern = (const pcre_uchar *)pattern;
cd->end_pattern = (const pcre_uchar *)(pattern + STRLEN_UC((const pcre_uchar *)pattern));
cd->req_varyopt = 0;
+cd->parens_depth = 0;
cd->assert_depth = 0;
cd->max_lookbehind = 0;
cd->external_options = options;
-cd->external_flags = 0;
cd->open_caps = NULL;
/* Now do the pre-compile. On error, errorcode will be set non-zero, so we
@@ -8032,6 +9028,7 @@ outside can help speed up starting point checks. */
ptr += skipatstart;
code = cworkspace;
*code = OP_BRA;
+
(void)compile_regex(cd->external_options, &code, &ptr, &errorcode, FALSE,
FALSE, 0, 0, &firstchar, &firstcharflags, &reqchar, &reqcharflags, NULL,
cd, &length);
@@ -8046,14 +9043,23 @@ if (length > MAX_PATTERN_SIZE)
goto PCRE_EARLY_ERROR_RETURN;
}
-/* Compute the size of data block needed and get it, either from malloc or
-externally provided function. Integer overflow should no longer be possible
-because nowadays we limit the maximum value of cd->names_found and
-cd->name_entry_size. */
+/* If there are groups with duplicate names and there are also references by
+name, we must allow for the possibility of named references to duplicated
+groups. These require an extra data item each. */
-size = sizeof(REAL_PCRE) + (length + cd->names_found * cd->name_entry_size) * sizeof(pcre_uchar);
-re = (REAL_PCRE *)(PUBL(malloc))(size);
+if (cd->dupnames && cd->namedrefcount > 0)
+ length += cd->namedrefcount * IMM2_SIZE * sizeof(pcre_uchar);
+
+/* Compute the size of the data block for storing the compiled pattern. Integer
+overflow should no longer be possible because nowadays we limit the maximum
+value of cd->names_found and cd->name_entry_size. */
+
+size = sizeof(REAL_PCRE) +
+ (length + cd->names_found * cd->name_entry_size) * sizeof(pcre_uchar);
+
+/* Get the memory. */
+re = (REAL_PCRE *)(PUBL(malloc))(size);
if (re == NULL)
{
errorcode = ERR21;
@@ -8070,6 +9076,8 @@ re->magic_number = MAGIC_NUMBER;
re->size = (int)size;
re->options = cd->external_options;
re->flags = cd->external_flags;
+re->limit_match = limit_match;
+re->limit_recursion = limit_recursion;
re->first_char = 0;
re->req_char = 0;
re->name_table_offset = sizeof(REAL_PCRE) / sizeof(pcre_uchar);
@@ -8079,7 +9087,9 @@ re->ref_count = 0;
re->tables = (tables == PRIV(default_tables))? NULL : tables;
re->nullpad = NULL;
#ifdef COMPILE_PCRE32
-re->dummy1 = re->dummy2 = 0;
+re->dummy = 0;
+#else
+re->dummy1 = re->dummy2 = re->dummy3 = 0;
#endif
/* The starting points of the name/number translation table and of the code are
@@ -8090,10 +9100,10 @@ field; this time it's used for remembering forward references to subpatterns.
*/
cd->final_bracount = cd->bracount; /* Save for checking forward references */
+cd->parens_depth = 0;
cd->assert_depth = 0;
cd->bracount = 0;
cd->max_lookbehind = 0;
-cd->names_found = 0;
cd->name_table = (pcre_uchar *)re + re->name_table_offset;
codestart = cd->name_table + re->name_entry_size * re->name_count;
cd->start_code = codestart;
@@ -8104,6 +9114,20 @@ cd->had_pruneorskip = FALSE;
cd->check_lookbehind = FALSE;
cd->open_caps = NULL;
+/* If any named groups were found, create the name/number table from the list
+created in the first pass. */
+
+if (cd->names_found > 0)
+ {
+ int i = cd->names_found;
+ named_group *ng = cd->named_groups;
+ cd->names_found = 0;
+ for (; i > 0; i--, ng++)
+ add_name(cd, ng->name, ng->length, ng->number);
+ if (cd->named_group_list_size > NAMED_GROUP_LIST_SIZE)
+ (PUBL(free))((void *)cd->named_groups);
+ }
+
/* Set up a starting, non-extracting bracket, then compile the expression. On
error, errorcode will be set non-zero, so we don't need to look at the result
of the function here. */
@@ -8167,16 +9191,24 @@ if (cd->hwm > cd->start_workspace)
}
}
-/* If the workspace had to be expanded, free the new memory. */
+/* If the workspace had to be expanded, free the new memory. Set the pointer to
+NULL to indicate that forward references have been filled in. */
if (cd->workspace_size > COMPILE_WORK_SIZE)
(PUBL(free))((void *)cd->start_workspace);
+cd->start_workspace = NULL;
/* Give an error if there's back reference to a non-existent capturing
subpattern. */
if (errorcode == 0 && re->top_backref > re->top_bracket) errorcode = ERR15;
+/* Unless disabled, check whether single character iterators can be
+auto-possessified. The function overwrites the appropriate opcode values. */
+
+if ((options & PCRE_NO_AUTO_POSSESS) == 0)
+ auto_possessify((pcre_uchar *)codestart, utf, cd);
+
/* If there were any lookbehind assertions that contained OP_RECURSE
(recursions or subroutine calls), a flag is set for them to be checked here,
because they may contain forward references. Actual recursions cannot be fixed
@@ -8374,6 +9406,20 @@ if (code - codestart > length)
}
#endif /* PCRE_DEBUG */
+/* Check for a pattern than can match an empty string, so that this information
+can be provided to applications. */
+
+do
+ {
+ if (could_be_empty_branch(codestart, code, utf, cd, NULL))
+ {
+ re->flags |= PCRE_MATCH_EMPTY;
+ break;
+ }
+ codestart += GET(codestart, 1);
+ }
+while (*codestart == OP_ALT);
+
#if defined COMPILE_PCRE8
return (pcre *)re;
#elif defined COMPILE_PCRE16
@@ -8384,3 +9430,4 @@ return (pcre32 *)re;
}
/* End of pcre_compile.c */
+
diff --git a/ext/pcre/pcrelib/pcre_config.c b/ext/pcre/pcrelib/pcre_config.c
index 3d5689f62c..1cbdd9c960 100644
--- a/ext/pcre/pcrelib/pcre_config.c
+++ b/ext/pcre/pcrelib/pcre_config.c
@@ -161,6 +161,10 @@ switch (what)
*((int *)where) = POSIX_MALLOC_THRESHOLD;
break;
+ case PCRE_CONFIG_PARENS_LIMIT:
+ *((unsigned long int *)where) = PARENS_NEST_LIMIT;
+ break;
+
case PCRE_CONFIG_MATCH_LIMIT:
*((unsigned long int *)where) = MATCH_LIMIT;
break;
diff --git a/ext/pcre/pcrelib/pcre_exec.c b/ext/pcre/pcrelib/pcre_exec.c
index 05d0e52d33..a3f0c1923f 100644
--- a/ext/pcre/pcrelib/pcre_exec.c
+++ b/ext/pcre/pcrelib/pcre_exec.c
@@ -6,7 +6,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -56,6 +56,20 @@ possible. There are also some static supporting functions. */
#undef min
#undef max
+/* The md->capture_last field uses the lower 16 bits for the last captured
+substring (which can never be greater than 65535) and a bit in the top half
+to mean "capture vector overflowed". This odd way of doing things was
+implemented when it was realized that preserving and restoring the overflow bit
+whenever the last capture number was saved/restored made for a neater
+interface, and doing it this way saved on (a) another variable, which would
+have increased the stack frame size (a big NO-NO in PCRE) and (b) another
+separate set of save/restore instructions. The following defines are used in
+implementing this. */
+
+#define CAPLMASK 0x0000ffff /* The bits used for last_capture */
+#define OVFLMASK 0xffff0000 /* The bits used for the overflow flag */
+#define OVFLBIT 0x00010000 /* The bit that is set for overflow */
+
/* Values for setting in md->match_function_type to indicate two special types
of call to match(). We do it this way to save on using another stack variable,
as stack usage is to be discouraged. */
@@ -73,13 +87,17 @@ defined PCRE_ERROR_xxx codes, which are all negative. */
negative to avoid the external error codes. */
#define MATCH_ACCEPT (-999)
-#define MATCH_COMMIT (-998)
-#define MATCH_KETRPOS (-997)
-#define MATCH_ONCE (-996)
+#define MATCH_KETRPOS (-998)
+#define MATCH_ONCE (-997)
+/* The next 5 must be kept together and in sequence so that a test that checks
+for any one of them can use a range. */
+#define MATCH_COMMIT (-996)
#define MATCH_PRUNE (-995)
#define MATCH_SKIP (-994)
#define MATCH_SKIP_ARG (-993)
#define MATCH_THEN (-992)
+#define MATCH_BACKTRACK_MAX MATCH_THEN
+#define MATCH_BACKTRACK_MIN MATCH_COMMIT
/* Maximum number of ints of offset to save on the stack for recursive calls.
If the offset vector is bigger, malloc is used. This should be a multiple of 3,
@@ -89,8 +107,8 @@ because the offset vector is always a multiple of 3 long. */
/* Min and max values for the common repeats; for the maxima, 0 => infinity */
-static const char rep_min[] = { 0, 0, 1, 1, 0, 0 };
-static const char rep_max[] = { 0, 0, 0, 0, 1, 1 };
+static const char rep_min[] = { 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, };
+static const char rep_max[] = { 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, };
#ifdef PCRE_DEBUG
/*************************************************
@@ -149,7 +167,7 @@ match_ref(int offset, register PCRE_PUCHAR eptr, int length, match_data *md,
{
PCRE_PUCHAR eptr_start = eptr;
register PCRE_PUCHAR p = md->start_subject + md->offset_vector[offset];
-#ifdef SUPPORT_UTF
+#if defined SUPPORT_UTF && defined SUPPORT_UCP
BOOL utf = md->utf;
#endif
@@ -177,8 +195,7 @@ ASCII characters. */
if (caseless)
{
-#ifdef SUPPORT_UTF
-#ifdef SUPPORT_UCP
+#if defined SUPPORT_UTF && defined SUPPORT_UCP
if (utf)
{
/* Match characters up to the end of the reference. NOTE: the number of
@@ -212,14 +229,13 @@ if (caseless)
}
else
#endif
-#endif
/* The same code works when not in UTF-8 mode and in UTF-8 mode when there
is no UCP support. */
{
while (length-- > 0)
{
- pcre_uchar cc, cp;
+ pcre_uint32 cc, cp;
if (eptr >= md->end_subject) return -2; /* Partial match */
cc = RAWUCHARTEST(eptr);
cp = RAWUCHARTEST(p);
@@ -416,10 +432,10 @@ typedef struct heapframe {
int Xlength;
int Xmax;
int Xmin;
- int Xnumber;
+ unsigned int Xnumber;
int Xoffset;
- int Xop;
- int Xsave_capture_last;
+ unsigned int Xop;
+ pcre_int32 Xsave_capture_last;
int Xsave_offset1, Xsave_offset2, Xsave_offset3;
int Xstacksave[REC_STACK_SAVE_MAX];
@@ -634,8 +650,8 @@ int max;
int min;
unsigned int number;
int offset;
-pcre_uchar op;
-int save_capture_last;
+unsigned int op;
+pcre_int32 save_capture_last;
int save_offset1, save_offset2, save_offset3;
int stacksave[REC_STACK_SAVE_MAX];
@@ -763,23 +779,16 @@ for (;;)
case OP_FAIL:
RRETURN(MATCH_NOMATCH);
- /* COMMIT overrides PRUNE, SKIP, and THEN */
-
case OP_COMMIT:
RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
eptrb, RM52);
- if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE &&
- rrc != MATCH_SKIP && rrc != MATCH_SKIP_ARG &&
- rrc != MATCH_THEN)
- RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
RRETURN(MATCH_COMMIT);
- /* PRUNE overrides THEN */
-
case OP_PRUNE:
RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
eptrb, RM51);
- if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
RRETURN(MATCH_PRUNE);
case OP_PRUNE_ARG:
@@ -789,38 +798,39 @@ for (;;)
eptrb, RM56);
if ((rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) &&
md->mark == NULL) md->mark = ecode + 2;
- if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
RRETURN(MATCH_PRUNE);
- /* SKIP overrides PRUNE and THEN */
-
case OP_SKIP:
RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md,
eptrb, RM53);
- if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)
- RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
md->start_match_ptr = eptr; /* Pass back current position */
RRETURN(MATCH_SKIP);
/* Note that, for Perl compatibility, SKIP with an argument does NOT set
- nomatch_mark. There is a flag that disables this opcode when re-matching a
- pattern that ended with a SKIP for which there was not a matching MARK. */
+ nomatch_mark. When a pattern match ends with a SKIP_ARG for which there was
+ not a matching mark, we have to re-run the match, ignoring the SKIP_ARG
+ that failed and any that precede it (either they also failed, or were not
+ triggered). To do this, we maintain a count of executed SKIP_ARGs. If a
+ SKIP_ARG gets to top level, the match is re-run with md->ignore_skip_arg
+ set to the count of the one that failed. */
case OP_SKIP_ARG:
- if (md->ignore_skip_arg)
+ md->skip_arg_count++;
+ if (md->skip_arg_count <= md->ignore_skip_arg)
{
ecode += PRIV(OP_lengths)[*ecode] + ecode[1];
break;
}
RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode] + ecode[1], offset_top, md,
eptrb, RM57);
- if (rrc != MATCH_NOMATCH && rrc != MATCH_PRUNE && rrc != MATCH_THEN)
- RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
/* Pass back the current skip name by overloading md->start_match_ptr and
returning the special MATCH_SKIP_ARG return code. This will either be
caught by a matching MARK, or get to the top, where it causes a rematch
- with the md->ignore_skip_arg flag set. */
+ with md->ignore_skip_arg set to the value of md->skip_arg_count. */
md->start_match_ptr = ecode + 2;
RRETURN(MATCH_SKIP_ARG);
@@ -1066,6 +1076,7 @@ for (;;)
/* In all other cases, we have to make another call to match(). */
save_mark = md->mark;
+ save_capture_last = md->capture_last;
RMATCH(eptr, ecode + PRIV(OP_lengths)[*ecode], offset_top, md, eptrb,
RM2);
@@ -1097,6 +1108,7 @@ for (;;)
ecode += GET(ecode, 1);
md->mark = save_mark;
if (*ecode != OP_ALT) break;
+ md->capture_last = save_capture_last;
}
RRETURN(MATCH_NOMATCH);
@@ -1159,6 +1171,7 @@ for (;;)
ecode = md->start_code + code_offset;
save_capture_last = md->capture_last;
matched_once = TRUE;
+ mstart = md->start_match_ptr; /* In case \K changed it */
continue;
}
@@ -1218,6 +1231,7 @@ for (;;)
POSSESSIVE_NON_CAPTURE:
matched_once = FALSE;
code_offset = (int)(ecode - md->start_code);
+ save_capture_last = md->capture_last;
for (;;)
{
@@ -1230,6 +1244,7 @@ for (;;)
eptr = md->end_match_ptr;
ecode = md->start_code + code_offset;
matched_once = TRUE;
+ mstart = md->start_match_ptr; /* In case \K reset it */
continue;
}
@@ -1247,6 +1262,7 @@ for (;;)
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
ecode += GET(ecode, 1);
if (*ecode != OP_ALT) break;
+ md->capture_last = save_capture_last;
}
if (matched_once || allow_zero)
@@ -1258,25 +1274,32 @@ for (;;)
/* Control never reaches here. */
- /* Conditional group: compilation checked that there are no more than
- two branches. If the condition is false, skipping the first branch takes us
- past the end if there is only one branch, but that's OK because that is
- exactly what going to the ket would do. */
+ /* Conditional group: compilation checked that there are no more than two
+ branches. If the condition is false, skipping the first branch takes us
+ past the end of the item if there is only one branch, but that's exactly
+ what we want. */
case OP_COND:
case OP_SCOND:
- codelink = GET(ecode, 1);
+
+ /* The variable codelink will be added to ecode when the condition is
+ false, to get to the second branch. Setting it to the offset to the ALT
+ or KET, then incrementing ecode achieves this effect. We now have ecode
+ pointing to the condition or callout. */
+
+ codelink = GET(ecode, 1); /* Offset to the second branch */
+ ecode += 1 + LINK_SIZE; /* From this opcode */
/* Because of the way auto-callout works during compile, a callout item is
inserted between OP_COND and an assertion condition. */
- if (ecode[LINK_SIZE+1] == OP_CALLOUT)
+ if (*ecode == OP_CALLOUT)
{
if (PUBL(callout) != NULL)
{
PUBL(callout_block) cb;
cb.version = 2; /* Version 1 of the callout block */
- cb.callout_number = ecode[LINK_SIZE+2];
+ cb.callout_number = ecode[1];
cb.offset_vector = md->offset_vector;
#if defined COMPILE_PCRE8
cb.subject = (PCRE_SPTR)md->start_subject;
@@ -1288,215 +1311,130 @@ for (;;)
cb.subject_length = (int)(md->end_subject - md->start_subject);
cb.start_match = (int)(mstart - md->start_subject);
cb.current_position = (int)(eptr - md->start_subject);
- cb.pattern_position = GET(ecode, LINK_SIZE + 3);
- cb.next_item_length = GET(ecode, 3 + 2*LINK_SIZE);
+ cb.pattern_position = GET(ecode, 2);
+ cb.next_item_length = GET(ecode, 2 + LINK_SIZE);
cb.capture_top = offset_top/2;
- cb.capture_last = md->capture_last;
+ cb.capture_last = md->capture_last & CAPLMASK;
+ /* Internal change requires this for API compatibility. */
+ if (cb.capture_last == 0) cb.capture_last = -1;
cb.callout_data = md->callout_data;
cb.mark = md->nomatch_mark;
if ((rrc = (*PUBL(callout))(&cb)) > 0) RRETURN(MATCH_NOMATCH);
if (rrc < 0) RRETURN(rrc);
}
+
+ /* Advance ecode past the callout, so it now points to the condition. We
+ must adjust codelink so that the value of ecode+codelink is unchanged. */
+
ecode += PRIV(OP_lengths)[OP_CALLOUT];
+ codelink -= PRIV(OP_lengths)[OP_CALLOUT];
}
- condcode = ecode[LINK_SIZE+1];
+ /* Test the various possible conditions */
- /* Now see what the actual condition is */
-
- if (condcode == OP_RREF || condcode == OP_NRREF) /* Recursion test */
+ condition = FALSE;
+ switch(condcode = *ecode)
{
- if (md->recursive == NULL) /* Not recursing => FALSE */
- {
- condition = FALSE;
- ecode += GET(ecode, 1);
- }
- else
+ case OP_RREF: /* Numbered group recursion test */
+ if (md->recursive != NULL) /* Not recursing => FALSE */
{
- unsigned int recno = GET2(ecode, LINK_SIZE + 2); /* Recursion group number*/
+ unsigned int recno = GET2(ecode, 1); /* Recursion group number*/
condition = (recno == RREF_ANY || recno == md->recursive->group_num);
+ }
+ break;
- /* If the test is for recursion into a specific subpattern, and it is
- false, but the test was set up by name, scan the table to see if the
- name refers to any other numbers, and test them. The condition is true
- if any one is set. */
-
- if (!condition && condcode == OP_NRREF)
+ case OP_DNRREF: /* Duplicate named group recursion test */
+ if (md->recursive != NULL)
+ {
+ int count = GET2(ecode, 1 + IMM2_SIZE);
+ pcre_uchar *slot = md->name_table + GET2(ecode, 1) * md->name_entry_size;
+ while (count-- > 0)
{
- pcre_uchar *slotA = md->name_table;
- for (i = 0; i < md->name_count; i++)
- {
- if (GET2(slotA, 0) == recno) break;
- slotA += md->name_entry_size;
- }
-
- /* Found a name for the number - there can be only one; duplicate
- names for different numbers are allowed, but not vice versa. First
- scan down for duplicates. */
-
- if (i < md->name_count)
- {
- pcre_uchar *slotB = slotA;
- while (slotB > md->name_table)
- {
- slotB -= md->name_entry_size;
- if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
- {
- condition = GET2(slotB, 0) == md->recursive->group_num;
- if (condition) break;
- }
- else break;
- }
-
- /* Scan up for duplicates */
-
- if (!condition)
- {
- slotB = slotA;
- for (i++; i < md->name_count; i++)
- {
- slotB += md->name_entry_size;
- if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
- {
- condition = GET2(slotB, 0) == md->recursive->group_num;
- if (condition) break;
- }
- else break;
- }
- }
- }
+ unsigned int recno = GET2(slot, 0);
+ condition = recno == md->recursive->group_num;
+ if (condition) break;
+ slot += md->name_entry_size;
}
-
- /* Chose branch according to the condition */
-
- ecode += condition? 1 + IMM2_SIZE : GET(ecode, 1);
}
- }
+ break;
- else if (condcode == OP_CREF || condcode == OP_NCREF) /* Group used test */
- {
- offset = GET2(ecode, LINK_SIZE+2) << 1; /* Doubled ref number */
+ case OP_CREF: /* Numbered group used test */
+ offset = GET2(ecode, 1) << 1; /* Doubled ref number */
condition = offset < offset_top && md->offset_vector[offset] >= 0;
+ break;
- /* If the numbered capture is unset, but the reference was by name,
- scan the table to see if the name refers to any other numbers, and test
- them. The condition is true if any one is set. This is tediously similar
- to the code above, but not close enough to try to amalgamate. */
-
- if (!condition && condcode == OP_NCREF)
+ case OP_DNCREF: /* Duplicate named group used test */
{
- unsigned int refno = offset >> 1;
- pcre_uchar *slotA = md->name_table;
-
- for (i = 0; i < md->name_count; i++)
+ int count = GET2(ecode, 1 + IMM2_SIZE);
+ pcre_uchar *slot = md->name_table + GET2(ecode, 1) * md->name_entry_size;
+ while (count-- > 0)
{
- if (GET2(slotA, 0) == refno) break;
- slotA += md->name_entry_size;
- }
-
- /* Found a name for the number - there can be only one; duplicate names
- for different numbers are allowed, but not vice versa. First scan down
- for duplicates. */
-
- if (i < md->name_count)
- {
- pcre_uchar *slotB = slotA;
- while (slotB > md->name_table)
- {
- slotB -= md->name_entry_size;
- if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
- {
- offset = GET2(slotB, 0) << 1;
- condition = offset < offset_top &&
- md->offset_vector[offset] >= 0;
- if (condition) break;
- }
- else break;
- }
-
- /* Scan up for duplicates */
-
- if (!condition)
- {
- slotB = slotA;
- for (i++; i < md->name_count; i++)
- {
- slotB += md->name_entry_size;
- if (STRCMP_UC_UC(slotA + IMM2_SIZE, slotB + IMM2_SIZE) == 0)
- {
- offset = GET2(slotB, 0) << 1;
- condition = offset < offset_top &&
- md->offset_vector[offset] >= 0;
- if (condition) break;
- }
- else break;
- }
- }
+ offset = GET2(slot, 0) << 1;
+ condition = offset < offset_top && md->offset_vector[offset] >= 0;
+ if (condition) break;
+ slot += md->name_entry_size;
}
}
+ break;
- /* Chose branch according to the condition */
-
- ecode += condition? 1 + IMM2_SIZE : GET(ecode, 1);
- }
-
- else if (condcode == OP_DEF) /* DEFINE - always false */
- {
- condition = FALSE;
- ecode += GET(ecode, 1);
- }
+ case OP_DEF: /* DEFINE - always false */
+ break;
- /* The condition is an assertion. Call match() to evaluate it - setting
- md->match_function_type to MATCH_CONDASSERT causes it to stop at the end of
- an assertion. */
+ /* The condition is an assertion. Call match() to evaluate it - setting
+ md->match_function_type to MATCH_CONDASSERT causes it to stop at the end
+ of an assertion. */
- else
- {
+ default:
md->match_function_type = MATCH_CONDASSERT;
- RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, NULL, RM3);
+ RMATCH(eptr, ecode, offset_top, md, NULL, RM3);
if (rrc == MATCH_MATCH)
{
if (md->end_offset_top > offset_top)
offset_top = md->end_offset_top; /* Captures may have happened */
condition = TRUE;
- ecode += 1 + LINK_SIZE + GET(ecode, LINK_SIZE + 2);
+
+ /* Advance ecode past the assertion to the start of the first branch,
+ but adjust it so that the general choosing code below works. */
+
+ ecode += GET(ecode, 1);
while (*ecode == OP_ALT) ecode += GET(ecode, 1);
+ ecode += 1 + LINK_SIZE - PRIV(OP_lengths)[condcode];
}
/* PCRE doesn't allow the effect of (*THEN) to escape beyond an
- assertion; it is therefore treated as NOMATCH. */
+ assertion; it is therefore treated as NOMATCH. Any other return is an
+ error. */
else if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN)
{
RRETURN(rrc); /* Need braces because of following else */
}
- else
- {
- condition = FALSE;
- ecode += codelink;
- }
+ break;
}
- /* We are now at the branch that is to be obeyed. As there is only one, can
- use tail recursion to avoid using another stack frame, except when there is
- unlimited repeat of a possibly empty group. In the latter case, a recursive
- call to match() is always required, unless the second alternative doesn't
- exist, in which case we can just plough on. Note that, for compatibility
- with Perl, the | in a conditional group is NOT treated as creating two
- alternatives. If a THEN is encountered in the branch, it propagates out to
- the enclosing alternative (unless nested in a deeper set of alternatives,
- of course). */
-
- if (condition || *ecode == OP_ALT)
+ /* Choose branch according to the condition */
+
+ ecode += condition? PRIV(OP_lengths)[condcode] : codelink;
+
+ /* We are now at the branch that is to be obeyed. As there is only one, we
+ can use tail recursion to avoid using another stack frame, except when
+ there is unlimited repeat of a possibly empty group. In the latter case, a
+ recursive call to match() is always required, unless the second alternative
+ doesn't exist, in which case we can just plough on. Note that, for
+ compatibility with Perl, the | in a conditional group is NOT treated as
+ creating two alternatives. If a THEN is encountered in the branch, it
+ propagates out to the enclosing alternative (unless nested in a deeper set
+ of alternatives, of course). */
+
+ if (condition || ecode[-(1+LINK_SIZE)] == OP_ALT)
{
if (op != OP_SCOND)
{
- ecode += 1 + LINK_SIZE;
goto TAIL_RECURSE;
}
md->match_function_type = MATCH_CBEGROUP;
- RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, eptrb, RM49);
+ RMATCH(eptr, ecode, offset_top, md, eptrb, RM49);
RRETURN(rrc);
}
@@ -1504,7 +1442,6 @@ for (;;)
else
{
- ecode += 1 + LINK_SIZE;
}
break;
@@ -1513,7 +1450,7 @@ for (;;)
to close any currently open capturing brackets. */
case OP_CLOSE:
- number = GET2(ecode, 1);
+ number = GET2(ecode, 1); /* Must be less than 65536 */
offset = number << 1;
#ifdef PCRE_DEBUG
@@ -1521,8 +1458,8 @@ for (;;)
printf("\n");
#endif
- md->capture_last = number;
- if (offset >= md->offset_max) md->offset_overflow = TRUE; else
+ md->capture_last = (md->capture_last & OVFLMASK) | number;
+ if (offset >= md->offset_max) md->capture_last |= OVFLBIT; else
{
md->offset_vector[offset] =
md->offset_vector[md->offset_end - number];
@@ -1584,28 +1521,49 @@ for (;;)
}
else condassert = FALSE;
+ /* Loop for each branch */
+
do
{
RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, NULL, RM4);
+
+ /* A match means that the assertion is true; break out of the loop
+ that matches its alternatives. */
+
if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT)
{
mstart = md->start_match_ptr; /* In case \K reset it */
break;
}
+
+ /* If not matched, restore the previous mark setting. */
+
md->mark = save_mark;
- /* A COMMIT failure must fail the entire assertion, without trying any
- subsequent branches. */
+ /* See comment in the code for capturing groups above about handling
+ THEN. */
- if (rrc == MATCH_COMMIT) RRETURN(MATCH_NOMATCH);
+ if (rrc == MATCH_THEN)
+ {
+ next = ecode + GET(ecode,1);
+ if (md->start_match_ptr < next &&
+ (*ecode == OP_ALT || *next == OP_ALT))
+ rrc = MATCH_NOMATCH;
+ }
- /* PCRE does not allow THEN to escape beyond an assertion; it
- is treated as NOMATCH. */
+ /* Anything other than NOMATCH causes the entire assertion to fail,
+ passing back the return code. This includes COMMIT, SKIP, PRUNE and an
+ uncaptured THEN, which means they take their normal effect. This
+ consistent approach does not always have exactly the same effect as in
+ Perl. */
- if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
ecode += GET(ecode, 1);
}
- while (*ecode == OP_ALT);
+ while (*ecode == OP_ALT); /* Continue for next alternative */
+
+ /* If we have tried all the alternative branches, the assertion has
+ failed. If not, we broke out after a match. */
if (*ecode == OP_KET) RRETURN(MATCH_NOMATCH);
@@ -1613,17 +1571,16 @@ for (;;)
if (condassert) RRETURN(MATCH_MATCH);
- /* Continue from after the assertion, updating the offsets high water
- mark, since extracts may have been taken during the assertion. */
+ /* Continue from after a successful assertion, updating the offsets high
+ water mark, since extracts may have been taken during the assertion. */
do ecode += GET(ecode,1); while (*ecode == OP_ALT);
ecode += 1 + LINK_SIZE;
offset_top = md->end_offset_top;
continue;
- /* Negative assertion: all branches must fail to match. Encountering SKIP,
- PRUNE, or COMMIT means we must assume failure without checking subsequent
- branches. */
+ /* Negative assertion: all branches must fail to match for the assertion to
+ succeed. */
case OP_ASSERT_NOT:
case OP_ASSERTBACK_NOT:
@@ -1635,28 +1592,64 @@ for (;;)
}
else condassert = FALSE;
+ /* Loop for each alternative branch. */
+
do
{
RMATCH(eptr, ecode + 1 + LINK_SIZE, offset_top, md, NULL, RM5);
- md->mark = save_mark;
- if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT) RRETURN(MATCH_NOMATCH);
- if (rrc == MATCH_SKIP || rrc == MATCH_PRUNE || rrc == MATCH_COMMIT)
+ md->mark = save_mark; /* Always restore the mark setting */
+
+ switch(rrc)
{
- do ecode += GET(ecode,1); while (*ecode == OP_ALT);
+ case MATCH_MATCH: /* A successful match means */
+ case MATCH_ACCEPT: /* the assertion has failed. */
+ RRETURN(MATCH_NOMATCH);
+
+ case MATCH_NOMATCH: /* Carry on with next branch */
break;
+
+ /* See comment in the code for capturing groups above about handling
+ THEN. */
+
+ case MATCH_THEN:
+ next = ecode + GET(ecode,1);
+ if (md->start_match_ptr < next &&
+ (*ecode == OP_ALT || *next == OP_ALT))
+ {
+ rrc = MATCH_NOMATCH;
+ break;
+ }
+ /* Otherwise fall through. */
+
+ /* COMMIT, SKIP, PRUNE, and an uncaptured THEN cause the whole
+ assertion to fail to match, without considering any more alternatives.
+ Failing to match means the assertion is true. This is a consistent
+ approach, but does not always have the same effect as in Perl. */
+
+ case MATCH_COMMIT:
+ case MATCH_SKIP:
+ case MATCH_SKIP_ARG:
+ case MATCH_PRUNE:
+ do ecode += GET(ecode,1); while (*ecode == OP_ALT);
+ goto NEG_ASSERT_TRUE; /* Break out of alternation loop */
+
+ /* Anything else is an error */
+
+ default:
+ RRETURN(rrc);
}
- /* PCRE does not allow THEN to escape beyond an assertion; it is treated
- as NOMATCH. */
+ /* Continue with next branch */
- if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN) RRETURN(rrc);
ecode += GET(ecode,1);
}
while (*ecode == OP_ALT);
- if (condassert) RRETURN(MATCH_MATCH); /* Condition assertion */
+ /* All branches in the assertion failed to match. */
- ecode += 1 + LINK_SIZE;
+ NEG_ASSERT_TRUE:
+ if (condassert) RRETURN(MATCH_MATCH); /* Condition assertion */
+ ecode += 1 + LINK_SIZE; /* Continue with current branch */
continue;
/* Move the subject pointer back. This occurs only at the start of
@@ -1716,7 +1709,9 @@ for (;;)
cb.pattern_position = GET(ecode, 2);
cb.next_item_length = GET(ecode, 2 + LINK_SIZE);
cb.capture_top = offset_top/2;
- cb.capture_last = md->capture_last;
+ cb.capture_last = md->capture_last & CAPLMASK;
+ /* Internal change requires this for API compatibility. */
+ if (cb.capture_last == 0) cb.capture_last = -1;
cb.callout_data = md->callout_data;
cb.mark = md->nomatch_mark;
if ((rrc = (*PUBL(callout))(&cb)) > 0) RRETURN(MATCH_NOMATCH);
@@ -1762,6 +1757,7 @@ for (;;)
/* Add to "recursing stack" */
new_recursive.group_num = recno;
+ new_recursive.saved_capture_last = md->capture_last;
new_recursive.subject_position = eptr;
new_recursive.prevrec = md->recursive;
md->recursive = &new_recursive;
@@ -1785,8 +1781,9 @@ for (;;)
new_recursive.saved_max * sizeof(int));
/* OK, now we can do the recursion. After processing each alternative,
- restore the offset data. If there were nested recursions, md->recursive
- might be changed, so reset it before looping. */
+ restore the offset data and the last captured value. If there were nested
+ recursions, md->recursive might be changed, so reset it before looping.
+ */
DPRINTF(("Recursing into group %d\n", new_recursive.group_num));
cbegroup = (*callpat >= OP_SBRA);
@@ -1797,6 +1794,7 @@ for (;;)
md, eptrb, RM6);
memcpy(md->offset_vector, new_recursive.offset_save,
new_recursive.saved_max * sizeof(int));
+ md->capture_last = new_recursive.saved_capture_last;
md->recursive = new_recursive.prevrec;
if (rrc == MATCH_MATCH || rrc == MATCH_ACCEPT)
{
@@ -1813,11 +1811,16 @@ for (;;)
goto RECURSION_MATCHED; /* Exit loop; end processing */
}
- /* PCRE does not allow THEN or COMMIT to escape beyond a recursion; it
- is treated as NOMATCH. */
+ /* PCRE does not allow THEN, SKIP, PRUNE or COMMIT to escape beyond a
+ recursion; they cause a NOMATCH for the entire recursion. These codes
+ are defined in a range that can be tested for. */
+
+ if (rrc >= MATCH_BACKTRACK_MIN && rrc <= MATCH_BACKTRACK_MAX)
+ RRETURN(MATCH_NOMATCH);
- else if (rrc != MATCH_NOMATCH && rrc != MATCH_THEN &&
- rrc != MATCH_COMMIT)
+ /* Any return code other than NOMATCH is an error. */
+
+ if (rrc != MATCH_NOMATCH)
{
DPRINTF(("Recursion gave error %d\n", rrc));
if (new_recursive.offset_save != stacksave)
@@ -1947,8 +1950,8 @@ for (;;)
/* Deal with capturing */
- md->capture_last = number;
- if (offset >= md->offset_max) md->offset_overflow = TRUE; else
+ md->capture_last = (md->capture_last & OVFLMASK) | number;
+ if (offset >= md->offset_max) md->capture_last |= OVFLBIT; else
{
/* If offset is greater than offset_top, it means that we are
"skipping" a capturing group, and that group's offsets must be marked
@@ -2004,6 +2007,7 @@ for (;;)
if (*ecode == OP_KETRPOS)
{
+ md->start_match_ptr = mstart; /* In case \K reset it */
md->end_match_ptr = eptr;
md->end_offset_top = offset_top;
RRETURN(MATCH_KETRPOS);
@@ -2571,19 +2575,24 @@ for (;;)
RRETURN(MATCH_NOMATCH);
break;
- case PT_SPACE: /* Perl space */
- if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_FF || c == CHAR_CR)
- == (op == OP_NOTPROP))
- RRETURN(MATCH_NOMATCH);
- break;
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included,
+ which means that Perl space and POSIX space are now identical. PCRE
+ was changed at release 8.34. */
+ case PT_SPACE: /* Perl space */
case PT_PXSPACE: /* POSIX space */
- if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_VT ||
- c == CHAR_FF || c == CHAR_CR)
- == (op == OP_NOTPROP))
- RRETURN(MATCH_NOMATCH);
+ switch(c)
+ {
+ HSPACE_CASES:
+ VSPACE_CASES:
+ if (op == OP_NOTPROP) RRETURN(MATCH_NOMATCH);
+ break;
+
+ default:
+ if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z) ==
+ (op == OP_NOTPROP)) RRETURN(MATCH_NOMATCH);
+ break;
+ }
break;
case PT_WORD:
@@ -2604,6 +2613,13 @@ for (;;)
}
break;
+ case PT_UCNC:
+ if ((c == CHAR_DOLLAR_SIGN || c == CHAR_COMMERCIAL_AT ||
+ c == CHAR_GRAVE_ACCENT || (c >= 0xa0 && c <= 0xd7ff) ||
+ c >= 0xe000) == (op == OP_NOTPROP))
+ RRETURN(MATCH_NOMATCH);
+ break;
+
/* This should never occur */
default:
@@ -2650,15 +2666,7 @@ for (;;)
similar code to character type repeats - written out again for speed.
However, if the referenced string is the empty string, always treat
it as matched, any number of times (otherwise there could be infinite
- loops). */
-
- case OP_REF:
- case OP_REFI:
- caseless = op == OP_REFI;
- offset = GET2(ecode, 1) << 1; /* Doubled ref number */
- ecode += 1 + IMM2_SIZE;
-
- /* If the reference is unset, there are two possibilities:
+ loops). If the reference is unset, there are two possibilities:
(a) In the default, Perl-compatible state, set the length negative;
this ensures that every attempt at a match fails. We can't just fail
@@ -2668,8 +2676,39 @@ for (;;)
so that the back reference matches an empty string.
Otherwise, set the length to the length of what was matched by the
- referenced subpattern. */
+ referenced subpattern.
+
+ The OP_REF and OP_REFI opcodes are used for a reference to a numbered group
+ or to a non-duplicated named group. For a duplicated named group, OP_DNREF
+ and OP_DNREFI are used. In this case we must scan the list of groups to
+ which the name refers, and use the first one that is set. */
+
+ case OP_DNREF:
+ case OP_DNREFI:
+ caseless = op == OP_DNREFI;
+ {
+ int count = GET2(ecode, 1+IMM2_SIZE);
+ pcre_uchar *slot = md->name_table + GET2(ecode, 1) * md->name_entry_size;
+ ecode += 1 + 2*IMM2_SIZE;
+
+ while (count-- > 0)
+ {
+ offset = GET2(slot, 0) << 1;
+ if (offset < offset_top && md->offset_vector[offset] >= 0) break;
+ slot += md->name_entry_size;
+ }
+ if (count < 0)
+ length = (md->jscript_compat)? 0 : -1;
+ else
+ length = md->offset_vector[offset+1] - md->offset_vector[offset];
+ }
+ goto REF_REPEAT;
+ case OP_REF:
+ case OP_REFI:
+ caseless = op == OP_REFI;
+ offset = GET2(ecode, 1) << 1; /* Doubled ref number */
+ ecode += 1 + IMM2_SIZE;
if (offset >= offset_top || md->offset_vector[offset] < 0)
length = (md->jscript_compat)? 0 : -1;
else
@@ -2677,6 +2716,7 @@ for (;;)
/* Set up for repetition, or handle the non-repeated case */
+ REF_REPEAT:
switch (*ecode)
{
case OP_CRSTAR:
@@ -2825,8 +2865,12 @@ for (;;)
case OP_CRMINPLUS:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSPLUS:
+ case OP_CRPOSQUERY:
c = *ecode++ - OP_CRSTAR;
- minimize = (c & 1) != 0;
+ if (c < OP_CRPOSSTAR - OP_CRSTAR) minimize = (c & 1) != 0;
+ else possessive = TRUE;
min = rep_min[c]; /* Pick up values from tables; */
max = rep_max[c]; /* zero for max => infinity */
if (max == 0) max = INT_MAX;
@@ -2834,7 +2878,9 @@ for (;;)
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
minimize = (*ecode == OP_CRMINRANGE);
+ possessive = (*ecode == OP_CRPOSRANGE);
min = GET2(ecode, 1);
max = GET2(ecode, 1 + IMM2_SIZE);
if (max == 0) max = INT_MAX;
@@ -2976,6 +3022,9 @@ for (;;)
if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) break;
eptr += len;
}
+
+ if (possessive) continue; /* No backtracking */
+
for (;;)
{
RMATCH(eptr, ecode, offset_top, md, eptrb, RM18);
@@ -3006,6 +3055,9 @@ for (;;)
if ((BYTE_MAP[c/8] & (1 << (c&7))) == 0) break;
eptr++;
}
+
+ if (possessive) continue; /* No backtracking */
+
while (eptr >= pp)
{
RMATCH(eptr, ecode, offset_top, md, eptrb, RM19);
@@ -3021,9 +3073,10 @@ for (;;)
/* Control never gets here */
- /* Match an extended character class. This opcode is encountered only
- when UTF-8 mode mode is supported. Nevertheless, we may not be in UTF-8
- mode, because Unicode properties are supported in non-UTF-8 mode. */
+ /* Match an extended character class. In the 8-bit library, this opcode is
+ encountered only when UTF-8 mode mode is supported. In the 16-bit and
+ 32-bit libraries, codepoints greater than 255 may be encountered even when
+ UTF is not supported. */
#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
case OP_XCLASS:
@@ -3039,8 +3092,12 @@ for (;;)
case OP_CRMINPLUS:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSPLUS:
+ case OP_CRPOSQUERY:
c = *ecode++ - OP_CRSTAR;
- minimize = (c & 1) != 0;
+ if (c < OP_CRPOSSTAR - OP_CRSTAR) minimize = (c & 1) != 0;
+ else possessive = TRUE;
min = rep_min[c]; /* Pick up values from tables; */
max = rep_max[c]; /* zero for max => infinity */
if (max == 0) max = INT_MAX;
@@ -3048,7 +3105,9 @@ for (;;)
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
minimize = (*ecode == OP_CRMINRANGE);
+ possessive = (*ecode == OP_CRPOSRANGE);
min = GET2(ecode, 1);
max = GET2(ecode, 1 + IMM2_SIZE);
if (max == 0) max = INT_MAX;
@@ -3120,6 +3179,9 @@ for (;;)
if (!PRIV(xclass)(c, data, utf)) break;
eptr += len;
}
+
+ if (possessive) continue; /* No backtracking */
+
for(;;)
{
RMATCH(eptr, ecode, offset_top, md, eptrb, RM21);
@@ -3190,7 +3252,7 @@ for (;;)
if (fc < 128)
{
- pcre_uchar cc = RAWUCHAR(eptr);
+ pcre_uint32 cc = RAWUCHAR(eptr);
if (md->lcc[fc] != TABLE_GET(cc, md->lcc, cc)) RRETURN(MATCH_NOMATCH);
ecode++;
eptr++;
@@ -3295,7 +3357,22 @@ for (;;)
max = rep_max[c]; /* zero for max => infinity */
if (max == 0) max = INT_MAX;
- /* Common code for all repeated single-character matches. */
+ /* Common code for all repeated single-character matches. We first check
+ for the minimum number of characters. If the minimum equals the maximum, we
+ are done. Otherwise, if minimizing, check the rest of the pattern for a
+ match; if there isn't one, advance up to the maximum, one character at a
+ time.
+
+ If maximizing, advance up to the maximum number of matching characters,
+ until eptr is past the end of the maximum run. If possessive, we are
+ then done (no backing up). Otherwise, match at this position; anything
+ other than no match is immediately returned. For nomatch, back up one
+ character, unless we are matching \R and the last thing matched was
+ \r\n, in which case, back up two bytes. When we reach the first optional
+ character position, we can save stack by doing a tail recurse.
+
+ The various UTF/non-UTF and caseful/caseless cases are handled separately,
+ for speed. */
REPEATCHAR:
#ifdef SUPPORT_UTF
@@ -3379,13 +3456,12 @@ for (;;)
}
}
- if (possessive) continue;
-
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM23);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr == pp) { RRETURN(MATCH_NOMATCH); }
#ifdef SUPPORT_UCP
eptr--;
BACKCHAR(eptr);
@@ -3439,8 +3515,7 @@ for (;;)
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc; /* Faster than pcre_uchar */
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -3455,8 +3530,7 @@ for (;;)
{
for (fi = min;; fi++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc; /* Faster than pcre_uchar */
RMATCH(eptr, ecode, offset_top, md, eptrb, RM24);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
if (fi >= max) RRETURN(MATCH_NOMATCH);
@@ -3476,8 +3550,7 @@ for (;;)
pp = eptr;
for (i = min; i < max; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc; /* Faster than pcre_uchar */
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -3487,18 +3560,16 @@ for (;;)
if (fc != cc && foc != cc) break;
eptr++;
}
-
- if (possessive) continue;
-
- while (eptr >= pp)
+ if (possessive) continue; /* No backtracking */
+ for (;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM25);
eptr--;
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
}
- RRETURN(MATCH_NOMATCH);
+ /* Control never gets here */
}
- /* Control never gets here */
}
/* Caseful comparisons (includes all multi-byte characters) */
@@ -3546,15 +3617,15 @@ for (;;)
if (fc != RAWUCHARTEST(eptr)) break;
eptr++;
}
- if (possessive) continue;
-
- while (eptr >= pp)
+ if (possessive) continue; /* No backtracking */
+ for (;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM27);
eptr--;
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
}
- RRETURN(MATCH_NOMATCH);
+ /* Control never gets here */
}
}
/* Control never gets here */
@@ -3726,7 +3797,7 @@ for (;;)
}
}
else
-#endif
+#endif /* SUPPORT_UTF */
/* Not UTF mode */
{
for (i = 1; i <= min; i++)
@@ -3764,7 +3835,7 @@ for (;;)
}
}
else
-#endif
+#endif /*SUPPORT_UTF */
/* Not UTF mode */
{
for (fi = min;; fi++)
@@ -3806,17 +3877,18 @@ for (;;)
if (fc == d || (unsigned int)foc == d) break;
eptr += len;
}
- if (possessive) continue;
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM30);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr-- == pp) break; /* Stop if tried at original pos */
+ eptr--;
BACKCHAR(eptr);
}
}
else
-#endif
+#endif /* SUPPORT_UTF */
/* Not UTF mode */
{
for (i = min; i < max; i++)
@@ -3829,18 +3901,17 @@ for (;;)
if (fc == *eptr || foc == *eptr) break;
eptr++;
}
- if (possessive) continue;
- while (eptr >= pp)
+ if (possessive) continue; /* No backtracking */
+ for (;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM31);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
eptr--;
}
}
-
- RRETURN(MATCH_NOMATCH);
+ /* Control never gets here */
}
- /* Control never gets here */
}
/* Caseful comparisons */
@@ -3941,12 +4012,13 @@ for (;;)
if (fc == d) break;
eptr += len;
}
- if (possessive) continue;
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM34);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr-- == pp) break; /* Stop if tried at original pos */
+ eptr--;
BACKCHAR(eptr);
}
}
@@ -3964,16 +4036,16 @@ for (;;)
if (fc == *eptr) break;
eptr++;
}
- if (possessive) continue;
- while (eptr >= pp)
+ if (possessive) continue; /* No backtracking */
+ for (;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM35);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
eptr--;
}
}
-
- RRETURN(MATCH_NOMATCH);
+ /* Control never gets here */
}
}
/* Control never gets here */
@@ -4155,7 +4227,12 @@ for (;;)
}
break;
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included,
+ which means that Perl space and POSIX space are now identical. PCRE
+ was changed at release 8.34. */
+
case PT_SPACE: /* Perl space */
+ case PT_PXSPACE: /* POSIX space */
for (i = 1; i <= min; i++)
{
if (eptr >= md->end_subject)
@@ -4164,26 +4241,18 @@ for (;;)
RRETURN(MATCH_NOMATCH);
}
GETCHARINCTEST(c, eptr);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
- RRETURN(MATCH_NOMATCH);
- }
- break;
-
- case PT_PXSPACE: /* POSIX space */
- for (i = 1; i <= min; i++)
- {
- if (eptr >= md->end_subject)
+ switch(c)
{
- SCHECK_PARTIAL();
- RRETURN(MATCH_NOMATCH);
+ HSPACE_CASES:
+ VSPACE_CASES:
+ if (prop_fail_result) RRETURN(MATCH_NOMATCH);
+ break;
+
+ default:
+ if ((UCD_CATEGORY(c) == ucp_Z) == prop_fail_result)
+ RRETURN(MATCH_NOMATCH);
+ break;
}
- GETCHARINCTEST(c, eptr);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
- RRETURN(MATCH_NOMATCH);
}
break;
@@ -4225,6 +4294,22 @@ for (;;)
}
break;
+ case PT_UCNC:
+ for (i = 1; i <= min; i++)
+ {
+ if (eptr >= md->end_subject)
+ {
+ SCHECK_PARTIAL();
+ RRETURN(MATCH_NOMATCH);
+ }
+ GETCHARINCTEST(c, eptr);
+ if ((c == CHAR_DOLLAR_SIGN || c == CHAR_COMMERCIAL_AT ||
+ c == CHAR_GRAVE_ACCENT || (c >= 0xa0 && c <= 0xd7ff) ||
+ c >= 0xe000) == prop_fail_result)
+ RRETURN(MATCH_NOMATCH);
+ }
+ break;
+
/* This should not occur */
default:
@@ -4430,8 +4515,7 @@ for (;;)
case OP_DIGIT:
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc;
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -4448,8 +4532,7 @@ for (;;)
case OP_NOT_WHITESPACE:
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc;
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -4466,8 +4549,7 @@ for (;;)
case OP_WHITESPACE:
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc;
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -4484,8 +4566,7 @@ for (;;)
case OP_NOT_WORDCHAR:
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc;
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -4502,8 +4583,7 @@ for (;;)
case OP_WORDCHAR:
for (i = 1; i <= min; i++)
{
- pcre_uchar cc;
-
+ pcre_uint32 cc;
if (eptr >= md->end_subject)
{
SCHECK_PARTIAL();
@@ -4892,25 +4972,11 @@ for (;;)
}
/* Control never gets here */
- case PT_SPACE: /* Perl space */
- for (fi = min;; fi++)
- {
- RMATCH(eptr, ecode, offset_top, md, eptrb, RM60);
- if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (fi >= max) RRETURN(MATCH_NOMATCH);
- if (eptr >= md->end_subject)
- {
- SCHECK_PARTIAL();
- RRETURN(MATCH_NOMATCH);
- }
- GETCHARINCTEST(c, eptr);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
- RRETURN(MATCH_NOMATCH);
- }
- /* Control never gets here */
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included,
+ which means that Perl space and POSIX space are now identical. PCRE
+ was changed at release 8.34. */
+ case PT_SPACE: /* Perl space */
case PT_PXSPACE: /* POSIX space */
for (fi = min;; fi++)
{
@@ -4923,10 +4989,18 @@ for (;;)
RRETURN(MATCH_NOMATCH);
}
GETCHARINCTEST(c, eptr);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
- RRETURN(MATCH_NOMATCH);
+ switch(c)
+ {
+ HSPACE_CASES:
+ VSPACE_CASES:
+ if (prop_fail_result) RRETURN(MATCH_NOMATCH);
+ break;
+
+ default:
+ if ((UCD_CATEGORY(c) == ucp_Z) == prop_fail_result)
+ RRETURN(MATCH_NOMATCH);
+ break;
+ }
}
/* Control never gets here */
@@ -4976,6 +5050,25 @@ for (;;)
}
/* Control never gets here */
+ case PT_UCNC:
+ for (fi = min;; fi++)
+ {
+ RMATCH(eptr, ecode, offset_top, md, eptrb, RM60);
+ if (rrc != MATCH_NOMATCH) RRETURN(rrc);
+ if (fi >= max) RRETURN(MATCH_NOMATCH);
+ if (eptr >= md->end_subject)
+ {
+ SCHECK_PARTIAL();
+ RRETURN(MATCH_NOMATCH);
+ }
+ GETCHARINCTEST(c, eptr);
+ if ((c == CHAR_DOLLAR_SIGN || c == CHAR_COMMERCIAL_AT ||
+ c == CHAR_GRAVE_ACCENT || (c >= 0xa0 && c <= 0xd7ff) ||
+ c >= 0xe000) == prop_fail_result)
+ RRETURN(MATCH_NOMATCH);
+ }
+ /* Control never gets here */
+
/* This should never occur */
default:
RRETURN(PCRE_ERROR_INTERNAL);
@@ -5391,7 +5484,12 @@ for (;;)
}
break;
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included,
+ which means that Perl space and POSIX space are now identical. PCRE
+ was changed at release 8.34. */
+
case PT_SPACE: /* Perl space */
+ case PT_PXSPACE: /* POSIX space */
for (i = min; i < max; i++)
{
int len = 1;
@@ -5401,30 +5499,21 @@ for (;;)
break;
}
GETCHARLENTEST(c, eptr, len);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
+ switch(c)
+ {
+ HSPACE_CASES:
+ VSPACE_CASES:
+ if (prop_fail_result) goto ENDLOOP99; /* Break the loop */
break;
- eptr+= len;
- }
- break;
- case PT_PXSPACE: /* POSIX space */
- for (i = min; i < max; i++)
- {
- int len = 1;
- if (eptr >= md->end_subject)
- {
- SCHECK_PARTIAL();
+ default:
+ if ((UCD_CATEGORY(c) == ucp_Z) == prop_fail_result)
+ goto ENDLOOP99; /* Break the loop */
break;
}
- GETCHARLENTEST(c, eptr, len);
- if ((UCD_CATEGORY(c) == ucp_Z || c == CHAR_HT || c == CHAR_NL ||
- c == CHAR_VT || c == CHAR_FF || c == CHAR_CR)
- == prop_fail_result)
- break;
eptr+= len;
}
+ ENDLOOP99:
break;
case PT_WORD:
@@ -5470,23 +5559,42 @@ for (;;)
GOT_MAX:
break;
+ case PT_UCNC:
+ for (i = min; i < max; i++)
+ {
+ int len = 1;
+ if (eptr >= md->end_subject)
+ {
+ SCHECK_PARTIAL();
+ break;
+ }
+ GETCHARLENTEST(c, eptr, len);
+ if ((c == CHAR_DOLLAR_SIGN || c == CHAR_COMMERCIAL_AT ||
+ c == CHAR_GRAVE_ACCENT || (c >= 0xa0 && c <= 0xd7ff) ||
+ c >= 0xe000) == prop_fail_result)
+ break;
+ eptr += len;
+ }
+ break;
+
default:
RRETURN(PCRE_ERROR_INTERNAL);
}
/* eptr is now past the end of the maximum run */
- if (possessive) continue;
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM44);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr-- == pp) break; /* Stop if tried at original pos */
+ eptr--;
if (utf) BACKCHAR(eptr);
}
}
- /* Match extended Unicode sequences. We will get here only if the
+ /* Match extended Unicode grapheme clusters. We will get here only if the
support is in the binary; otherwise a compile-time error occurs. */
else if (ctype == OP_EXTUNI)
@@ -5518,22 +5626,42 @@ for (;;)
/* eptr is now past the end of the maximum run */
- if (possessive) continue;
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ int lgb, rgb;
+ PCRE_PUCHAR fptr;
+
+ if (eptr == pp) goto TAIL_RECURSE; /* At start of char run */
RMATCH(eptr, ecode, offset_top, md, eptrb, RM45);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr-- == pp) break; /* Stop if tried at original pos */
- for (;;) /* Move back over one extended */
+
+ /* Backtracking over an extended grapheme cluster involves inspecting
+ the previous two characters (if present) to see if a break is
+ permitted between them. */
+
+ eptr--;
+ if (!utf) c = *eptr; else
+ {
+ BACKCHAR(eptr);
+ GETCHAR(c, eptr);
+ }
+ rgb = UCD_GRAPHBREAK(c);
+
+ for (;;)
{
- if (!utf) c = *eptr; else
+ if (eptr == pp) goto TAIL_RECURSE; /* At start of char run */
+ fptr = eptr - 1;
+ if (!utf) c = *fptr; else
{
- BACKCHAR(eptr);
- GETCHAR(c, eptr);
+ BACKCHAR(fptr);
+ GETCHAR(c, fptr);
}
- if (UCD_CATEGORY(c) != ucp_M) break;
- eptr--;
+ lgb = UCD_GRAPHBREAK(c);
+ if ((PRIV(ucp_gbtable)[lgb] & (1 << rgb)) == 0) break;
+ eptr = fptr;
+ rgb = lgb;
}
}
}
@@ -5799,18 +5927,13 @@ for (;;)
RRETURN(PCRE_ERROR_INTERNAL);
}
- /* eptr is now past the end of the maximum run. If possessive, we are
- done (no backing up). Otherwise, match at this position; anything other
- than no match is immediately returned. For nomatch, back up one
- character, unless we are matching \R and the last thing matched was
- \r\n, in which case, back up two bytes. */
-
- if (possessive) continue;
+ if (possessive) continue; /* No backtracking */
for(;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM46);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
- if (eptr-- == pp) break; /* Stop if tried at original pos */
+ eptr--;
BACKCHAR(eptr);
if (ctype == OP_ANYNL && eptr > pp && RAWUCHAR(eptr) == CHAR_NL &&
RAWUCHAR(eptr - 1) == CHAR_CR) eptr--;
@@ -6048,15 +6171,10 @@ for (;;)
RRETURN(PCRE_ERROR_INTERNAL);
}
- /* eptr is now past the end of the maximum run. If possessive, we are
- done (no backing up). Otherwise, match at this position; anything other
- than no match is immediately returned. For nomatch, back up one
- character (byte), unless we are matching \R and the last thing matched
- was \r\n, in which case, back up two bytes. */
-
- if (possessive) continue;
- while (eptr >= pp)
+ if (possessive) continue; /* No backtracking */
+ for (;;)
{
+ if (eptr == pp) goto TAIL_RECURSE;
RMATCH(eptr, ecode, offset_top, md, eptrb, RM47);
if (rrc != MATCH_NOMATCH) RRETURN(rrc);
eptr--;
@@ -6065,11 +6183,8 @@ for (;;)
}
}
- /* Get here if we can't make it match with any permitted repetitions */
-
- RRETURN(MATCH_NOMATCH);
+ /* Control never gets here */
}
- /* Control never gets here */
/* There's been some horrible disaster. Arrival here can only mean there is
something seriously wrong in the code above or the OP_xxx definitions. */
@@ -6103,10 +6218,10 @@ switch (frame->Xwhere)
LBL(53) LBL(54) LBL(55) LBL(56) LBL(57) LBL(58) LBL(63) LBL(64)
LBL(65) LBL(66)
#if defined SUPPORT_UTF || !defined COMPILE_PCRE8
- LBL(21)
+ LBL(20) LBL(21)
#endif
#ifdef SUPPORT_UTF
- LBL(16) LBL(18) LBL(20)
+ LBL(16) LBL(18)
LBL(22) LBL(23) LBL(28) LBL(30)
LBL(32) LBL(34) LBL(42) LBL(46)
#ifdef SUPPORT_UCP
@@ -6264,6 +6379,7 @@ const pcre_uint8 *start_bits = NULL;
PCRE_PUCHAR start_match = (PCRE_PUCHAR)subject + start_offset;
PCRE_PUCHAR end_subject;
PCRE_PUCHAR start_partial = NULL;
+PCRE_PUCHAR match_partial = NULL;
PCRE_PUCHAR req_char_ptr = start_match - 1;
const pcre_study_data *study;
@@ -6393,6 +6509,8 @@ md->callout_data = NULL;
tables = re->tables;
+/* The two limit values override the defaults, whatever their value. */
+
if (extra_data != NULL)
{
register unsigned int flags = extra_data->flags;
@@ -6407,6 +6525,15 @@ if (extra_data != NULL)
if ((flags & PCRE_EXTRA_TABLES) != 0) tables = extra_data->tables;
}
+/* Limits in the regex override only if they are smaller. */
+
+if ((re->flags & PCRE_MLSET) != 0 && re->limit_match < md->match_limit)
+ md->match_limit = re->limit_match;
+
+if ((re->flags & PCRE_RLSET) != 0 &&
+ re->limit_recursion < md->match_limit_recursion)
+ md->match_limit_recursion = re->limit_recursion;
+
/* If the exec call supplied NULL for tables, use the inbuilt ones. This
is a feature that makes it possible to save compiled regex and re-use them
in other programs later. */
@@ -6432,7 +6559,7 @@ end_subject = md->end_subject;
md->endonly = (re->options & PCRE_DOLLAR_ENDONLY) != 0;
md->use_ucp = (re->options & PCRE_UCP) != 0;
md->jscript_compat = (re->options & PCRE_JAVASCRIPT_COMPAT) != 0;
-md->ignore_skip_arg = FALSE;
+md->ignore_skip_arg = 0;
/* Some options are unpacked into BOOL variables in the hope that testing
them will be faster than individual option bits. */
@@ -6542,11 +6669,9 @@ if (re->top_backref > 0 && re->top_backref >= ocount/3)
DPRINTF(("Got memory to hold back references\n"));
}
else md->offset_vector = offsets;
-
md->offset_end = ocount;
md->offset_max = (2*ocount)/3;
-md->offset_overflow = FALSE;
-md->capture_last = -1;
+md->capture_last = 0;
/* Reset the working variable associated with each extraction. These should
never be used unless previously set, but they get saved and restored, and so we
@@ -6816,8 +6941,13 @@ for(;;)
md->match_call_count = 0;
md->match_function_type = 0;
md->end_offset_top = 0;
+ md->skip_arg_count = 0;
rc = match(start_match, md->start_code, start_match, 2, md, NULL, 0);
- if (md->hitend && start_partial == NULL) start_partial = md->start_used_ptr;
+ if (md->hitend && start_partial == NULL)
+ {
+ start_partial = md->start_used_ptr;
+ match_partial = start_match;
+ }
switch(rc)
{
@@ -6830,14 +6960,14 @@ for(;;)
case MATCH_SKIP_ARG:
new_start_match = start_match;
- md->ignore_skip_arg = TRUE;
+ md->ignore_skip_arg = md->skip_arg_count;
break;
- /* SKIP passes back the next starting point explicitly, but if it is the
- same as the match we have just done, treat it as NOMATCH. */
+ /* SKIP passes back the next starting point explicitly, but if it is no
+ greater than the match we have just done, treat it as NOMATCH. */
case MATCH_SKIP:
- if (md->start_match_ptr != start_match)
+ if (md->start_match_ptr > start_match)
{
new_start_match = md->start_match_ptr;
break;
@@ -6845,12 +6975,12 @@ for(;;)
/* Fall through */
/* NOMATCH and PRUNE advance by one character. THEN at this level acts
- exactly like PRUNE. Unset the ignore SKIP-with-argument flag. */
+ exactly like PRUNE. Unset ignore SKIP-with-argument. */
case MATCH_NOMATCH:
case MATCH_PRUNE:
case MATCH_THEN:
- md->ignore_skip_arg = FALSE;
+ md->ignore_skip_arg = 0;
new_start_match = start_match + 1;
#ifdef SUPPORT_UTF
if (utf)
@@ -6943,7 +7073,7 @@ if (rc == MATCH_MATCH || rc == MATCH_ACCEPT)
(arg_offset_max - 2) * sizeof(int));
DPRINTF(("Copied offsets from temporary memory\n"));
}
- if (md->end_offset_top > arg_offset_max) md->offset_overflow = TRUE;
+ if (md->end_offset_top > arg_offset_max) md->capture_last |= OVFLBIT;
DPRINTF(("Freeing temporary memory\n"));
(PUBL(free))(md->offset_vector);
}
@@ -6951,7 +7081,8 @@ if (rc == MATCH_MATCH || rc == MATCH_ACCEPT)
/* Set the return code to the number of captured strings, or 0 if there were
too many to fit into the vector. */
- rc = (md->offset_overflow && md->end_offset_top >= arg_offset_max)?
+ rc = ((md->capture_last & OVFLBIT) != 0 &&
+ md->end_offset_top >= arg_offset_max)?
0 : md->end_offset_top/2;
/* If there is space in the offset vector, set any unused pairs at the end of
@@ -7016,7 +7147,7 @@ if (rc != MATCH_NOMATCH && rc != PCRE_ERROR_PARTIAL)
/* Handle partial matches - disable any mark data */
-if (start_partial != NULL)
+if (match_partial != NULL)
{
DPRINTF((">>>> returning PCRE_ERROR_PARTIAL\n"));
md->mark = NULL;
@@ -7024,6 +7155,8 @@ if (start_partial != NULL)
{
offsets[0] = (int)(start_partial - (PCRE_PUCHAR)subject);
offsets[1] = (int)(end_subject - (PCRE_PUCHAR)subject);
+ if (offsetcount > 2)
+ offsets[2] = (int)(match_partial - (PCRE_PUCHAR)subject);
}
rc = PCRE_ERROR_PARTIAL;
}
diff --git a/ext/pcre/pcrelib/pcre_fullinfo.c b/ext/pcre/pcrelib/pcre_fullinfo.c
index 02c9df4a82..a6c2ece6ca 100644
--- a/ext/pcre/pcrelib/pcre_fullinfo.c
+++ b/ext/pcre/pcrelib/pcre_fullinfo.c
@@ -6,7 +6,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -222,6 +222,20 @@ switch (what)
*((int *)where) = re->max_lookbehind;
break;
+ case PCRE_INFO_MATCHLIMIT:
+ if ((re->flags & PCRE_MLSET) == 0) return PCRE_ERROR_UNSET;
+ *((pcre_uint32 *)where) = re->limit_match;
+ break;
+
+ case PCRE_INFO_RECURSIONLIMIT:
+ if ((re->flags & PCRE_RLSET) == 0) return PCRE_ERROR_UNSET;
+ *((pcre_uint32 *)where) = re->limit_recursion;
+ break;
+
+ case PCRE_INFO_MATCH_EMPTY:
+ *((int *)where) = (re->flags & PCRE_MATCH_EMPTY) != 0;
+ break;
+
default: return PCRE_ERROR_BADOPTION;
}
diff --git a/ext/pcre/pcrelib/pcre_internal.h b/ext/pcre/pcrelib/pcre_internal.h
index 43f5364556..0b9798c554 100644
--- a/ext/pcre/pcrelib/pcre_internal.h
+++ b/ext/pcre/pcrelib/pcre_internal.h
@@ -7,7 +7,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -194,23 +194,31 @@ preprocessor time in standard C environments. */
typedef unsigned char pcre_uint8;
#if USHRT_MAX == 65535
- typedef unsigned short pcre_uint16;
- typedef short pcre_int16;
+typedef unsigned short pcre_uint16;
+typedef short pcre_int16;
+#define PCRE_UINT16_MAX USHRT_MAX
+#define PCRE_INT16_MAX SHRT_MAX
#elif UINT_MAX == 65535
- typedef unsigned int pcre_uint16;
- typedef int pcre_int16;
+typedef unsigned int pcre_uint16;
+typedef int pcre_int16;
+#define PCRE_UINT16_MAX UINT_MAX
+#define PCRE_INT16_MAX INT_MAX
#else
-# error Cannot determine a type for 16-bit unsigned integers
+#error Cannot determine a type for 16-bit integers
#endif
-#if UINT_MAX == 4294967295
- typedef unsigned int pcre_uint32;
- typedef int pcre_int32;
-#elif ULONG_MAX == 4294967295
- typedef unsigned long int pcre_uint32;
- typedef long int pcre_int32;
+#if UINT_MAX == 4294967295U
+typedef unsigned int pcre_uint32;
+typedef int pcre_int32;
+#define PCRE_UINT32_MAX UINT_MAX
+#define PCRE_INT32_MAX INT_MAX
+#elif ULONG_MAX == 4294967295UL
+typedef unsigned long int pcre_uint32;
+typedef long int pcre_int32;
+#define PCRE_UINT32_MAX ULONG_MAX
+#define PCRE_INT32_MAX LONG_MAX
#else
-# error Cannot determine a type for 32-bit unsigned integers
+#error Cannot determine a type for 32-bit integers
#endif
/* When checking for integer overflow in pcre_compile(), we need to handle
@@ -221,11 +229,9 @@ stdint.h is available, include it; it may define INT64_MAX. Systems that do not
have stdint.h (e.g. Solaris) may have inttypes.h. The macro int64_t may be set
by "configure". */
-#ifdef PHP_WIN32
-#include "win32/php_stdint.h"
-#elif HAVE_STDINT_H
+#if defined HAVE_STDINT_H
#include <stdint.h>
-#elif HAVE_INTTYPES_H
+#elif defined HAVE_INTTYPES_H
#include <inttypes.h>
#endif
@@ -1123,23 +1129,27 @@ other. NOTE: The values also appear in pcre_jit_compile.c. */
/* Private flags containing information about the compiled regex. They used to
-live at the top end of the options word, but that got almost full, so now they
-are in a 16-bit flags word. From release 8.00, PCRE_NOPARTIAL is unused, as
-the restrictions on partial matching have been lifted. It remains for backwards
+live at the top end of the options word, but that got almost full, so they were
+moved to a 16-bit flags word - which got almost full, so now they are in a
+32-bit flags word. From release 8.00, PCRE_NOPARTIAL is unused, as the
+restrictions on partial matching have been lifted. It remains for backwards
compatibility. */
-#define PCRE_MODE8 0x0001 /* compiled in 8 bit mode */
-#define PCRE_MODE16 0x0002 /* compiled in 16 bit mode */
-#define PCRE_MODE32 0x0004 /* compiled in 32 bit mode */
-#define PCRE_FIRSTSET 0x0010 /* first_char is set */
-#define PCRE_FCH_CASELESS 0x0020 /* caseless first char */
-#define PCRE_REQCHSET 0x0040 /* req_byte is set */
-#define PCRE_RCH_CASELESS 0x0080 /* caseless requested char */
-#define PCRE_STARTLINE 0x0100 /* start after \n for multiline */
-#define PCRE_NOPARTIAL 0x0200 /* can't use partial with this regex */
-#define PCRE_JCHANGED 0x0400 /* j option used in regex */
-#define PCRE_HASCRORLF 0x0800 /* explicit \r or \n in pattern */
-#define PCRE_HASTHEN 0x1000 /* pattern contains (*THEN) */
+#define PCRE_MODE8 0x00000001 /* compiled in 8 bit mode */
+#define PCRE_MODE16 0x00000002 /* compiled in 16 bit mode */
+#define PCRE_MODE32 0x00000004 /* compiled in 32 bit mode */
+#define PCRE_FIRSTSET 0x00000010 /* first_char is set */
+#define PCRE_FCH_CASELESS 0x00000020 /* caseless first char */
+#define PCRE_REQCHSET 0x00000040 /* req_byte is set */
+#define PCRE_RCH_CASELESS 0x00000080 /* caseless requested char */
+#define PCRE_STARTLINE 0x00000100 /* start after \n for multiline */
+#define PCRE_NOPARTIAL 0x00000200 /* can't use partial with this regex */
+#define PCRE_JCHANGED 0x00000400 /* j option used in regex */
+#define PCRE_HASCRORLF 0x00000800 /* explicit \r or \n in pattern */
+#define PCRE_HASTHEN 0x00001000 /* pattern contains (*THEN) */
+#define PCRE_MLSET 0x00002000 /* match limit set by regex */
+#define PCRE_RLSET 0x00004000 /* recursion limit set by regex */
+#define PCRE_MATCH_EMPTY 0x00008000 /* pattern can match empty string */
#if defined COMPILE_PCRE8
#define PCRE_MODE PCRE_MODE8
@@ -1164,9 +1174,10 @@ time, run time, or study time, respectively. */
#define PUBLIC_COMPILE_OPTIONS \
(PCRE_CASELESS|PCRE_EXTENDED|PCRE_ANCHORED|PCRE_MULTILINE| \
PCRE_DOTALL|PCRE_DOLLAR_ENDONLY|PCRE_EXTRA|PCRE_UNGREEDY|PCRE_UTF8| \
- PCRE_NO_AUTO_CAPTURE|PCRE_NO_UTF8_CHECK|PCRE_AUTO_CALLOUT|PCRE_FIRSTLINE| \
+ PCRE_NO_AUTO_CAPTURE|PCRE_NO_AUTO_POSSESS| \
+ PCRE_NO_UTF8_CHECK|PCRE_AUTO_CALLOUT|PCRE_FIRSTLINE| \
PCRE_DUPNAMES|PCRE_NEWLINE_BITS|PCRE_BSR_ANYCRLF|PCRE_BSR_UNICODE| \
- PCRE_JAVASCRIPT_COMPAT|PCRE_UCP|PCRE_NO_START_OPTIMIZE)
+ PCRE_JAVASCRIPT_COMPAT|PCRE_UCP|PCRE_NO_START_OPTIMIZE|PCRE_NEVER_UTF)
#define PUBLIC_EXEC_OPTIONS \
(PCRE_ANCHORED|PCRE_NOTBOL|PCRE_NOTEOL|PCRE_NOTEMPTY|PCRE_NOTEMPTY_ATSTART| \
@@ -1522,20 +1533,25 @@ a positive value. */
#define STRING_xdigit "xdigit"
#define STRING_DEFINE "DEFINE"
-
-#define STRING_CR_RIGHTPAR "CR)"
-#define STRING_LF_RIGHTPAR "LF)"
-#define STRING_CRLF_RIGHTPAR "CRLF)"
-#define STRING_ANY_RIGHTPAR "ANY)"
-#define STRING_ANYCRLF_RIGHTPAR "ANYCRLF)"
-#define STRING_BSR_ANYCRLF_RIGHTPAR "BSR_ANYCRLF)"
-#define STRING_BSR_UNICODE_RIGHTPAR "BSR_UNICODE)"
-#define STRING_UTF8_RIGHTPAR "UTF8)"
-#define STRING_UTF16_RIGHTPAR "UTF16)"
-#define STRING_UTF32_RIGHTPAR "UTF32)"
-#define STRING_UTF_RIGHTPAR "UTF)"
-#define STRING_UCP_RIGHTPAR "UCP)"
-#define STRING_NO_START_OPT_RIGHTPAR "NO_START_OPT)"
+#define STRING_WEIRD_STARTWORD "[:<:]]"
+#define STRING_WEIRD_ENDWORD "[:>:]]"
+
+#define STRING_CR_RIGHTPAR "CR)"
+#define STRING_LF_RIGHTPAR "LF)"
+#define STRING_CRLF_RIGHTPAR "CRLF)"
+#define STRING_ANY_RIGHTPAR "ANY)"
+#define STRING_ANYCRLF_RIGHTPAR "ANYCRLF)"
+#define STRING_BSR_ANYCRLF_RIGHTPAR "BSR_ANYCRLF)"
+#define STRING_BSR_UNICODE_RIGHTPAR "BSR_UNICODE)"
+#define STRING_UTF8_RIGHTPAR "UTF8)"
+#define STRING_UTF16_RIGHTPAR "UTF16)"
+#define STRING_UTF32_RIGHTPAR "UTF32)"
+#define STRING_UTF_RIGHTPAR "UTF)"
+#define STRING_UCP_RIGHTPAR "UCP)"
+#define STRING_NO_AUTO_POSSESS_RIGHTPAR "NO_AUTO_POSSESS)"
+#define STRING_NO_START_OPT_RIGHTPAR "NO_START_OPT)"
+#define STRING_LIMIT_MATCH_EQ "LIMIT_MATCH="
+#define STRING_LIMIT_RECURSION_EQ "LIMIT_RECURSION="
#else /* SUPPORT_UTF */
@@ -1783,20 +1799,25 @@ only. */
#define STRING_xdigit STR_x STR_d STR_i STR_g STR_i STR_t
#define STRING_DEFINE STR_D STR_E STR_F STR_I STR_N STR_E
-
-#define STRING_CR_RIGHTPAR STR_C STR_R STR_RIGHT_PARENTHESIS
-#define STRING_LF_RIGHTPAR STR_L STR_F STR_RIGHT_PARENTHESIS
-#define STRING_CRLF_RIGHTPAR STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
-#define STRING_ANY_RIGHTPAR STR_A STR_N STR_Y STR_RIGHT_PARENTHESIS
-#define STRING_ANYCRLF_RIGHTPAR STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
-#define STRING_BSR_ANYCRLF_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
-#define STRING_BSR_UNICODE_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_U STR_N STR_I STR_C STR_O STR_D STR_E STR_RIGHT_PARENTHESIS
-#define STRING_UTF8_RIGHTPAR STR_U STR_T STR_F STR_8 STR_RIGHT_PARENTHESIS
-#define STRING_UTF16_RIGHTPAR STR_U STR_T STR_F STR_1 STR_6 STR_RIGHT_PARENTHESIS
-#define STRING_UTF32_RIGHTPAR STR_U STR_T STR_F STR_3 STR_2 STR_RIGHT_PARENTHESIS
-#define STRING_UTF_RIGHTPAR STR_U STR_T STR_F STR_RIGHT_PARENTHESIS
-#define STRING_UCP_RIGHTPAR STR_U STR_C STR_P STR_RIGHT_PARENTHESIS
-#define STRING_NO_START_OPT_RIGHTPAR STR_N STR_O STR_UNDERSCORE STR_S STR_T STR_A STR_R STR_T STR_UNDERSCORE STR_O STR_P STR_T STR_RIGHT_PARENTHESIS
+#define STRING_WEIRD_STARTWORD STR_LEFT_SQUARE_BRACKET STR_COLON STR_LESS_THAN_SIGN STR_COLON STR_RIGHT_SQUARE_BRACKET STR_RIGHT_SQUARE_BRACKET
+#define STRING_WEIRD_ENDWORD STR_LEFT_SQUARE_BRACKET STR_COLON STR_GREATER_THAN_SIGN STR_COLON STR_RIGHT_SQUARE_BRACKET STR_RIGHT_SQUARE_BRACKET
+
+#define STRING_CR_RIGHTPAR STR_C STR_R STR_RIGHT_PARENTHESIS
+#define STRING_LF_RIGHTPAR STR_L STR_F STR_RIGHT_PARENTHESIS
+#define STRING_CRLF_RIGHTPAR STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
+#define STRING_ANY_RIGHTPAR STR_A STR_N STR_Y STR_RIGHT_PARENTHESIS
+#define STRING_ANYCRLF_RIGHTPAR STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
+#define STRING_BSR_ANYCRLF_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_A STR_N STR_Y STR_C STR_R STR_L STR_F STR_RIGHT_PARENTHESIS
+#define STRING_BSR_UNICODE_RIGHTPAR STR_B STR_S STR_R STR_UNDERSCORE STR_U STR_N STR_I STR_C STR_O STR_D STR_E STR_RIGHT_PARENTHESIS
+#define STRING_UTF8_RIGHTPAR STR_U STR_T STR_F STR_8 STR_RIGHT_PARENTHESIS
+#define STRING_UTF16_RIGHTPAR STR_U STR_T STR_F STR_1 STR_6 STR_RIGHT_PARENTHESIS
+#define STRING_UTF32_RIGHTPAR STR_U STR_T STR_F STR_3 STR_2 STR_RIGHT_PARENTHESIS
+#define STRING_UTF_RIGHTPAR STR_U STR_T STR_F STR_RIGHT_PARENTHESIS
+#define STRING_UCP_RIGHTPAR STR_U STR_C STR_P STR_RIGHT_PARENTHESIS
+#define STRING_NO_AUTO_POSSESS_RIGHTPAR STR_N STR_O STR_UNDERSCORE STR_A STR_U STR_T STR_O STR_UNDERSCORE STR_P STR_O STR_S STR_S STR_E STR_S STR_S STR_RIGHT_PARENTHESIS
+#define STRING_NO_START_OPT_RIGHTPAR STR_N STR_O STR_UNDERSCORE STR_S STR_T STR_A STR_R STR_T STR_UNDERSCORE STR_O STR_P STR_T STR_RIGHT_PARENTHESIS
+#define STRING_LIMIT_MATCH_EQ STR_L STR_I STR_M STR_I STR_T STR_UNDERSCORE STR_M STR_A STR_T STR_C STR_H STR_EQUALS_SIGN
+#define STRING_LIMIT_RECURSION_EQ STR_L STR_I STR_M STR_I STR_T STR_UNDERSCORE STR_R STR_E STR_C STR_U STR_R STR_S STR_I STR_O STR_N STR_EQUALS_SIGN
#endif /* SUPPORT_UTF */
@@ -1837,6 +1858,18 @@ only. */
#define PT_PXSPACE 7 /* POSIX space - Z plus 9,10,11,12,13 */
#define PT_WORD 8 /* Word - L plus N plus underscore */
#define PT_CLIST 9 /* Pseudo-property: match character list */
+#define PT_UCNC 10 /* Universal Character nameable character */
+#define PT_TABSIZE 11 /* Size of square table for autopossessify tests */
+
+/* The following special properties are used only in XCLASS items, when POSIX
+classes are specified and PCRE_UCP is set - in other words, for Unicode
+handling of these classes. They are not available via the \p or \P escapes like
+those in the above list, and so they do not take part in the autopossessifying
+table. */
+
+#define PT_PXGRAPH 11 /* [:graph:] - characters that mark the paper */
+#define PT_PXPRINT 12 /* [:print:] - [:graph:] plus non-control spaces */
+#define PT_PXPUNCT 13 /* [:punct:] - punctuation characters */
/* Flag bits and data types for the extended class (OP_XCLASS) for classes that
contain characters with values greater than 255. */
@@ -1851,9 +1884,9 @@ contain characters with values greater than 255. */
#define XCL_NOTPROP 4 /* Unicode inverted property (ditto) */
/* These are escaped items that aren't just an encoding of a particular data
-value such as \n. They must have non-zero values, as check_escape() returns
-0 for a data character. Also, they must appear in the same order as in the opcode
-definitions below, up to ESC_z. There's a dummy for OP_ALLANY because it
+value such as \n. They must have non-zero values, as check_escape() returns 0
+for a data character. Also, they must appear in the same order as in the
+opcode definitions below, up to ESC_z. There's a dummy for OP_ALLANY because it
corresponds to "." in DOTALL mode rather than an escape sequence. It is also
used for [^] in JavaScript compatibility mode, and for \C in non-utf mode. In
non-DOTALL mode, "." behaves like \N.
@@ -1876,12 +1909,31 @@ enum { ESC_A = 1, ESC_G, ESC_K, ESC_B, ESC_b, ESC_D, ESC_d, ESC_S, ESC_s,
ESC_E, ESC_Q, ESC_g, ESC_k,
ESC_DU, ESC_du, ESC_SU, ESC_su, ESC_WU, ESC_wu };
-/* Opcode table: Starting from 1 (i.e. after OP_END), the values up to
-OP_EOD must correspond in order to the list of escapes immediately above.
-*** NOTE NOTE NOTE *** Whenever this list is updated, the two macro definitions
-that follow must also be updated to match. There are also tables called
-"coptable" and "poptable" in pcre_dfa_exec.c that must be updated. */
+/********************** Opcode definitions ******************/
+
+/****** NOTE NOTE NOTE ******
+
+Starting from 1 (i.e. after OP_END), the values up to OP_EOD must correspond in
+order to the list of escapes immediately above. Furthermore, values up to
+OP_DOLLM must not be changed without adjusting the table called autoposstab in
+pcre_compile.c
+
+Whenever this list is updated, the two macro definitions that follow must be
+updated to match. The possessification table called "opcode_possessify" in
+pcre_compile.c must also be updated, and also the tables called "coptable"
+and "poptable" in pcre_dfa_exec.c.
+
+****** NOTE NOTE NOTE ******/
+
+
+/* The values between FIRST_AUTOTAB_OP and LAST_AUTOTAB_RIGHT_OP, inclusive,
+are used in a table for deciding whether a repeated character type can be
+auto-possessified. */
+
+#define FIRST_AUTOTAB_OP OP_NOT_DIGIT
+#define LAST_AUTOTAB_LEFT_OP OP_EXTUNI
+#define LAST_AUTOTAB_RIGHT_OP OP_DOLLM
enum {
OP_END, /* 0 End of pattern */
@@ -1914,10 +1966,15 @@ enum {
OP_EODN, /* 23 End of data or \n at end of data (\Z) */
OP_EOD, /* 24 End of data (\z) */
- OP_CIRC, /* 25 Start of line - not multiline */
- OP_CIRCM, /* 26 Start of line - multiline */
- OP_DOLL, /* 27 End of line - not multiline */
- OP_DOLLM, /* 28 End of line - multiline */
+ /* Line end assertions */
+
+ OP_DOLL, /* 25 End of line - not multiline */
+ OP_DOLLM, /* 26 End of line - multiline */
+ OP_CIRC, /* 27 Start of line - not multiline */
+ OP_CIRCM, /* 28 Start of line - multiline */
+
+ /* Single characters; caseful must precede the caseless ones */
+
OP_CHAR, /* 29 Match one character, casefully */
OP_CHARI, /* 30 Match one character, caselessly */
OP_NOT, /* 31 Match one character, not the given one, casefully */
@@ -1926,7 +1983,7 @@ enum {
/* The following sets of 13 opcodes must always be kept in step because
the offset from the first one is used to generate the others. */
- /**** Single characters, caseful, must precede the caseless ones ****/
+ /* Repeated characters; caseful must precede the caseless ones */
OP_STAR, /* 33 The maximizing and minimizing versions of */
OP_MINSTAR, /* 34 these six opcodes must come in pairs, with */
@@ -1944,7 +2001,7 @@ enum {
OP_POSQUERY, /* 44 Posesssified query, caseful */
OP_POSUPTO, /* 45 Possessified upto, caseful */
- /**** Single characters, caseless, must follow the caseful ones */
+ /* Repeated characters; caseless must follow the caseful ones */
OP_STARI, /* 46 */
OP_MINSTARI, /* 47 */
@@ -1962,8 +2019,8 @@ enum {
OP_POSQUERYI, /* 57 Posesssified query, caseless */
OP_POSUPTOI, /* 58 Possessified upto, caseless */
- /**** The negated ones must follow the non-negated ones, and match them ****/
- /**** Negated single character, caseful; must precede the caseless ones ****/
+ /* The negated ones must follow the non-negated ones, and match them */
+ /* Negated repeated character, caseful; must precede the caseless ones */
OP_NOTSTAR, /* 59 The maximizing and minimizing versions of */
OP_NOTMINSTAR, /* 60 these six opcodes must come in pairs, with */
@@ -1981,7 +2038,7 @@ enum {
OP_NOTPOSQUERY, /* 70 */
OP_NOTPOSUPTO, /* 71 */
- /**** Negated single character, caseless; must follow the caseful ones ****/
+ /* Negated repeated character, caseless; must follow the caseful ones */
OP_NOTSTARI, /* 72 */
OP_NOTMINSTARI, /* 73 */
@@ -1999,7 +2056,7 @@ enum {
OP_NOTPOSQUERYI, /* 83 */
OP_NOTPOSUPTOI, /* 84 */
- /**** Character types ****/
+ /* Character types */
OP_TYPESTAR, /* 85 The maximizing and minimizing versions of */
OP_TYPEMINSTAR, /* 86 these six opcodes must come in pairs, with */
@@ -2030,89 +2087,96 @@ enum {
OP_CRRANGE, /* 104 These are different to the three sets above. */
OP_CRMINRANGE, /* 105 */
+ OP_CRPOSSTAR, /* 106 Possessified versions */
+ OP_CRPOSPLUS, /* 107 */
+ OP_CRPOSQUERY, /* 108 */
+ OP_CRPOSRANGE, /* 109 */
+
/* End of quantifier opcodes */
- OP_CLASS, /* 106 Match a character class, chars < 256 only */
- OP_NCLASS, /* 107 Same, but the bitmap was created from a negative
+ OP_CLASS, /* 110 Match a character class, chars < 256 only */
+ OP_NCLASS, /* 111 Same, but the bitmap was created from a negative
class - the difference is relevant only when a
character > 255 is encountered. */
- OP_XCLASS, /* 108 Extended class for handling > 255 chars within the
+ OP_XCLASS, /* 112 Extended class for handling > 255 chars within the
class. This does both positive and negative. */
- OP_REF, /* 109 Match a back reference, casefully */
- OP_REFI, /* 110 Match a back reference, caselessly */
- OP_RECURSE, /* 111 Match a numbered subpattern (possibly recursive) */
- OP_CALLOUT, /* 112 Call out to external function if provided */
-
- OP_ALT, /* 113 Start of alternation */
- OP_KET, /* 114 End of group that doesn't have an unbounded repeat */
- OP_KETRMAX, /* 115 These two must remain together and in this */
- OP_KETRMIN, /* 116 order. They are for groups the repeat for ever. */
- OP_KETRPOS, /* 117 Possessive unlimited repeat. */
+ OP_REF, /* 113 Match a back reference, casefully */
+ OP_REFI, /* 114 Match a back reference, caselessly */
+ OP_DNREF, /* 115 Match a duplicate name backref, casefully */
+ OP_DNREFI, /* 116 Match a duplicate name backref, caselessly */
+ OP_RECURSE, /* 117 Match a numbered subpattern (possibly recursive) */
+ OP_CALLOUT, /* 118 Call out to external function if provided */
+
+ OP_ALT, /* 119 Start of alternation */
+ OP_KET, /* 120 End of group that doesn't have an unbounded repeat */
+ OP_KETRMAX, /* 121 These two must remain together and in this */
+ OP_KETRMIN, /* 122 order. They are for groups the repeat for ever. */
+ OP_KETRPOS, /* 123 Possessive unlimited repeat. */
/* The assertions must come before BRA, CBRA, ONCE, and COND, and the four
asserts must remain in order. */
- OP_REVERSE, /* 118 Move pointer back - used in lookbehind assertions */
- OP_ASSERT, /* 119 Positive lookahead */
- OP_ASSERT_NOT, /* 120 Negative lookahead */
- OP_ASSERTBACK, /* 121 Positive lookbehind */
- OP_ASSERTBACK_NOT, /* 122 Negative lookbehind */
+ OP_REVERSE, /* 124 Move pointer back - used in lookbehind assertions */
+ OP_ASSERT, /* 125 Positive lookahead */
+ OP_ASSERT_NOT, /* 126 Negative lookahead */
+ OP_ASSERTBACK, /* 127 Positive lookbehind */
+ OP_ASSERTBACK_NOT, /* 128 Negative lookbehind */
/* ONCE, ONCE_NC, BRA, BRAPOS, CBRA, CBRAPOS, and COND must come immediately
after the assertions, with ONCE first, as there's a test for >= ONCE for a
subpattern that isn't an assertion. The POS versions must immediately follow
the non-POS versions in each case. */
- OP_ONCE, /* 123 Atomic group, contains captures */
- OP_ONCE_NC, /* 124 Atomic group containing no captures */
- OP_BRA, /* 125 Start of non-capturing bracket */
- OP_BRAPOS, /* 126 Ditto, with unlimited, possessive repeat */
- OP_CBRA, /* 127 Start of capturing bracket */
- OP_CBRAPOS, /* 128 Ditto, with unlimited, possessive repeat */
- OP_COND, /* 129 Conditional group */
+ OP_ONCE, /* 129 Atomic group, contains captures */
+ OP_ONCE_NC, /* 130 Atomic group containing no captures */
+ OP_BRA, /* 131 Start of non-capturing bracket */
+ OP_BRAPOS, /* 132 Ditto, with unlimited, possessive repeat */
+ OP_CBRA, /* 133 Start of capturing bracket */
+ OP_CBRAPOS, /* 134 Ditto, with unlimited, possessive repeat */
+ OP_COND, /* 135 Conditional group */
/* These five must follow the previous five, in the same order. There's a
check for >= SBRA to distinguish the two sets. */
- OP_SBRA, /* 130 Start of non-capturing bracket, check empty */
- OP_SBRAPOS, /* 131 Ditto, with unlimited, possessive repeat */
- OP_SCBRA, /* 132 Start of capturing bracket, check empty */
- OP_SCBRAPOS, /* 133 Ditto, with unlimited, possessive repeat */
- OP_SCOND, /* 134 Conditional group, check empty */
+ OP_SBRA, /* 136 Start of non-capturing bracket, check empty */
+ OP_SBRAPOS, /* 137 Ditto, with unlimited, possessive repeat */
+ OP_SCBRA, /* 138 Start of capturing bracket, check empty */
+ OP_SCBRAPOS, /* 139 Ditto, with unlimited, possessive repeat */
+ OP_SCOND, /* 140 Conditional group, check empty */
/* The next two pairs must (respectively) be kept together. */
- OP_CREF, /* 135 Used to hold a capture number as condition */
- OP_NCREF, /* 136 Same, but generated by a name reference*/
- OP_RREF, /* 137 Used to hold a recursion number as condition */
- OP_NRREF, /* 138 Same, but generated by a name reference*/
- OP_DEF, /* 139 The DEFINE condition */
+ OP_CREF, /* 141 Used to hold a capture number as condition */
+ OP_DNCREF, /* 142 Used to point to duplicate names as a condition */
+ OP_RREF, /* 143 Used to hold a recursion number as condition */
+ OP_DNRREF, /* 144 Used to point to duplicate names as a condition */
+ OP_DEF, /* 145 The DEFINE condition */
- OP_BRAZERO, /* 140 These two must remain together and in this */
- OP_BRAMINZERO, /* 141 order. */
- OP_BRAPOSZERO, /* 142 */
+ OP_BRAZERO, /* 146 These two must remain together and in this */
+ OP_BRAMINZERO, /* 147 order. */
+ OP_BRAPOSZERO, /* 148 */
/* These are backtracking control verbs */
- OP_MARK, /* 143 always has an argument */
- OP_PRUNE, /* 144 */
- OP_PRUNE_ARG, /* 145 same, but with argument */
- OP_SKIP, /* 146 */
- OP_SKIP_ARG, /* 147 same, but with argument */
- OP_THEN, /* 148 */
- OP_THEN_ARG, /* 149 same, but with argument */
- OP_COMMIT, /* 150 */
+ OP_MARK, /* 149 always has an argument */
+ OP_PRUNE, /* 150 */
+ OP_PRUNE_ARG, /* 151 same, but with argument */
+ OP_SKIP, /* 152 */
+ OP_SKIP_ARG, /* 153 same, but with argument */
+ OP_THEN, /* 154 */
+ OP_THEN_ARG, /* 155 same, but with argument */
+ OP_COMMIT, /* 156 */
/* These are forced failure and success verbs */
- OP_FAIL, /* 151 */
- OP_ACCEPT, /* 152 */
- OP_ASSERT_ACCEPT, /* 153 Used inside assertions */
- OP_CLOSE, /* 154 Used before OP_ACCEPT to close open captures */
+ OP_FAIL, /* 157 */
+ OP_ACCEPT, /* 158 */
+ OP_ASSERT_ACCEPT, /* 159 Used inside assertions */
+ OP_CLOSE, /* 160 Used before OP_ACCEPT to close open captures */
/* This is used to skip a subpattern with a {0} quantifier */
- OP_SKIPZERO, /* 155 */
+ OP_SKIPZERO, /* 161 */
/* This is not an opcode, but is used to check that tables indexed by opcode
are the correct length, in order to catch updating errors - there have been
@@ -2123,7 +2187,8 @@ enum {
/* *** NOTE NOTE NOTE *** Whenever the list above is updated, the two macro
definitions that follow must also be updated to match. There are also tables
-called "coptable" and "poptable" in pcre_dfa_exec.c that must be updated. */
+called "opcode_possessify" in pcre_compile.c and "coptable" and "poptable" in
+pcre_dfa_exec.c that must be updated. */
/* This macro defines textual names for all the opcodes. These are used only
@@ -2136,7 +2201,7 @@ some cases doesn't actually use these names at all). */
"\\S", "\\s", "\\W", "\\w", "Any", "AllAny", "Anybyte", \
"notprop", "prop", "\\R", "\\H", "\\h", "\\V", "\\v", \
"extuni", "\\Z", "\\z", \
- "^", "^", "$", "$", "char", "chari", "not", "noti", \
+ "$", "$", "^", "^", "char", "chari", "not", "noti", \
"*", "*?", "+", "+?", "?", "??", \
"{", "{", "{", \
"*+","++", "?+", "{", \
@@ -2152,7 +2217,8 @@ some cases doesn't actually use these names at all). */
"*", "*?", "+", "+?", "?", "??", "{", "{", "{", \
"*+","++", "?+", "{", \
"*", "*?", "+", "+?", "?", "??", "{", "{", \
- "class", "nclass", "xclass", "Ref", "Refi", \
+ "*+","++", "?+", "{", \
+ "class", "nclass", "xclass", "Ref", "Refi", "DnRef", "DnRefi", \
"Recurse", "Callout", \
"Alt", "Ket", "KetRmax", "KetRmin", "KetRpos", \
"Reverse", "Assert", "Assert not", "AssertB", "AssertB not", \
@@ -2161,7 +2227,7 @@ some cases doesn't actually use these names at all). */
"Cond", \
"SBra", "SBraPos", "SCBra", "SCBraPos", \
"SCond", \
- "Cond ref", "Cond nref", "Cond rec", "Cond nrec", "Cond def", \
+ "Cond ref", "Cond dnref", "Cond rec", "Cond dnrec", "Cond def", \
"Brazero", "Braminzero", "Braposzero", \
"*MARK", "*PRUNE", "*PRUNE", "*SKIP", "*SKIP", \
"*THEN", "*THEN", "*COMMIT", "*FAIL", \
@@ -2186,7 +2252,7 @@ in UTF-8 mode. The code that uses this table must know about such things. */
3, 3, /* \P, \p */ \
1, 1, 1, 1, 1, /* \R, \H, \h, \V, \v */ \
1, /* \X */ \
- 1, 1, 1, 1, 1, 1, /* \Z, \z, ^, ^M, $, $M */ \
+ 1, 1, 1, 1, 1, 1, /* \Z, \z, $, $M ^, ^M */ \
2, /* Char - the minimum length */ \
2, /* Chari - the minimum length */ \
2, /* not */ \
@@ -2217,11 +2283,14 @@ in UTF-8 mode. The code that uses this table must know about such things. */
/* Character class & ref repeats */ \
1, 1, 1, 1, 1, 1, /* *, *?, +, +?, ?, ?? */ \
1+2*IMM2_SIZE, 1+2*IMM2_SIZE, /* CRRANGE, CRMINRANGE */ \
+ 1, 1, 1, 1+2*IMM2_SIZE, /* Possessive *+, ++, ?+, CRPOSRANGE */ \
1+(32/sizeof(pcre_uchar)), /* CLASS */ \
1+(32/sizeof(pcre_uchar)), /* NCLASS */ \
0, /* XCLASS - variable length */ \
1+IMM2_SIZE, /* REF */ \
1+IMM2_SIZE, /* REFI */ \
+ 1+2*IMM2_SIZE, /* DNREF */ \
+ 1+2*IMM2_SIZE, /* DNREFI */ \
1+LINK_SIZE, /* RECURSE */ \
2+2*LINK_SIZE, /* CALLOUT */ \
1+LINK_SIZE, /* Alt */ \
@@ -2246,8 +2315,8 @@ in UTF-8 mode. The code that uses this table must know about such things. */
1+LINK_SIZE+IMM2_SIZE, /* SCBRA */ \
1+LINK_SIZE+IMM2_SIZE, /* SCBRAPOS */ \
1+LINK_SIZE, /* SCOND */ \
- 1+IMM2_SIZE, 1+IMM2_SIZE, /* CREF, NCREF */ \
- 1+IMM2_SIZE, 1+IMM2_SIZE, /* RREF, NRREF */ \
+ 1+IMM2_SIZE, 1+2*IMM2_SIZE, /* CREF, DNCREF */ \
+ 1+IMM2_SIZE, 1+2*IMM2_SIZE, /* RREF, DNRREF */ \
1, /* DEF */ \
1, 1, 1, /* BRAZERO, BRAMINZERO, BRAPOSZERO */ \
3, 1, 3, /* MARK, PRUNE, PRUNE_ARG */ \
@@ -2256,8 +2325,7 @@ in UTF-8 mode. The code that uses this table must know about such things. */
1, 1, 1, 1, /* COMMIT, FAIL, ACCEPT, ASSERT_ACCEPT */ \
1+IMM2_SIZE, 1 /* CLOSE, SKIPZERO */
-/* A magic value for OP_RREF and OP_NRREF to indicate the "any recursion"
-condition. */
+/* A magic value for OP_RREF to indicate the "any recursion" condition. */
#define RREF_ANY 0xffff
@@ -2272,9 +2340,11 @@ enum { ERR0, ERR1, ERR2, ERR3, ERR4, ERR5, ERR6, ERR7, ERR8, ERR9,
ERR40, ERR41, ERR42, ERR43, ERR44, ERR45, ERR46, ERR47, ERR48, ERR49,
ERR50, ERR51, ERR52, ERR53, ERR54, ERR55, ERR56, ERR57, ERR58, ERR59,
ERR60, ERR61, ERR62, ERR63, ERR64, ERR65, ERR66, ERR67, ERR68, ERR69,
- ERR70, ERR71, ERR72, ERR73, ERR74, ERR75, ERR76, ERR77, ERRCOUNT };
+ ERR70, ERR71, ERR72, ERR73, ERR74, ERR75, ERR76, ERR77, ERR78, ERR79,
+ ERR80, ERR81, ERR82, ERR83, ERR84, ERRCOUNT };
/* JIT compiling modes. The function list is indexed by them. */
+
enum { JIT_COMPILE, JIT_PARTIAL_SOFT_COMPILE, JIT_PARTIAL_HARD_COMPILE,
JIT_NUMBER_OF_COMPILE_MODES };
@@ -2282,48 +2352,49 @@ enum { JIT_COMPILE, JIT_PARTIAL_SOFT_COMPILE, JIT_PARTIAL_HARD_COMPILE,
code vector run on as long as necessary after the end. We store an explicit
offset to the name table so that if a regex is compiled on one host, saved, and
then run on another where the size of pointers is different, all might still
-be well. For the case of compiled-on-4 and run-on-8, we include an extra
-pointer that is always NULL. For future-proofing, a few dummy fields were
-originally included - even though you can never get this planning right - but
-there is only one left now.
-
-NOTE NOTE NOTE:
-Because people can now save and re-use compiled patterns, any additions to this
-structure should be made at the end, and something earlier (e.g. a new
-flag in the options or one of the dummy fields) should indicate that the new
-fields are present. Currently PCRE always sets the dummy fields to zero.
-NOTE NOTE NOTE
+be well.
+
+The size of the structure must be a multiple of 8 bytes. For the case of
+compiled-on-4 and run-on-8, we include an extra pointer that is always NULL so
+that there are an even number of pointers which therefore are a multiple of 8
+bytes.
+
+It is necessary to fork the struct for the 32 bit library, since it needs to
+use pcre_uint32 for first_char and req_char. We can't put an ifdef inside the
+typedef because pcretest needs access to the struct of the 8-, 16- and 32-bit
+variants.
+
+*** WARNING ***
+When new fields are added to these structures, remember to adjust the code in
+pcre_byte_order.c that is concerned with swapping the byte order of the fields
+when a compiled regex is reloaded on a host with different endianness.
+*** WARNING ***
+There is also similar byte-flipping code in pcretest.c, which is used for
+testing the byte-flipping features. It must also be kept in step.
+*** WARNING ***
*/
-#if defined COMPILE_PCRE8
-#define REAL_PCRE real_pcre
-#elif defined COMPILE_PCRE16
-#define REAL_PCRE real_pcre16
-#elif defined COMPILE_PCRE32
-#define REAL_PCRE real_pcre32
-#endif
-
-/* It is necessary to fork the struct for 32 bit, since it needs to use
- * pcre_uchar for first_char and req_char. Can't put an ifdef inside the
- * typedef since pcretest needs access to the struct of the 8-, 16-
- * and 32-bit variants. */
-
typedef struct real_pcre8_or_16 {
pcre_uint32 magic_number;
pcre_uint32 size; /* Total that was malloced */
pcre_uint32 options; /* Public options */
- pcre_uint16 flags; /* Private flags */
+ pcre_uint32 flags; /* Private flags */
+ pcre_uint32 limit_match; /* Limit set from regex */
+ pcre_uint32 limit_recursion; /* Limit set from regex */
+ pcre_uint16 first_char; /* Starting character */
+ pcre_uint16 req_char; /* This character must be seen */
pcre_uint16 max_lookbehind; /* Longest lookbehind (characters) */
pcre_uint16 top_bracket; /* Highest numbered group */
pcre_uint16 top_backref; /* Highest numbered back reference */
- pcre_uint16 first_char; /* Starting character */
- pcre_uint16 req_char; /* This character must be seen */
pcre_uint16 name_table_offset; /* Offset to name table that follows */
pcre_uint16 name_entry_size; /* Size of any name items */
pcre_uint16 name_count; /* Number of name items */
pcre_uint16 ref_count; /* Reference count */
+ pcre_uint16 dummy1; /* To ensure size is a multiple of 8 */
+ pcre_uint16 dummy2; /* To ensure size is a multiple of 8 */
+ pcre_uint16 dummy3; /* To ensure size is a multiple of 8 */
const pcre_uint8 *tables; /* Pointer to tables or NULL for std */
- const pcre_uint8 *nullpad; /* NULL padding */
+ void *nullpad; /* NULL padding */
} real_pcre8_or_16;
typedef struct real_pcre8_or_16 real_pcre;
@@ -2333,22 +2404,31 @@ typedef struct real_pcre32 {
pcre_uint32 magic_number;
pcre_uint32 size; /* Total that was malloced */
pcre_uint32 options; /* Public options */
- pcre_uint16 flags; /* Private flags */
+ pcre_uint32 flags; /* Private flags */
+ pcre_uint32 limit_match; /* Limit set from regex */
+ pcre_uint32 limit_recursion; /* Limit set from regex */
+ pcre_uint32 first_char; /* Starting character */
+ pcre_uint32 req_char; /* This character must be seen */
pcre_uint16 max_lookbehind; /* Longest lookbehind (characters) */
pcre_uint16 top_bracket; /* Highest numbered group */
pcre_uint16 top_backref; /* Highest numbered back reference */
- pcre_uint32 first_char; /* Starting character */
- pcre_uint32 req_char; /* This character must be seen */
pcre_uint16 name_table_offset; /* Offset to name table that follows */
pcre_uint16 name_entry_size; /* Size of any name items */
pcre_uint16 name_count; /* Number of name items */
pcre_uint16 ref_count; /* Reference count */
- pcre_uint16 dummy1; /* for later expansion */
- pcre_uint16 dummy2; /* for later expansion */
+ pcre_uint16 dummy; /* To ensure size is a multiple of 8 */
const pcre_uint8 *tables; /* Pointer to tables or NULL for std */
- void *nullpad; /* for later expansion */
+ void *nullpad; /* NULL padding */
} real_pcre32;
+#if defined COMPILE_PCRE8
+#define REAL_PCRE real_pcre
+#elif defined COMPILE_PCRE16
+#define REAL_PCRE real_pcre16
+#elif defined COMPILE_PCRE32
+#define REAL_PCRE real_pcre32
+#endif
+
/* Assert that the size of REAL_PCRE is divisible by 8 */
typedef int __assert_real_pcre_size_divisible_8[(sizeof(REAL_PCRE) % 8) == 0 ? 1 : -1];
@@ -2382,6 +2462,15 @@ typedef struct open_capitem {
pcre_uint16 flag; /* Set TRUE if recursive back ref */
} open_capitem;
+/* Structure for building a list of named groups during the first pass of
+compiling. */
+
+typedef struct named_group {
+ const pcre_uchar *name; /* Points to the name in the pattern */
+ int length; /* Length of the name */
+ pcre_uint32 number; /* Group number */
+} named_group;
+
/* Structure for passing "static" information around between the functions
doing the compiling, so that they are thread-safe. */
@@ -2394,24 +2483,29 @@ typedef struct compile_data {
const pcre_uchar *start_code; /* The start of the compiled code */
const pcre_uchar *start_pattern; /* The start of the pattern */
const pcre_uchar *end_pattern; /* The end of the pattern */
- open_capitem *open_caps; /* Chain of open capture items */
pcre_uchar *hwm; /* High watermark of workspace */
+ open_capitem *open_caps; /* Chain of open capture items */
+ named_group *named_groups; /* Points to vector in pre-compile */
pcre_uchar *name_table; /* The name/number table */
int names_found; /* Number of entries so far */
int name_entry_size; /* Size of each entry */
+ int named_group_list_size; /* Number of entries in the list */
int workspace_size; /* Size of workspace */
- unsigned int bracount; /* Count of capturing parens as we compile */
+ unsigned int bracount; /* Count of capturing parens as we compile */
int final_bracount; /* Saved value after first pass */
int max_lookbehind; /* Maximum lookbehind (characters) */
int top_backref; /* Maximum back reference */
unsigned int backref_map; /* Bitmap of low back refs */
+ unsigned int namedrefcount; /* Number of backreferences by name */
+ int parens_depth; /* Depth of nested parentheses */
int assert_depth; /* Depth of nested assertions */
- int external_options; /* External (initial) options */
- int external_flags; /* External flag bits to be set */
+ pcre_uint32 external_options; /* External (initial) options */
+ pcre_uint32 external_flags; /* External flag bits to be set */
int req_varyopt; /* "After variable item" flag for reqbyte */
BOOL had_accept; /* (*ACCEPT) encountered */
BOOL had_pruneorskip; /* (*PRUNE) or (*SKIP) encountered */
BOOL check_lookbehind; /* Lookbehinds need later checking */
+ BOOL dupnames; /* Duplicate names exist */
int nltype; /* Newline type */
int nllen; /* Newline string length */
pcre_uchar nl[4]; /* Newline string when fixed length */
@@ -2433,6 +2527,7 @@ typedef struct recursion_info {
unsigned int group_num; /* Number of group that was called */
int *offset_save; /* Pointer to start of saved offsets */
int saved_max; /* Number of saved offsets */
+ int saved_capture_last; /* Last capture number */
PCRE_PUCHAR subject_position; /* Position at start of recursion */
} recursion_info;
@@ -2469,12 +2564,13 @@ typedef struct match_data {
int nllen; /* Newline string length */
int name_count; /* Number of names in name table */
int name_entry_size; /* Size of entry in names table */
+ unsigned int skip_arg_count; /* For counting SKIP_ARGs */
+ unsigned int ignore_skip_arg; /* For re-run when SKIP arg name not found */
pcre_uchar *name_table; /* Table of names */
pcre_uchar nl[4]; /* Newline string when fixed */
const pcre_uint8 *lcc; /* Points to lower casing table */
const pcre_uint8 *fcc; /* Points to case-flipping table */
const pcre_uint8 *ctypes; /* Points to table of type maps */
- BOOL offset_overflow; /* Set if too many extractions */
BOOL notbol; /* NOTBOL flag */
BOOL noteol; /* NOTEOL flag */
BOOL utf; /* UTF-8 / UTF-16 flag */
@@ -2486,7 +2582,6 @@ typedef struct match_data {
BOOL hitend; /* Hit the end of the subject at some point */
BOOL bsr_anycrlf; /* \R is just any CRLF, not full Unicode */
BOOL hasthen; /* Pattern contains (*THEN) */
- BOOL ignore_skip_arg; /* For re-run when SKIP name not found */
const pcre_uchar *start_code; /* For use when recursing */
PCRE_PUCHAR start_subject; /* Start of the subject string */
PCRE_PUCHAR end_subject; /* End of the subject string */
@@ -2495,7 +2590,7 @@ typedef struct match_data {
PCRE_PUCHAR start_used_ptr; /* Earliest consulted character */
int partial; /* PARTIAL options */
int end_offset_top; /* Highwater mark at end of match */
- int capture_last; /* Most recent capture number */
+ pcre_int32 capture_last; /* Most recent capture number + overflow flag */
int start_offset; /* The start offset value */
int match_function_type; /* Set for certain special calls of MATCH() */
eptrblock *eptrchain; /* Chain of eptrblocks for tail recursions */
diff --git a/ext/pcre/pcrelib/pcre_maketables.c b/ext/pcre/pcrelib/pcre_maketables.c
index 610a669586..a44a6eaa90 100644
--- a/ext/pcre/pcrelib/pcre_maketables.c
+++ b/ext/pcre/pcrelib/pcre_maketables.c
@@ -98,13 +98,17 @@ for (i = 0; i < 256; i++) *p++ = tolower(i);
for (i = 0; i < 256; i++) *p++ = islower(i)? toupper(i) : tolower(i);
/* Then the character class tables. Don't try to be clever and save effort on
-exclusive ones - in some locales things may be different. Note that the table
-for "space" includes everything "isspace" gives, including VT in the default
-locale. This makes it work for the POSIX class [:space:]. Note also that it is
-possible for a character to be alnum or alpha without being lower or upper,
-such as "male and female ordinals" (\xAA and \xBA) in the fr_FR locale (at
-least under Debian Linux's locales as of 12/2005). So we must test for alnum
-specially. */
+exclusive ones - in some locales things may be different.
+
+Note that the table for "space" includes everything "isspace" gives, including
+VT in the default locale. This makes it work for the POSIX class [:space:].
+From release 8.34 is is also correct for Perl space, because Perl added VT at
+release 5.18.
+
+Note also that it is possible for a character to be alnum or alpha without
+being lower or upper, such as "male and female ordinals" (\xAA and \xBA) in the
+fr_FR locale (at least under Debian Linux's locales as of 12/2005). So we must
+test for alnum specially. */
memset(p, 0, cbit_length);
for (i = 0; i < 256; i++)
@@ -123,14 +127,15 @@ for (i = 0; i < 256; i++)
}
p += cbit_length;
-/* Finally, the character type table. In this, we exclude VT from the white
-space chars, because Perl doesn't recognize it as such for \s and for comments
-within regexes. */
+/* Finally, the character type table. In this, we used to exclude VT from the
+white space chars, because Perl didn't recognize it as such for \s and for
+comments within regexes. However, Perl changed at release 5.18, so PCRE changed
+at release 8.34. */
for (i = 0; i < 256; i++)
{
int x = 0;
- if (i != CHAR_VT && isspace(i)) x += ctype_space;
+ if (isspace(i)) x += ctype_space;
if (isalpha(i)) x += ctype_letter;
if (isdigit(i)) x += ctype_digit;
if (isxdigit(i)) x += ctype_xdigit;
diff --git a/ext/pcre/pcrelib/pcre_study.c b/ext/pcre/pcrelib/pcre_study.c
index 12d2a66817..c2aff517a5 100644
--- a/ext/pcre/pcrelib/pcre_study.c
+++ b/ext/pcre/pcrelib/pcre_study.c
@@ -66,8 +66,9 @@ string of that length that matches. In UTF8 mode, the result is in characters
rather than bytes.
Arguments:
+ re compiled pattern block
code pointer to start of group (the bracket)
- startcode pointer to start of the whole pattern
+ startcode pointer to start of the whole pattern's code
options the compiling options
int RECURSE depth
@@ -78,8 +79,8 @@ Returns: the minimum length
*/
static int
-find_minlength(const pcre_uchar *code, const pcre_uchar *startcode, int options,
- int recurse_depth)
+find_minlength(const REAL_PCRE *re, const pcre_uchar *code,
+ const pcre_uchar *startcode, int options, int recurse_depth)
{
int length = -1;
/* PCRE_UTF16 has the same value as PCRE_UTF8. */
@@ -129,7 +130,7 @@ for (;;)
case OP_SBRAPOS:
case OP_ONCE:
case OP_ONCE_NC:
- d = find_minlength(cc, startcode, options, recurse_depth);
+ d = find_minlength(re, cc, startcode, options, recurse_depth);
if (d < 0) return d;
branchlength += d;
do cc += GET(cc, 1); while (*cc == OP_ALT);
@@ -175,9 +176,9 @@ for (;;)
case OP_REVERSE:
case OP_CREF:
- case OP_NCREF:
+ case OP_DNCREF:
case OP_RREF:
- case OP_NRREF:
+ case OP_DNRREF:
case OP_DEF:
case OP_CALLOUT:
case OP_SOD:
@@ -341,6 +342,7 @@ for (;;)
{
case OP_CRPLUS:
case OP_CRMINPLUS:
+ case OP_CRPOSPLUS:
branchlength++;
/* Fall through */
@@ -348,11 +350,14 @@ for (;;)
case OP_CRMINSTAR:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSQUERY:
cc++;
break;
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
branchlength += GET2(cc,1);
cc += 1 + 2 * IMM2_SIZE;
break;
@@ -375,7 +380,38 @@ for (;;)
matches an empty string (by default it causes a matching failure), so in
that case we must set the minimum length to zero. */
- case OP_REF:
+ case OP_DNREF: /* Duplicate named pattern back reference */
+ case OP_DNREFI:
+ if ((options & PCRE_JAVASCRIPT_COMPAT) == 0)
+ {
+ int count = GET2(cc, 1+IMM2_SIZE);
+ pcre_uchar *slot = (pcre_uchar *)re +
+ re->name_table_offset + GET2(cc, 1) * re->name_entry_size;
+ d = INT_MAX;
+ while (count-- > 0)
+ {
+ ce = cs = (pcre_uchar *)PRIV(find_bracket)(startcode, utf, GET2(slot, 0));
+ if (cs == NULL) return -2;
+ do ce += GET(ce, 1); while (*ce == OP_ALT);
+ if (cc > cs && cc < ce)
+ {
+ d = 0;
+ had_recurse = TRUE;
+ break;
+ }
+ else
+ {
+ int dd = find_minlength(re, cs, startcode, options, recurse_depth);
+ if (dd < d) d = dd;
+ }
+ slot += re->name_entry_size;
+ }
+ }
+ else d = 0;
+ cc += 1 + 2*IMM2_SIZE;
+ goto REPEAT_BACK_REFERENCE;
+
+ case OP_REF: /* Single back reference */
case OP_REFI:
if ((options & PCRE_JAVASCRIPT_COMPAT) == 0)
{
@@ -389,7 +425,7 @@ for (;;)
}
else
{
- d = find_minlength(cs, startcode, options, recurse_depth);
+ d = find_minlength(re, cs, startcode, options, recurse_depth);
}
}
else d = 0;
@@ -397,24 +433,29 @@ for (;;)
/* Handle repeated back references */
+ REPEAT_BACK_REFERENCE:
switch (*cc)
{
case OP_CRSTAR:
case OP_CRMINSTAR:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSQUERY:
min = 0;
cc++;
break;
case OP_CRPLUS:
case OP_CRMINPLUS:
+ case OP_CRPOSPLUS:
min = 1;
cc++;
break;
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
min = GET2(cc, 1);
cc += 1 + 2 * IMM2_SIZE;
break;
@@ -437,7 +478,8 @@ for (;;)
had_recurse = TRUE;
else
{
- branchlength += find_minlength(cs, startcode, options, recurse_depth + 1);
+ branchlength += find_minlength(re, cs, startcode, options,
+ recurse_depth + 1);
}
cc += 1 + LINK_SIZE;
break;
@@ -778,6 +820,10 @@ do
case OP_COND:
case OP_CREF:
case OP_DEF:
+ case OP_DNCREF:
+ case OP_DNREF:
+ case OP_DNREFI:
+ case OP_DNRREF:
case OP_DOLL:
case OP_DOLLM:
case OP_END:
@@ -786,7 +832,6 @@ do
case OP_EXTUNI:
case OP_FAIL:
case OP_MARK:
- case OP_NCREF:
case OP_NOT:
case OP_NOTEXACT:
case OP_NOTEXACTI:
@@ -818,7 +863,6 @@ do
case OP_NOTUPTOI:
case OP_NOT_HSPACE:
case OP_NOT_VSPACE:
- case OP_NRREF:
case OP_PROP:
case OP_PRUNE:
case OP_PRUNE_ARG:
@@ -1183,24 +1227,16 @@ do
set_type_bits(start_bits, cbit_digit, table_limit, cd);
break;
- /* The cbit_space table has vertical tab as whitespace; we have to
- ensure it gets set as not whitespace. Luckily, the code value is the
- same (0x0b) in ASCII and EBCDIC, so we can just adjust the appropriate
- bit. */
+ /* The cbit_space table has vertical tab as whitespace; we no longer
+ have to play fancy tricks because Perl added VT to its whitespace at
+ release 5.18. PCRE added it at release 8.34. */
case OP_NOT_WHITESPACE:
set_nottype_bits(start_bits, cbit_space, table_limit, cd);
- start_bits[1] |= 0x08;
break;
- /* The cbit_space table has vertical tab as whitespace; we have to
- avoid setting it. Luckily, the code value is the same (0x0b) in ASCII
- and EBCDIC, so we can just adjust the appropriate bit. */
-
case OP_WHITESPACE:
- c = start_bits[1]; /* Save in case it was already set */
set_type_bits(start_bits, cbit_space, table_limit, cd);
- start_bits[1] = (start_bits[1] & ~0x08) | c;
break;
case OP_NOT_WORDCHAR:
@@ -1277,11 +1313,14 @@ do
case OP_CRMINSTAR:
case OP_CRQUERY:
case OP_CRMINQUERY:
+ case OP_CRPOSSTAR:
+ case OP_CRPOSQUERY:
tcode++;
break;
case OP_CRRANGE:
case OP_CRMINRANGE:
+ case OP_CRPOSRANGE:
if (GET2(tcode, 1) == 0) tcode += 1 + 2 * IMM2_SIZE;
else try_next = FALSE;
break;
@@ -1346,6 +1385,7 @@ pcre_uchar *code;
compile_data compile_block;
const REAL_PCRE *re = (const REAL_PCRE *)external_re;
+
*errorptr = NULL;
if (re == NULL || re->magic_number != MAGIC_NUMBER)
@@ -1422,7 +1462,7 @@ if ((re->options & PCRE_ANCHORED) == 0 &&
/* Find the minimum length of subject string. */
-switch(min = find_minlength(code, code, re->options, 0))
+switch(min = find_minlength(re, code, code, re->options, 0))
{
case -2: *errorptr = "internal error: missing capturing bracket"; return NULL;
case -3: *errorptr = "internal error: opcode not recognized"; return NULL;
diff --git a/ext/pcre/pcrelib/pcre_tables.c b/ext/pcre/pcrelib/pcre_tables.c
index 34ee0488a8..f38ab52cbb 100644
--- a/ext/pcre/pcrelib/pcre_tables.c
+++ b/ext/pcre/pcrelib/pcre_tables.c
@@ -346,6 +346,7 @@ strings to make sure that UTF-8 support works on EBCDIC platforms. */
#define STRING_Xan0 STR_X STR_a STR_n "\0"
#define STRING_Xps0 STR_X STR_p STR_s "\0"
#define STRING_Xsp0 STR_X STR_s STR_p "\0"
+#define STRING_Xuc0 STR_X STR_u STR_c "\0"
#define STRING_Xwd0 STR_X STR_w STR_d "\0"
#define STRING_Yi0 STR_Y STR_i "\0"
#define STRING_Z0 STR_Z "\0"
@@ -493,6 +494,7 @@ const char PRIV(utt_names)[] =
STRING_Xan0
STRING_Xps0
STRING_Xsp0
+ STRING_Xuc0
STRING_Xwd0
STRING_Yi0
STRING_Z0
@@ -640,12 +642,13 @@ const ucp_type_table PRIV(utt)[] = {
{ 1011, PT_ALNUM, 0 },
{ 1015, PT_PXSPACE, 0 },
{ 1019, PT_SPACE, 0 },
- { 1023, PT_WORD, 0 },
- { 1027, PT_SC, ucp_Yi },
- { 1030, PT_GC, ucp_Z },
- { 1032, PT_PC, ucp_Zl },
- { 1035, PT_PC, ucp_Zp },
- { 1038, PT_PC, ucp_Zs }
+ { 1023, PT_UCNC, 0 },
+ { 1027, PT_WORD, 0 },
+ { 1031, PT_SC, ucp_Yi },
+ { 1034, PT_GC, ucp_Z },
+ { 1036, PT_PC, ucp_Zl },
+ { 1039, PT_PC, ucp_Zp },
+ { 1042, PT_PC, ucp_Zs }
};
const int PRIV(utt_size) = sizeof(PRIV(utt)) / sizeof(ucp_type_table);
diff --git a/ext/pcre/pcrelib/pcre_ucd.c b/ext/pcre/pcrelib/pcre_ucd.c
index 56f31a1e69..46ea70c44c 100644
--- a/ext/pcre/pcrelib/pcre_ucd.c
+++ b/ext/pcre/pcrelib/pcre_ucd.c
@@ -20,7 +20,7 @@ needed. */
/* Unicode character database. */
/* This file was autogenerated by the MultiStage2.py script. */
-/* Total size: 65696 bytes, block size: 128. */
+/* Total size: 65688 bytes, block size: 128. */
/* The tables herein are needed only when UCP support is built
into PCRE. This module should not be referenced otherwise, so
@@ -79,7 +79,7 @@ const pcre_uint32 PRIV(ucd_caseless_sets)[] = {
#ifndef PCRE_INCLUDED
-const ucd_record PRIV(ucd_records)[] = { /* 5024 bytes, record size 8 */
+const ucd_record PRIV(ucd_records)[] = { /* 5016 bytes, record size 8 */
{ 9, 0, 2, 0, 0, }, /* 0 */
{ 9, 0, 1, 0, 0, }, /* 1 */
{ 9, 0, 0, 0, 0, }, /* 2 */
@@ -422,7 +422,7 @@ const ucd_record PRIV(ucd_records)[] = { /* 5024 bytes, record size 8 */
{ 37, 21, 12, 0, 0, }, /* 339 */
{ 37, 17, 12, 0, 0, }, /* 340 */
{ 37, 12, 3, 0, 0, }, /* 341 */
- { 37, 29, 12, 0, 0, }, /* 342 */
+ { 37, 1, 2, 0, 0, }, /* 342 */
{ 37, 13, 12, 0, 0, }, /* 343 */
{ 37, 7, 12, 0, 0, }, /* 344 */
{ 37, 6, 12, 0, 0, }, /* 345 */
@@ -598,116 +598,115 @@ const ucd_record PRIV(ucd_records)[] = { /* 5024 bytes, record size 8 */
{ 83, 10, 5, 0, 0, }, /* 515 */
{ 83, 7, 12, 0, 0, }, /* 516 */
{ 83, 21, 12, 0, 0, }, /* 517 */
- { 83, 6, 12, 0, 0, }, /* 518 */
- { 83, 13, 12, 0, 0, }, /* 519 */
- { 67, 7, 12, 0, 0, }, /* 520 */
- { 67, 12, 3, 0, 0, }, /* 521 */
- { 67, 10, 5, 0, 0, }, /* 522 */
- { 67, 13, 12, 0, 0, }, /* 523 */
- { 67, 21, 12, 0, 0, }, /* 524 */
- { 38, 6, 12, 0, 0, }, /* 525 */
- { 91, 7, 12, 0, 0, }, /* 526 */
- { 91, 12, 3, 0, 0, }, /* 527 */
- { 91, 6, 12, 0, 0, }, /* 528 */
- { 91, 21, 12, 0, 0, }, /* 529 */
- { 86, 7, 12, 0, 0, }, /* 530 */
- { 86, 10, 5, 0, 0, }, /* 531 */
- { 86, 12, 3, 0, 0, }, /* 532 */
- { 86, 21, 12, 0, 0, }, /* 533 */
- { 86, 6, 12, 0, 0, }, /* 534 */
- { 86, 13, 12, 0, 0, }, /* 535 */
- { 23, 7, 9, 0, 0, }, /* 536 */
- { 23, 7, 10, 0, 0, }, /* 537 */
- { 9, 4, 2, 0, 0, }, /* 538 */
- { 9, 3, 12, 0, 0, }, /* 539 */
- { 25, 25, 12, 0, 0, }, /* 540 */
- { 0, 24, 12, 0, 0, }, /* 541 */
- { 9, 6, 3, 0, 0, }, /* 542 */
- { 35, 7, 12, 0, 0, }, /* 543 */
- { 19, 14, 12, 0, 0, }, /* 544 */
- { 19, 15, 12, 0, 0, }, /* 545 */
- { 19, 26, 12, 0, 0, }, /* 546 */
- { 70, 7, 12, 0, 0, }, /* 547 */
- { 66, 7, 12, 0, 0, }, /* 548 */
- { 41, 7, 12, 0, 0, }, /* 549 */
- { 41, 15, 12, 0, 0, }, /* 550 */
- { 18, 7, 12, 0, 0, }, /* 551 */
- { 18, 14, 12, 0, 0, }, /* 552 */
- { 59, 7, 12, 0, 0, }, /* 553 */
- { 59, 21, 12, 0, 0, }, /* 554 */
- { 42, 7, 12, 0, 0, }, /* 555 */
- { 42, 21, 12, 0, 0, }, /* 556 */
- { 42, 14, 12, 0, 0, }, /* 557 */
- { 13, 9, 12, 0, 40, }, /* 558 */
- { 13, 5, 12, 0, -40, }, /* 559 */
- { 46, 7, 12, 0, 0, }, /* 560 */
- { 44, 7, 12, 0, 0, }, /* 561 */
- { 44, 13, 12, 0, 0, }, /* 562 */
- { 11, 7, 12, 0, 0, }, /* 563 */
- { 80, 7, 12, 0, 0, }, /* 564 */
- { 80, 21, 12, 0, 0, }, /* 565 */
- { 80, 15, 12, 0, 0, }, /* 566 */
- { 65, 7, 12, 0, 0, }, /* 567 */
- { 65, 15, 12, 0, 0, }, /* 568 */
- { 65, 21, 12, 0, 0, }, /* 569 */
- { 71, 7, 12, 0, 0, }, /* 570 */
- { 71, 21, 12, 0, 0, }, /* 571 */
- { 97, 7, 12, 0, 0, }, /* 572 */
- { 96, 7, 12, 0, 0, }, /* 573 */
- { 30, 7, 12, 0, 0, }, /* 574 */
- { 30, 12, 3, 0, 0, }, /* 575 */
- { 30, 15, 12, 0, 0, }, /* 576 */
- { 30, 21, 12, 0, 0, }, /* 577 */
- { 87, 7, 12, 0, 0, }, /* 578 */
- { 87, 15, 12, 0, 0, }, /* 579 */
- { 87, 21, 12, 0, 0, }, /* 580 */
- { 77, 7, 12, 0, 0, }, /* 581 */
- { 77, 21, 12, 0, 0, }, /* 582 */
- { 82, 7, 12, 0, 0, }, /* 583 */
- { 82, 15, 12, 0, 0, }, /* 584 */
- { 81, 7, 12, 0, 0, }, /* 585 */
- { 81, 15, 12, 0, 0, }, /* 586 */
- { 88, 7, 12, 0, 0, }, /* 587 */
- { 0, 15, 12, 0, 0, }, /* 588 */
- { 93, 10, 5, 0, 0, }, /* 589 */
- { 93, 12, 3, 0, 0, }, /* 590 */
- { 93, 7, 12, 0, 0, }, /* 591 */
- { 93, 21, 12, 0, 0, }, /* 592 */
- { 93, 15, 12, 0, 0, }, /* 593 */
- { 93, 13, 12, 0, 0, }, /* 594 */
- { 84, 12, 3, 0, 0, }, /* 595 */
- { 84, 10, 5, 0, 0, }, /* 596 */
- { 84, 7, 12, 0, 0, }, /* 597 */
- { 84, 21, 12, 0, 0, }, /* 598 */
- { 84, 1, 2, 0, 0, }, /* 599 */
- { 100, 7, 12, 0, 0, }, /* 600 */
- { 100, 13, 12, 0, 0, }, /* 601 */
- { 95, 12, 3, 0, 0, }, /* 602 */
- { 95, 7, 12, 0, 0, }, /* 603 */
- { 95, 10, 5, 0, 0, }, /* 604 */
- { 95, 13, 12, 0, 0, }, /* 605 */
- { 95, 21, 12, 0, 0, }, /* 606 */
- { 99, 12, 3, 0, 0, }, /* 607 */
- { 99, 10, 5, 0, 0, }, /* 608 */
- { 99, 7, 12, 0, 0, }, /* 609 */
- { 99, 21, 12, 0, 0, }, /* 610 */
- { 99, 13, 12, 0, 0, }, /* 611 */
- { 101, 7, 12, 0, 0, }, /* 612 */
- { 101, 12, 3, 0, 0, }, /* 613 */
- { 101, 10, 5, 0, 0, }, /* 614 */
- { 101, 13, 12, 0, 0, }, /* 615 */
- { 62, 7, 12, 0, 0, }, /* 616 */
- { 62, 14, 12, 0, 0, }, /* 617 */
- { 62, 21, 12, 0, 0, }, /* 618 */
- { 79, 7, 12, 0, 0, }, /* 619 */
- { 98, 7, 12, 0, 0, }, /* 620 */
- { 98, 10, 5, 0, 0, }, /* 621 */
- { 98, 12, 3, 0, 0, }, /* 622 */
- { 98, 6, 12, 0, 0, }, /* 623 */
- { 9, 10, 3, 0, 0, }, /* 624 */
- { 19, 12, 3, 0, 0, }, /* 625 */
- { 9, 26, 11, 0, 0, }, /* 626 */
- { 26, 26, 12, 0, 0, }, /* 627 */
+ { 83, 13, 12, 0, 0, }, /* 518 */
+ { 67, 7, 12, 0, 0, }, /* 519 */
+ { 67, 12, 3, 0, 0, }, /* 520 */
+ { 67, 10, 5, 0, 0, }, /* 521 */
+ { 67, 13, 12, 0, 0, }, /* 522 */
+ { 67, 21, 12, 0, 0, }, /* 523 */
+ { 38, 6, 12, 0, 0, }, /* 524 */
+ { 91, 7, 12, 0, 0, }, /* 525 */
+ { 91, 12, 3, 0, 0, }, /* 526 */
+ { 91, 6, 12, 0, 0, }, /* 527 */
+ { 91, 21, 12, 0, 0, }, /* 528 */
+ { 86, 7, 12, 0, 0, }, /* 529 */
+ { 86, 10, 5, 0, 0, }, /* 530 */
+ { 86, 12, 3, 0, 0, }, /* 531 */
+ { 86, 21, 12, 0, 0, }, /* 532 */
+ { 86, 6, 12, 0, 0, }, /* 533 */
+ { 86, 13, 12, 0, 0, }, /* 534 */
+ { 23, 7, 9, 0, 0, }, /* 535 */
+ { 23, 7, 10, 0, 0, }, /* 536 */
+ { 9, 4, 2, 0, 0, }, /* 537 */
+ { 9, 3, 12, 0, 0, }, /* 538 */
+ { 25, 25, 12, 0, 0, }, /* 539 */
+ { 0, 24, 12, 0, 0, }, /* 540 */
+ { 9, 6, 3, 0, 0, }, /* 541 */
+ { 35, 7, 12, 0, 0, }, /* 542 */
+ { 19, 14, 12, 0, 0, }, /* 543 */
+ { 19, 15, 12, 0, 0, }, /* 544 */
+ { 19, 26, 12, 0, 0, }, /* 545 */
+ { 70, 7, 12, 0, 0, }, /* 546 */
+ { 66, 7, 12, 0, 0, }, /* 547 */
+ { 41, 7, 12, 0, 0, }, /* 548 */
+ { 41, 15, 12, 0, 0, }, /* 549 */
+ { 18, 7, 12, 0, 0, }, /* 550 */
+ { 18, 14, 12, 0, 0, }, /* 551 */
+ { 59, 7, 12, 0, 0, }, /* 552 */
+ { 59, 21, 12, 0, 0, }, /* 553 */
+ { 42, 7, 12, 0, 0, }, /* 554 */
+ { 42, 21, 12, 0, 0, }, /* 555 */
+ { 42, 14, 12, 0, 0, }, /* 556 */
+ { 13, 9, 12, 0, 40, }, /* 557 */
+ { 13, 5, 12, 0, -40, }, /* 558 */
+ { 46, 7, 12, 0, 0, }, /* 559 */
+ { 44, 7, 12, 0, 0, }, /* 560 */
+ { 44, 13, 12, 0, 0, }, /* 561 */
+ { 11, 7, 12, 0, 0, }, /* 562 */
+ { 80, 7, 12, 0, 0, }, /* 563 */
+ { 80, 21, 12, 0, 0, }, /* 564 */
+ { 80, 15, 12, 0, 0, }, /* 565 */
+ { 65, 7, 12, 0, 0, }, /* 566 */
+ { 65, 15, 12, 0, 0, }, /* 567 */
+ { 65, 21, 12, 0, 0, }, /* 568 */
+ { 71, 7, 12, 0, 0, }, /* 569 */
+ { 71, 21, 12, 0, 0, }, /* 570 */
+ { 97, 7, 12, 0, 0, }, /* 571 */
+ { 96, 7, 12, 0, 0, }, /* 572 */
+ { 30, 7, 12, 0, 0, }, /* 573 */
+ { 30, 12, 3, 0, 0, }, /* 574 */
+ { 30, 15, 12, 0, 0, }, /* 575 */
+ { 30, 21, 12, 0, 0, }, /* 576 */
+ { 87, 7, 12, 0, 0, }, /* 577 */
+ { 87, 15, 12, 0, 0, }, /* 578 */
+ { 87, 21, 12, 0, 0, }, /* 579 */
+ { 77, 7, 12, 0, 0, }, /* 580 */
+ { 77, 21, 12, 0, 0, }, /* 581 */
+ { 82, 7, 12, 0, 0, }, /* 582 */
+ { 82, 15, 12, 0, 0, }, /* 583 */
+ { 81, 7, 12, 0, 0, }, /* 584 */
+ { 81, 15, 12, 0, 0, }, /* 585 */
+ { 88, 7, 12, 0, 0, }, /* 586 */
+ { 0, 15, 12, 0, 0, }, /* 587 */
+ { 93, 10, 5, 0, 0, }, /* 588 */
+ { 93, 12, 3, 0, 0, }, /* 589 */
+ { 93, 7, 12, 0, 0, }, /* 590 */
+ { 93, 21, 12, 0, 0, }, /* 591 */
+ { 93, 15, 12, 0, 0, }, /* 592 */
+ { 93, 13, 12, 0, 0, }, /* 593 */
+ { 84, 12, 3, 0, 0, }, /* 594 */
+ { 84, 10, 5, 0, 0, }, /* 595 */
+ { 84, 7, 12, 0, 0, }, /* 596 */
+ { 84, 21, 12, 0, 0, }, /* 597 */
+ { 84, 1, 2, 0, 0, }, /* 598 */
+ { 100, 7, 12, 0, 0, }, /* 599 */
+ { 100, 13, 12, 0, 0, }, /* 600 */
+ { 95, 12, 3, 0, 0, }, /* 601 */
+ { 95, 7, 12, 0, 0, }, /* 602 */
+ { 95, 10, 5, 0, 0, }, /* 603 */
+ { 95, 13, 12, 0, 0, }, /* 604 */
+ { 95, 21, 12, 0, 0, }, /* 605 */
+ { 99, 12, 3, 0, 0, }, /* 606 */
+ { 99, 10, 5, 0, 0, }, /* 607 */
+ { 99, 7, 12, 0, 0, }, /* 608 */
+ { 99, 21, 12, 0, 0, }, /* 609 */
+ { 99, 13, 12, 0, 0, }, /* 610 */
+ { 101, 7, 12, 0, 0, }, /* 611 */
+ { 101, 12, 3, 0, 0, }, /* 612 */
+ { 101, 10, 5, 0, 0, }, /* 613 */
+ { 101, 13, 12, 0, 0, }, /* 614 */
+ { 62, 7, 12, 0, 0, }, /* 615 */
+ { 62, 14, 12, 0, 0, }, /* 616 */
+ { 62, 21, 12, 0, 0, }, /* 617 */
+ { 79, 7, 12, 0, 0, }, /* 618 */
+ { 98, 7, 12, 0, 0, }, /* 619 */
+ { 98, 10, 5, 0, 0, }, /* 620 */
+ { 98, 12, 3, 0, 0, }, /* 621 */
+ { 98, 6, 12, 0, 0, }, /* 622 */
+ { 9, 10, 3, 0, 0, }, /* 623 */
+ { 19, 12, 3, 0, 0, }, /* 624 */
+ { 9, 26, 11, 0, 0, }, /* 625 */
+ { 26, 26, 12, 0, 0, }, /* 626 */
};
const pcre_uint8 PRIV(ucd_stage1)[] = { /* 8704 bytes */
@@ -1380,7 +1379,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
/* block 12 */
185,185,185,185,185,109,186,186,186,187,187,188, 4,187,189,189,
-190,190,190,190,190,190,190,190,190,190,190, 4,109,109,187, 4,
+190,190,190,190,190,190,190,190,190,190,190, 4,185,109,187, 4,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
102,191,191,191,191,191,191,191,191,191,191,104,104,104,104,104,
@@ -1760,7 +1759,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
/* block 50 */
360,360,360,360,360,360,360,360,360,360,360,360,360,360,360,360,
-360,360,360,360,360,360,360,361,361,362,362,362,109,109,363,363,
+360,360,360,360,360,360,360,361,361,362,362,361,109,109,363,363,
364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,
364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,
364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,364,
@@ -1885,7 +1884,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
4, 4, 4, 4, 4, 4, 4, 4, 4, 21, 25, 4, 4, 4, 4, 15,
15, 4, 4, 4, 8, 6, 7, 4, 4, 4, 4, 4, 4, 4, 4, 4,
4, 4, 8, 4, 15, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 3,
- 22, 22, 22, 22, 22,426,426,426,426,426, 22, 22, 22, 22, 22, 22,
+ 22, 22, 22, 22, 22,426, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22,
23,101,109,109, 23, 23, 23, 23, 23, 23, 8, 8, 8, 6, 7,101,
/* block 63 */
@@ -1929,7 +1928,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
/* block 67 */
- 19, 19, 19, 19, 19, 19, 19, 19, 8, 8, 8, 8, 19, 19, 19, 19,
+ 19, 19, 19, 19, 19, 19, 19, 19, 6, 7, 6, 7, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
8, 8, 19, 19, 19, 19, 19, 19, 19, 6, 7, 19, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
@@ -2353,30 +2352,30 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
516,516,516,516,516,516,516,516,516,516,516,516,516,516,516,516,
516,516,516,516,516,516,516,516,516,516,516,516,516,516,516,516,
516,516,516,514,515,515,514,514,514,514,515,515,514,515,515,515,
-515,517,517,517,517,517,517,517,517,517,517,517,517,517,109,518,
-519,519,519,519,519,519,519,519,519,519,109,109,109,109,517,517,
+515,517,517,517,517,517,517,517,517,517,517,517,517,517,109,102,
+518,518,518,518,518,518,518,518,518,518,109,109,109,109,517,517,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 110 */
-520,520,520,520,520,520,520,520,520,520,520,520,520,520,520,520,
-520,520,520,520,520,520,520,520,520,520,520,520,520,520,520,520,
-520,520,520,520,520,520,520,520,520,521,521,521,521,521,521,522,
-522,521,521,522,522,521,521,109,109,109,109,109,109,109,109,109,
-520,520,520,521,520,520,520,520,520,520,520,520,521,522,109,109,
-523,523,523,523,523,523,523,523,523,523,109,109,524,524,524,524,
+519,519,519,519,519,519,519,519,519,519,519,519,519,519,519,519,
+519,519,519,519,519,519,519,519,519,519,519,519,519,519,519,519,
+519,519,519,519,519,519,519,519,519,520,520,520,520,520,520,521,
+521,520,520,521,521,520,520,109,109,109,109,109,109,109,109,109,
+519,519,519,520,519,519,519,519,519,519,519,519,520,521,109,109,
+522,522,522,522,522,522,522,522,522,522,109,109,523,523,523,523,
295,295,295,295,295,295,295,295,295,295,295,295,295,295,295,295,
-525,295,295,295,295,295,295,301,301,301,295,296,109,109,109,109,
+524,295,295,295,295,295,295,301,301,301,295,296,109,109,109,109,
/* block 111 */
-526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,
-526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,
-526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,526,
-527,526,527,527,527,526,526,527,527,526,526,526,526,526,527,527,
-526,527,526,109,109,109,109,109,109,109,109,109,109,109,109,109,
-109,109,109,109,109,109,109,109,109,109,109,526,526,528,529,529,
-530,530,530,530,530,530,530,530,530,530,530,531,532,532,531,531,
-533,533,530,534,534,531,532,109,109,109,109,109,109,109,109,109,
+525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,
+525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,
+525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,525,
+526,525,526,526,526,525,525,526,526,525,525,525,525,525,526,526,
+525,526,525,109,109,109,109,109,109,109,109,109,109,109,109,109,
+109,109,109,109,109,109,109,109,109,109,109,525,525,527,528,528,
+529,529,529,529,529,529,529,529,529,529,529,530,531,531,530,530,
+532,532,529,533,533,530,531,109,109,109,109,109,109,109,109,109,
/* block 112 */
109,308,308,308,308,308,308,109,109,308,308,308,308,308,308,109,
@@ -2393,85 +2392,85 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
-530,530,530,530,530,530,530,530,530,530,530,530,530,530,530,530,
-530,530,530,530,530,530,530,530,530,530,530,530,530,530,530,530,
-530,530,530,531,531,532,531,531,532,531,531,533,531,532,109,109,
-535,535,535,535,535,535,535,535,535,535,109,109,109,109,109,109,
+529,529,529,529,529,529,529,529,529,529,529,529,529,529,529,529,
+529,529,529,529,529,529,529,529,529,529,529,529,529,529,529,529,
+529,529,529,530,530,531,530,530,531,530,530,532,530,531,109,109,
+534,534,534,534,534,534,534,534,534,534,109,109,109,109,109,109,
/* block 114 */
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
/* block 115 */
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
/* block 116 */
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
/* block 117 */
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
/* block 118 */
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
/* block 119 */
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
/* block 120 */
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-536,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,536,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,536,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+535,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,535,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,535,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
/* block 121 */
-537,537,537,537,537,537,537,537,536,537,537,537,537,537,537,537,
-537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
-537,537,537,537,109,109,109,109,109,109,109,109,109,109,109,109,
+536,536,536,536,536,536,536,536,535,536,536,536,536,536,536,536,
+536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,536,
+536,536,536,536,109,109,109,109,109,109,109,109,109,109,109,109,
306,306,306,306,306,306,306,306,306,306,306,306,306,306,306,306,
306,306,306,306,306,306,306,109,109,109,109,307,307,307,307,307,
307,307,307,307,307,307,307,307,307,307,307,307,307,307,307,307,
@@ -2479,6 +2478,16 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
307,307,307,307,307,307,307,307,307,307,307,307,109,109,109,109,
/* block 122 */
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,537,
+
+/* block 123 */
538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
@@ -2488,16 +2497,6 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
-/* block 123 */
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-
/* block 124 */
475,475,475,475,475,475,475,475,475,475,475,475,475,475,475,475,
475,475,475,475,475,475,475,475,475,475,475,475,475,475,475,475,
@@ -2521,7 +2520,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
/* block 126 */
33, 33, 33, 33, 33, 33, 33,109,109,109,109,109,109,109,109,109,
109,109,109,178,178,178,178,178,109,109,109,109,109,184,181,184,
-184,184,184,184,184,184,184,184,184,540,184,184,184,184,184,184,
+184,184,184,184,184,184,184,184,184,539,184,184,184,184,184,184,
184,184,184,184,184,184,184,109,184,184,184,184,184,109,184,109,
184,184,109,184,184,109,184,184,184,184,184,184,184,184,184,184,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
@@ -2532,8 +2531,8 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
-191,191,541,541,541,541,541,541,541,541,541,541,541,541,541,541,
-541,541,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
+191,191,540,540,540,540,540,540,540,540,540,540,540,540,540,540,
+540,540,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,191,191,191,191,191,191,191,191,191,191,191,191,191,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,191,
@@ -2600,7 +2599,7 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
/* block 134 */
469,469,469,469,469,469,469,469,469,469,469,469,469,469,469,469,
-469,469,469,469,469,469,469,469,469,469,469,469,469,469,542,542,
+469,469,469,469,469,469,469,469,469,469,469,469,469,469,541,541,
472,472,472,472,472,472,472,472,472,472,472,472,472,472,472,472,
472,472,472,472,472,472,472,472,472,472,472,472,472,472,472,109,
109,109,472,472,472,472,472,472,109,109,472,472,472,472,472,472,
@@ -2609,37 +2608,37 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
426,426,426,426,426,426,426,426,426, 22, 22, 22, 19, 19,109,109,
/* block 135 */
-543,543,543,543,543,543,543,543,543,543,543,543,109,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,109,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,109,543,543,109,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,109,109,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,109,109,
+542,542,542,542,542,542,542,542,542,542,542,542,109,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,109,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,109,542,542,109,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,109,109,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 136 */
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
-543,543,543,543,543,543,543,543,543,543,543,109,109,109,109,109,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,542,
+542,542,542,542,542,542,542,542,542,542,542,109,109,109,109,109,
/* block 137 */
4, 4, 4,109,109,109,109, 23, 23, 23, 23, 23, 23, 23, 23, 23,
23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23,
23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23,
23, 23, 23, 23,109,109,109, 19, 19, 19, 19, 19, 19, 19, 19, 19,
-544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,
-544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,
-544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,544,
-544,544,544,544,544,545,545,545,545,546,546,546,546,546,546,546,
+543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
+543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
+543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,543,
+543,543,543,543,543,544,544,544,544,545,545,545,545,545,545,545,
/* block 138 */
-546,546,546,546,546,546,546,546,546,546,545,109,109,109,109,109,
+545,545,545,545,545,545,545,545,545,545,544,109,109,109,109,109,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -2649,49 +2648,49 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,104,109,109,
/* block 139 */
+546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,
+546,546,546,546,546,546,546,546,546,546,546,546,546,109,109,109,
547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,
-547,547,547,547,547,547,547,547,547,547,547,547,547,109,109,109,
-548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,
-548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,
-548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,
-548,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
+547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,
+547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,547,
+547,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 140 */
-549,549,549,549,549,549,549,549,549,549,549,549,549,549,549,549,
-549,549,549,549,549,549,549,549,549,549,549,549,549,549,549,109,
-550,550,550,550,109,109,109,109,109,109,109,109,109,109,109,109,
-551,551,551,551,551,551,551,551,551,551,551,551,551,551,551,551,
-551,552,551,551,551,551,551,551,551,551,552,109,109,109,109,109,
+548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,
+548,548,548,548,548,548,548,548,548,548,548,548,548,548,548,109,
+549,549,549,549,109,109,109,109,109,109,109,109,109,109,109,109,
+550,550,550,550,550,550,550,550,550,550,550,550,550,550,550,550,
+550,551,550,550,550,550,550,550,550,550,551,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 141 */
-553,553,553,553,553,553,553,553,553,553,553,553,553,553,553,553,
-553,553,553,553,553,553,553,553,553,553,553,553,553,553,109,554,
-555,555,555,555,555,555,555,555,555,555,555,555,555,555,555,555,
-555,555,555,555,555,555,555,555,555,555,555,555,555,555,555,555,
-555,555,555,555,109,109,109,109,555,555,555,555,555,555,555,555,
-556,557,557,557,557,557,109,109,109,109,109,109,109,109,109,109,
+552,552,552,552,552,552,552,552,552,552,552,552,552,552,552,552,
+552,552,552,552,552,552,552,552,552,552,552,552,552,552,109,553,
+554,554,554,554,554,554,554,554,554,554,554,554,554,554,554,554,
+554,554,554,554,554,554,554,554,554,554,554,554,554,554,554,554,
+554,554,554,554,109,109,109,109,554,554,554,554,554,554,554,554,
+555,556,556,556,556,556,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 142 */
+557,557,557,557,557,557,557,557,557,557,557,557,557,557,557,557,
+557,557,557,557,557,557,557,557,557,557,557,557,557,557,557,557,
+557,557,557,557,557,557,557,557,558,558,558,558,558,558,558,558,
558,558,558,558,558,558,558,558,558,558,558,558,558,558,558,558,
558,558,558,558,558,558,558,558,558,558,558,558,558,558,558,558,
-558,558,558,558,558,558,558,558,559,559,559,559,559,559,559,559,
559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,
559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,
-560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,
-560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,
-560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,
+559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,559,
/* block 143 */
-561,561,561,561,561,561,561,561,561,561,561,561,561,561,561,561,
-561,561,561,561,561,561,561,561,561,561,561,561,561,561,109,109,
-562,562,562,562,562,562,562,562,562,562,109,109,109,109,109,109,
+560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,560,
+560,560,560,560,560,560,560,560,560,560,560,560,560,560,109,109,
+561,561,561,561,561,561,561,561,561,561,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -2699,61 +2698,61 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 144 */
-563,563,563,563,563,563,109,109,563,109,563,563,563,563,563,563,
+562,562,562,562,562,562,109,109,562,109,562,562,562,562,562,562,
+562,562,562,562,562,562,562,562,562,562,562,562,562,562,562,562,
+562,562,562,562,562,562,562,562,562,562,562,562,562,562,562,562,
+562,562,562,562,562,562,109,562,562,109,109,109,562,109,109,562,
563,563,563,563,563,563,563,563,563,563,563,563,563,563,563,563,
-563,563,563,563,563,563,563,563,563,563,563,563,563,563,563,563,
-563,563,563,563,563,563,109,563,563,109,109,109,563,109,109,563,
-564,564,564,564,564,564,564,564,564,564,564,564,564,564,564,564,
-564,564,564,564,564,564,109,565,566,566,566,566,566,566,566,566,
+563,563,563,563,563,563,109,564,565,565,565,565,565,565,565,565,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 145 */
-567,567,567,567,567,567,567,567,567,567,567,567,567,567,567,567,
-567,567,567,567,567,567,568,568,568,568,568,568,109,109,109,569,
-570,570,570,570,570,570,570,570,570,570,570,570,570,570,570,570,
-570,570,570,570,570,570,570,570,570,570,109,109,109,109,109,571,
+566,566,566,566,566,566,566,566,566,566,566,566,566,566,566,566,
+566,566,566,566,566,566,567,567,567,567,567,567,109,109,109,568,
+569,569,569,569,569,569,569,569,569,569,569,569,569,569,569,569,
+569,569,569,569,569,569,569,569,569,569,109,109,109,109,109,570,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 146 */
+571,571,571,571,571,571,571,571,571,571,571,571,571,571,571,571,
+571,571,571,571,571,571,571,571,571,571,571,571,571,571,571,571,
572,572,572,572,572,572,572,572,572,572,572,572,572,572,572,572,
-572,572,572,572,572,572,572,572,572,572,572,572,572,572,572,572,
-573,573,573,573,573,573,573,573,573,573,573,573,573,573,573,573,
-573,573,573,573,573,573,573,573,109,109,109,109,109,109,573,573,
+572,572,572,572,572,572,572,572,109,109,109,109,109,109,572,572,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 147 */
-574,575,575,575,109,575,575,109,109,109,109,109,575,575,575,575,
-574,574,574,574,109,574,574,574,109,574,574,574,574,574,574,574,
-574,574,574,574,574,574,574,574,574,574,574,574,574,574,574,574,
-574,574,574,574,109,109,109,109,575,575,575,109,109,109,109,575,
-576,576,576,576,576,576,576,576,109,109,109,109,109,109,109,109,
-577,577,577,577,577,577,577,577,577,109,109,109,109,109,109,109,
-578,578,578,578,578,578,578,578,578,578,578,578,578,578,578,578,
-578,578,578,578,578,578,578,578,578,578,578,578,578,579,579,580,
+573,574,574,574,109,574,574,109,109,109,109,109,574,574,574,574,
+573,573,573,573,109,573,573,573,109,573,573,573,573,573,573,573,
+573,573,573,573,573,573,573,573,573,573,573,573,573,573,573,573,
+573,573,573,573,109,109,109,109,574,574,574,109,109,109,109,574,
+575,575,575,575,575,575,575,575,109,109,109,109,109,109,109,109,
+576,576,576,576,576,576,576,576,576,109,109,109,109,109,109,109,
+577,577,577,577,577,577,577,577,577,577,577,577,577,577,577,577,
+577,577,577,577,577,577,577,577,577,577,577,577,577,578,578,579,
/* block 148 */
-581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,
-581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,
-581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,581,
-581,581,581,581,581,581,109,109,109,582,582,582,582,582,582,582,
-583,583,583,583,583,583,583,583,583,583,583,583,583,583,583,583,
-583,583,583,583,583,583,109,109,584,584,584,584,584,584,584,584,
-585,585,585,585,585,585,585,585,585,585,585,585,585,585,585,585,
-585,585,585,109,109,109,109,109,586,586,586,586,586,586,586,586,
+580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,
+580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,
+580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,580,
+580,580,580,580,580,580,109,109,109,581,581,581,581,581,581,581,
+582,582,582,582,582,582,582,582,582,582,582,582,582,582,582,582,
+582,582,582,582,582,582,109,109,583,583,583,583,583,583,583,583,
+584,584,584,584,584,584,584,584,584,584,584,584,584,584,584,584,
+584,584,584,109,109,109,109,109,585,585,585,585,585,585,585,585,
/* block 149 */
-587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,
-587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,
-587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,
-587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,
-587,587,587,587,587,587,587,587,587,109,109,109,109,109,109,109,
+586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,
+586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,
+586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,
+586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,586,
+586,586,586,586,586,586,586,586,586,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -2765,103 +2764,103 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
-588,588,588,588,588,588,588,588,588,588,588,588,588,588,588,588,
-588,588,588,588,588,588,588,588,588,588,588,588,588,588,588,109,
+587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,
+587,587,587,587,587,587,587,587,587,587,587,587,587,587,587,109,
/* block 151 */
-589,590,589,591,591,591,591,591,591,591,591,591,591,591,591,591,
-591,591,591,591,591,591,591,591,591,591,591,591,591,591,591,591,
-591,591,591,591,591,591,591,591,591,591,591,591,591,591,591,591,
-591,591,591,591,591,591,591,591,590,590,590,590,590,590,590,590,
-590,590,590,590,590,590,590,592,592,592,592,592,592,592,109,109,
-109,109,593,593,593,593,593,593,593,593,593,593,593,593,593,593,
-593,593,593,593,593,593,594,594,594,594,594,594,594,594,594,594,
+588,589,588,590,590,590,590,590,590,590,590,590,590,590,590,590,
+590,590,590,590,590,590,590,590,590,590,590,590,590,590,590,590,
+590,590,590,590,590,590,590,590,590,590,590,590,590,590,590,590,
+590,590,590,590,590,590,590,590,589,589,589,589,589,589,589,589,
+589,589,589,589,589,589,589,591,591,591,591,591,591,591,109,109,
+109,109,592,592,592,592,592,592,592,592,592,592,592,592,592,592,
+592,592,592,592,592,592,593,593,593,593,593,593,593,593,593,593,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 152 */
-595,595,596,597,597,597,597,597,597,597,597,597,597,597,597,597,
-597,597,597,597,597,597,597,597,597,597,597,597,597,597,597,597,
-597,597,597,597,597,597,597,597,597,597,597,597,597,597,597,597,
-596,596,596,595,595,595,595,596,596,595,595,598,598,599,598,598,
-598,598,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
-600,600,600,600,600,600,600,600,600,600,600,600,600,600,600,600,
-600,600,600,600,600,600,600,600,600,109,109,109,109,109,109,109,
-601,601,601,601,601,601,601,601,601,601,109,109,109,109,109,109,
+594,594,595,596,596,596,596,596,596,596,596,596,596,596,596,596,
+596,596,596,596,596,596,596,596,596,596,596,596,596,596,596,596,
+596,596,596,596,596,596,596,596,596,596,596,596,596,596,596,596,
+595,595,595,594,594,594,594,595,595,594,594,597,597,598,597,597,
+597,597,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
+599,599,599,599,599,599,599,599,599,599,599,599,599,599,599,599,
+599,599,599,599,599,599,599,599,599,109,109,109,109,109,109,109,
+600,600,600,600,600,600,600,600,600,600,109,109,109,109,109,109,
/* block 153 */
-602,602,602,603,603,603,603,603,603,603,603,603,603,603,603,603,
-603,603,603,603,603,603,603,603,603,603,603,603,603,603,603,603,
-603,603,603,603,603,603,603,602,602,602,602,602,604,602,602,602,
-602,602,602,602,602,109,605,605,605,605,605,605,605,605,605,605,
-606,606,606,606,109,109,109,109,109,109,109,109,109,109,109,109,
+601,601,601,602,602,602,602,602,602,602,602,602,602,602,602,602,
+602,602,602,602,602,602,602,602,602,602,602,602,602,602,602,602,
+602,602,602,602,602,602,602,601,601,601,601,601,603,601,601,601,
+601,601,601,601,601,109,604,604,604,604,604,604,604,604,604,604,
+605,605,605,605,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 154 */
-607,607,608,609,609,609,609,609,609,609,609,609,609,609,609,609,
-609,609,609,609,609,609,609,609,609,609,609,609,609,609,609,609,
-609,609,609,609,609,609,609,609,609,609,609,609,609,609,609,609,
-609,609,609,608,608,608,607,607,607,607,607,607,607,607,607,608,
-608,609,609,609,609,610,610,610,610,109,109,109,109,109,109,109,
-611,611,611,611,611,611,611,611,611,611,109,109,109,109,109,109,
+606,606,607,608,608,608,608,608,608,608,608,608,608,608,608,608,
+608,608,608,608,608,608,608,608,608,608,608,608,608,608,608,608,
+608,608,608,608,608,608,608,608,608,608,608,608,608,608,608,608,
+608,608,608,607,607,607,606,606,606,606,606,606,606,606,606,607,
+607,608,608,608,608,609,609,609,609,109,109,109,109,109,109,109,
+610,610,610,610,610,610,610,610,610,610,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 155 */
-612,612,612,612,612,612,612,612,612,612,612,612,612,612,612,612,
-612,612,612,612,612,612,612,612,612,612,612,612,612,612,612,612,
-612,612,612,612,612,612,612,612,612,612,612,613,614,613,614,614,
-613,613,613,613,613,613,614,613,109,109,109,109,109,109,109,109,
-615,615,615,615,615,615,615,615,615,615,109,109,109,109,109,109,
+611,611,611,611,611,611,611,611,611,611,611,611,611,611,611,611,
+611,611,611,611,611,611,611,611,611,611,611,611,611,611,611,611,
+611,611,611,611,611,611,611,611,611,611,611,612,613,612,613,613,
+612,612,612,612,612,612,613,612,109,109,109,109,109,109,109,109,
+614,614,614,614,614,614,614,614,614,614,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 156 */
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
/* block 157 */
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,
+615,615,615,615,615,615,615,615,615,615,615,615,615,615,615,109,
+109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
+
+/* block 158 */
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,
-616,616,616,616,616,616,616,616,616,616,616,616,616,616,616,109,
-109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
-
-/* block 158 */
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,617,
-617,617,617,109,109,109,109,109,109,109,109,109,109,109,109,109,
-618,618,618,618,109,109,109,109,109,109,109,109,109,109,109,109,
+616,616,616,109,109,109,109,109,109,109,109,109,109,109,109,109,
+617,617,617,617,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 159 */
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
/* block 160 */
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
-619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,109,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,
+618,618,618,618,618,618,618,618,618,618,618,618,618,618,618,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -2889,18 +2888,18 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 163 */
+619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
+619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
+619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
+619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,619,
+619,619,619,619,619,109,109,109,109,109,109,109,109,109,109,109,
+619,620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,
620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,
-620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,
-620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,
-620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,
-620,620,620,620,620,109,109,109,109,109,109,109,109,109,109,109,
-620,621,621,621,621,621,621,621,621,621,621,621,621,621,621,621,
-621,621,621,621,621,621,621,621,621,621,621,621,621,621,621,621,
-621,621,621,621,621,621,621,621,621,621,621,621,621,621,621,109,
+620,620,620,620,620,620,620,620,620,620,620,620,620,620,620,109,
/* block 164 */
-109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,622,
-622,622,622,623,623,623,623,623,623,623,623,623,623,623,623,623,
+109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,621,
+621,621,621,622,622,622,622,622,622,622,622,622,622,622,622,622,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -2935,8 +2934,8 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
- 19, 19, 19, 19, 19,624,395,104,104,104, 19, 19, 19,395,624,624,
-624,624,624, 22, 22, 22, 22, 22, 22, 22, 22,104,104,104,104,104,
+ 19, 19, 19, 19, 19,623,395,104,104,104, 19, 19, 19,395,623,623,
+623,623,623, 22, 22, 22, 22, 22, 22, 22, 22,104,104,104,104,104,
/* block 168 */
104,104,104, 19, 19,104,104,104,104,104,104,104, 19, 19, 19, 19,
@@ -2949,11 +2948,11 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
/* block 169 */
-546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,
-546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,
-546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,
-546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,546,
-546,546,625,625,625,546,109,109,109,109,109,109,109,109,109,109,
+545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,
+545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,
+545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,
+545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,545,
+545,545,624,624,624,545,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
@@ -3105,11 +3104,11 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,109,
-109,109,109,109,109,109,626,626,626,626,626,626,626,626,626,626,
-626,626,626,626,626,626,626,626,626,626,626,626,626,626,626,626,
+109,109,109,109,109,109,625,625,625,625,625,625,625,625,625,625,
+625,625,625,625,625,625,625,625,625,625,625,625,625,625,625,625,
/* block 185 */
-627, 19, 19,109,109,109,109,109,109,109,109,109,109,109,109,109,
+626, 19, 19,109,109,109,109,109,109,109,109,109,109,109,109,109,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,
19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19,109,109,109,109,109,
@@ -3279,14 +3278,14 @@ const pcre_uint16 PRIV(ucd_stage2)[] = { /* 51968 bytes, block = 128 */
426,426,426,426,426,426,426,426,426,426,426,426,426,426,426,426,
/* block 202 */
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,539,
-539,539,539,539,539,539,539,539,539,539,539,539,539,539,109,109,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,538,
+538,538,538,538,538,538,538,538,538,538,538,538,538,538,109,109,
};
diff --git a/ext/pcre/pcrelib/pcre_valid_utf8.c b/ext/pcre/pcrelib/pcre_valid_utf8.c
index a415927568..3b0f6464a3 100644
--- a/ext/pcre/pcrelib/pcre_valid_utf8.c
+++ b/ext/pcre/pcrelib/pcre_valid_utf8.c
@@ -6,7 +6,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -92,7 +92,7 @@ PCRE_UTF8_ERR18 Overlong 5-byte sequence (won't ever occur)
PCRE_UTF8_ERR19 Overlong 6-byte sequence (won't ever occur)
PCRE_UTF8_ERR20 Isolated 0x80 byte (not within UTF-8 character)
PCRE_UTF8_ERR21 Byte with the illegal value 0xfe or 0xff
-PCRE_UTF8_ERR22 Non-character
+PCRE_UTF8_ERR22 Unused (was non-character)
Arguments:
string points to the string
@@ -118,7 +118,6 @@ if (length < 0)
for (p = string; length-- > 0; p++)
{
register pcre_uchar ab, c, d;
- pcre_uint32 v = 0;
c = *p;
if (c < 128) continue; /* ASCII character */
@@ -187,7 +186,6 @@ for (p = string; length-- > 0; p++)
*erroroffset = (int)(p - string) - 2;
return PCRE_UTF8_ERR14;
}
- v = ((c & 0x0f) << 12) | ((d & 0x3f) << 6) | (*p & 0x3f);
break;
/* 4-byte character. Check 3rd and 4th bytes for 0x80. Then check first 2
@@ -215,7 +213,6 @@ for (p = string; length-- > 0; p++)
*erroroffset = (int)(p - string) - 3;
return PCRE_UTF8_ERR13;
}
- v = ((c & 0x07) << 18) | ((d & 0x3f) << 12) | ((p[-1] & 0x3f) << 6) | (*p & 0x3f);
break;
/* 5-byte and 6-byte characters are not allowed by RFC 3629, and will be
@@ -290,14 +287,6 @@ for (p = string; length-- > 0; p++)
*erroroffset = (int)(p - string) - ab;
return (ab == 4)? PCRE_UTF8_ERR11 : PCRE_UTF8_ERR12;
}
-
- /* Reject non-characters. The pointer p is currently at the last byte of the
- character. */
- if ((v & 0xfffeu) == 0xfffeu || (v >= 0xfdd0 && v <= 0xfdef))
- {
- *erroroffset = (int)(p - string) - ab;
- return PCRE_UTF8_ERR22;
- }
}
#else /* Not SUPPORT_UTF */
diff --git a/ext/pcre/pcrelib/pcre_xclass.c b/ext/pcre/pcrelib/pcre_xclass.c
index fa73cd8c9d..ad153be785 100644
--- a/ext/pcre/pcrelib/pcre_xclass.c
+++ b/ext/pcre/pcrelib/pcre_xclass.c
@@ -6,7 +6,7 @@
and semantics are as close as possible to those of the Perl 5 language.
Written by Philip Hazel
- Copyright (c) 1997-2012 University of Cambridge
+ Copyright (c) 1997-2013 University of Cambridge
-----------------------------------------------------------------------------
Redistribution and use in source and binary forms, with or without
@@ -128,55 +128,120 @@ while ((t = *data++) != XCL_END)
else /* XCL_PROP & XCL_NOTPROP */
{
const ucd_record *prop = GET_UCD(c);
+ BOOL isprop = t == XCL_PROP;
switch(*data)
{
case PT_ANY:
- if (t == XCL_PROP) return !negated;
+ if (isprop) return !negated;
break;
case PT_LAMP:
if ((prop->chartype == ucp_Lu || prop->chartype == ucp_Ll ||
- prop->chartype == ucp_Lt) == (t == XCL_PROP)) return !negated;
+ prop->chartype == ucp_Lt) == isprop) return !negated;
break;
case PT_GC:
- if ((data[1] == PRIV(ucp_gentype)[prop->chartype]) == (t == XCL_PROP))
+ if ((data[1] == PRIV(ucp_gentype)[prop->chartype]) == isprop)
return !negated;
break;
case PT_PC:
- if ((data[1] == prop->chartype) == (t == XCL_PROP)) return !negated;
+ if ((data[1] == prop->chartype) == isprop) return !negated;
break;
case PT_SC:
- if ((data[1] == prop->script) == (t == XCL_PROP)) return !negated;
+ if ((data[1] == prop->script) == isprop) return !negated;
break;
case PT_ALNUM:
if ((PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
- PRIV(ucp_gentype)[prop->chartype] == ucp_N) == (t == XCL_PROP))
+ PRIV(ucp_gentype)[prop->chartype] == ucp_N) == isprop)
return !negated;
break;
- case PT_SPACE: /* Perl space */
- if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_FF || c == CHAR_CR)
- == (t == XCL_PROP))
- return !negated;
- break;
+ /* Perl space used to exclude VT, but from Perl 5.18 it is included,
+ which means that Perl space and POSIX space are now identical. PCRE
+ was changed at release 8.34. */
+ case PT_SPACE: /* Perl space */
case PT_PXSPACE: /* POSIX space */
- if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z ||
- c == CHAR_HT || c == CHAR_NL || c == CHAR_VT ||
- c == CHAR_FF || c == CHAR_CR) == (t == XCL_PROP))
- return !negated;
+ switch(c)
+ {
+ HSPACE_CASES:
+ VSPACE_CASES:
+ if (isprop) return !negated;
+ break;
+
+ default:
+ if ((PRIV(ucp_gentype)[prop->chartype] == ucp_Z) == isprop)
+ return !negated;
+ break;
+ }
break;
case PT_WORD:
if ((PRIV(ucp_gentype)[prop->chartype] == ucp_L ||
PRIV(ucp_gentype)[prop->chartype] == ucp_N || c == CHAR_UNDERSCORE)
- == (t == XCL_PROP))
+ == isprop)
+ return !negated;
+ break;
+
+ case PT_UCNC:
+ if (c < 0xa0)
+ {
+ if ((c == CHAR_DOLLAR_SIGN || c == CHAR_COMMERCIAL_AT ||
+ c == CHAR_GRAVE_ACCENT) == isprop)
+ return !negated;
+ }
+ else
+ {
+ if ((c < 0xd800 || c > 0xdfff) == isprop)
+ return !negated;
+ }
+ break;
+
+ /* The following three properties can occur only in an XCLASS, as there
+ is no \p or \P coding for them. */
+
+ /* Graphic character. Implement this as not Z (space or separator) and
+ not C (other), except for Cf (format) with a few exceptions. This seems
+ to be what Perl does. The exceptional characters are:
+
+ U+061C Arabic Letter Mark
+ U+180E Mongolian Vowel Separator
+ U+2066 - U+2069 Various "isolate"s
+ */
+
+ case PT_PXGRAPH:
+ if ((PRIV(ucp_gentype)[prop->chartype] != ucp_Z &&
+ (PRIV(ucp_gentype)[prop->chartype] != ucp_C ||
+ (prop->chartype == ucp_Cf &&
+ c != 0x061c && c != 0x180e && (c < 0x2066 || c > 0x2069))
+ )) == isprop)
+ return !negated;
+ break;
+
+ /* Printable character: same as graphic, with the addition of Zs, i.e.
+ not Zl and not Zp, and U+180E. */
+
+ case PT_PXPRINT:
+ if ((prop->chartype != ucp_Zl &&
+ prop->chartype != ucp_Zp &&
+ (PRIV(ucp_gentype)[prop->chartype] != ucp_C ||
+ (prop->chartype == ucp_Cf &&
+ c != 0x061c && (c < 0x2066 || c > 0x2069))
+ )) == isprop)
+ return !negated;
+ break;
+
+ /* Punctuation: all Unicode punctuation, plus ASCII characters that
+ Unicode treats as symbols rather than punctuation, for Perl
+ compatibility (these are $+<=>^`|~). */
+
+ case PT_PXPUNCT:
+ if ((PRIV(ucp_gentype)[prop->chartype] == ucp_P ||
+ (c < 256 && PRIV(ucp_gentype)[prop->chartype] == ucp_S)) == isprop)
return !negated;
break;
diff --git a/ext/pcre/pcrelib/pcreposix.c b/ext/pcre/pcrelib/pcreposix.c
index 15195c0e98..7cf4a4a657 100644
--- a/ext/pcre/pcrelib/pcreposix.c
+++ b/ext/pcre/pcrelib/pcreposix.c
@@ -110,7 +110,7 @@ static const int eint[] = {
REG_BADPAT, /* POSIX collating elements are not supported */
REG_INVARG, /* this version of PCRE is not compiled with PCRE_UTF8 support */
REG_BADPAT, /* spare error */
- REG_BADPAT, /* character value in \x{...} sequence is too large */
+ REG_BADPAT, /* character value in \x{} or \o{} is too large */
/* 35 */
REG_BADPAT, /* invalid condition (?(0) */
REG_BADPAT, /* \C not allowed in lookbehind assertion */
@@ -162,7 +162,15 @@ static const int eint[] = {
/* 75 */
REG_BADPAT, /* overlong MARK name */
REG_BADPAT, /* character value in \u.... sequence is too large */
- REG_BADPAT /* invalid UTF-32 string (should not occur) */
+ REG_BADPAT, /* invalid UTF-32 string (should not occur) */
+ REG_BADPAT, /* setting UTF is disabled by the application */
+ REG_BADPAT, /* non-hex character in \\x{} (closing brace missing?) */
+ /* 80 */
+ REG_BADPAT, /* non-octal character in \o{} (closing brace missing?) */
+ REG_BADPAT, /* missing opening brace after \o */
+ REG_BADPAT, /* parentheses too deeply nested */
+ REG_BADPAT, /* invalid range in character class */
+ REG_BADPAT /* group name must start with a non-digit */
};
/* Table of texts corresponding to POSIX error codes */
diff --git a/ext/pcre/pcrelib/testdata/grepbinary b/ext/pcre/pcrelib/testdata/grepbinary
new file mode 100644
index 0000000000..5efa130204
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/grepbinary
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/grepfilelist b/ext/pcre/pcrelib/testdata/grepfilelist
new file mode 100644
index 0000000000..dd73ec7f91
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/grepfilelist
@@ -0,0 +1,3 @@
+testdata/grepinputv
+
+testdata/grepinputx
diff --git a/ext/pcre/pcrelib/testdata/grepinput3 b/ext/pcre/pcrelib/testdata/grepinput3
new file mode 100644
index 0000000000..7409cfc07a
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/grepinput3
@@ -0,0 +1,15 @@
+triple: t1_txt s1_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t2_txt s1_tag s_txt p_tag p_txt o_tag
+Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.
+
+triple: t3_txt s2_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t4_txt s1_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t5_txt s1_tag s_txt p_tag p_txt o_tag
+o_txt
+
+triple: t6_txt s2_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t7_txt s1_tag s_txt p_tag p_txt o_tag o_txt
diff --git a/ext/pcre/pcrelib/testdata/grepinput8 b/ext/pcre/pcrelib/testdata/grepinput8
index 7163aa69d3..c4b8c440f2 100644
--- a/ext/pcre/pcrelib/testdata/grepinput8
+++ b/ext/pcre/pcrelib/testdata/grepinput8
@@ -1,10 +1,10 @@
X one
-X two X three X four X five
+X two X three X four X five
X six
X seven…X eight
X nine
X ten
Before 111
-Before 222
Before 333…Match
+Before 222
Before 333…Match
After 111
After 222
After 333
And so on and so on
diff --git a/ext/pcre/pcrelib/testdata/grepinputv b/ext/pcre/pcrelib/testdata/grepinputv
new file mode 100644
index 0000000000..d33d326b01
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/grepinputv
@@ -0,0 +1,4 @@
+The quick brown
+fox jumps
+over the lazy dog.
+This time it jumps and jumps and jumps.
diff --git a/ext/pcre/pcrelib/testdata/grepoutput b/ext/pcre/pcrelib/testdata/grepoutput
index 733b9d6a3b..9bf9d9d62e 100644
--- a/ext/pcre/pcrelib/testdata/grepoutput
+++ b/ext/pcre/pcrelib/testdata/grepoutput
@@ -705,3 +705,41 @@ RC=0
./testdata/grepinput:zero|a
./testdata/grepinput:.|zero|the|.
RC=0
+---------------------------- Test 102 -----------------------------
+2:
+5:
+7:
+9:
+12:
+14:
+RC=0
+---------------------------- Test 103 -----------------------------
+RC=0
+---------------------------- Test 104 -----------------------------
+2:
+5:
+7:
+9:
+12:
+14:
+RC=0
+---------------------------- Test 105 -----------------------------
+triple: t1_txt s1_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t2_txt s1_tag s_txt p_tag p_txt o_tag
+Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.
+
+triple: t3_txt s2_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t4_txt s1_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t5_txt s1_tag s_txt p_tag p_txt o_tag
+o_txt
+
+triple: t6_txt s2_tag s_txt p_tag p_txt o_tag o_txt
+
+triple: t7_txt s1_tag s_txt p_tag p_txt o_tag o_txt
+RC=0
+---------------------------- Test 106 -----------------------------
+a
+RC=0
diff --git a/ext/pcre/pcrelib/testdata/grepoutput8 b/ext/pcre/pcrelib/testdata/grepoutput8
index 385266b3cf..91493bdcf0 100644
--- a/ext/pcre/pcrelib/testdata/grepoutput8
+++ b/ext/pcre/pcrelib/testdata/grepoutput8
@@ -1,12 +1,12 @@
---------------------------- Test U1 ------------------------------
1:X one
-2:X two 3:X three 4:X four 5:X five
+2:X two 3:X three 4:X four 5:X five
6:X six
7:X seven…8:X eight
9:X nine
10:X ten
RC=0
---------------------------- Test U2 ------------------------------
12-Before 111
-13-Before 222
14-Before 333…15:Match
+13-Before 222
14-Before 333…15:Match
16-After 111
17-After 222
18-After 333
RC=0
diff --git a/ext/pcre/pcrelib/testdata/grepoutputN b/ext/pcre/pcrelib/testdata/grepoutputN
index 6760314aa2..1f9f8801e3 100644
--- a/ext/pcre/pcrelib/testdata/grepoutputN
+++ b/ext/pcre/pcrelib/testdata/grepoutputN
@@ -1,16 +1,16 @@
----------------------------- Test N1 ------------------------------
-1:abc 2:def ---------------------------- Test N2 ------------------------------
-1:abc def
+---------------------------- Test N1 ------------------------------
+1:abc 2:def ---------------------------- Test N2 ------------------------------
+1:abc def
2:ghi
-jkl---------------------------- Test N3 ------------------------------
+jkl---------------------------- Test N3 ------------------------------
2:def 3:
ghi
-jkl---------------------------- Test N4 ------------------------------
+jkl---------------------------- Test N4 ------------------------------
2:ghi
-jkl---------------------------- Test N5 ------------------------------
-1:abc 2:def
+jkl---------------------------- Test N5 ------------------------------
+1:abc 2:def
3:ghi
-4:jkl---------------------------- Test N6 ------------------------------
-1:abc 2:def
+4:jkl---------------------------- Test N6 ------------------------------
+1:abc 2:def
3:ghi
4:jkl \ No newline at end of file
diff --git a/ext/pcre/pcrelib/testdata/greppatN4 b/ext/pcre/pcrelib/testdata/greppatN4
new file mode 100644
index 0000000000..7112d84fa1
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/greppatN4
@@ -0,0 +1,2 @@
+xxx
+jkl \ No newline at end of file
diff --git a/ext/pcre/pcrelib/testdata/saved16 b/ext/pcre/pcrelib/testdata/saved16
new file mode 100644
index 0000000000..f86326c9f8
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved16
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved16BE-1 b/ext/pcre/pcrelib/testdata/saved16BE-1
new file mode 100644
index 0000000000..e6edddc6e0
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved16BE-1
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved16BE-2 b/ext/pcre/pcrelib/testdata/saved16BE-2
new file mode 100644
index 0000000000..c91ce37bd4
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved16BE-2
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved16LE-1 b/ext/pcre/pcrelib/testdata/saved16LE-1
new file mode 100644
index 0000000000..5035ec0721
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved16LE-1
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved16LE-2 b/ext/pcre/pcrelib/testdata/saved16LE-2
new file mode 100644
index 0000000000..656c058d26
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved16LE-2
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved32 b/ext/pcre/pcrelib/testdata/saved32
new file mode 100644
index 0000000000..a4e27041ce
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved32
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved32BE-1 b/ext/pcre/pcrelib/testdata/saved32BE-1
new file mode 100644
index 0000000000..b4c2ffe42c
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved32BE-1
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved32BE-2 b/ext/pcre/pcrelib/testdata/saved32BE-2
new file mode 100644
index 0000000000..79bb5e8805
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved32BE-2
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved32LE-1 b/ext/pcre/pcrelib/testdata/saved32LE-1
new file mode 100644
index 0000000000..49392b89a1
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved32LE-1
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved32LE-2 b/ext/pcre/pcrelib/testdata/saved32LE-2
new file mode 100644
index 0000000000..5f64af9b9d
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved32LE-2
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/saved8 b/ext/pcre/pcrelib/testdata/saved8
new file mode 100644
index 0000000000..8cf0c1312d
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/saved8
Binary files differ
diff --git a/ext/pcre/pcrelib/testdata/testinput1 b/ext/pcre/pcrelib/testdata/testinput1
index e6d048ad8c..7b36360d04 100644
--- a/ext/pcre/pcrelib/testdata/testinput1
+++ b/ext/pcre/pcrelib/testdata/testinput1
@@ -1,6 +1,8 @@
/-- This set of tests is for features that are compatible with all versions of
- Perl >= 5.10, in non-UTF-8 mode. It should run clean for both the 8-bit and
- 16-bit PCRE libraries. --/
+ Perl >= 5.10, in non-UTF-8 mode. It should run clean for the 8-bit, 16-bit,
+ and 32-bit PCRE libraries. --/
+
+< forbid 89?=ABCDEFfGILMNPTUWXZ<
/the quick brown fox/
the quick brown fox
@@ -1483,14 +1485,19 @@
abc\100\x30
abc\100\060
abc\100\60
+
+/^A\8B\9C$/
+ A8B9C
+ *** Failers
+ A\08B\09C
+
+/^(A)(B)(C)(D)(E)(F)(G)(H)(I)\8\9$/
+ ABCDEFGHIHI
-/abc\81/
- abc\081
- abc\0\x38\x31
-
-/abc\91/
- abc\091
- abc\0\x39\x31
+/^[A\8B\9C]+$/
+ A8B9C
+ *** Failers
+ A8B9C\x00
/(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k)(l)\12\123/
abcdefghijkllS
@@ -3654,13 +3661,6 @@
/a*/g
abbab
-/^[a-\d]/
- abcde
- -things
- 0digit
- *** Failers
- bcdef
-
/^[\d-a]/
abcde
-things
@@ -3773,9 +3773,9 @@
abc123abc
abc123bc
-/-- This tests for an IPv6 address in the form where it can have up to --/
-/-- eight components, one and only one of which is empty. This must be --/
-/-- an internal component. --/
+/-- This tests for an IPv6 address in the form where it can have up to
+ eight components, one and only one of which is empty. This must be
+ an internal component. --/
/^(?!:) # colon disallowed at start
(?: # start of item
@@ -4221,9 +4221,6 @@
ab
bc
-/^(?=(a)){0}b(?1)/
- backgammon
-
/^(?=(?1))?[az]([abc])d/
abd
zcdxx
@@ -4656,16 +4653,10 @@
/(?<pn> \( ( [^()]++ | (?&pn) )* \) )/x
(ab(cd)ef)
-/^(?!a(*SKIP)b)/
- ac
-
/^(?=a(*SKIP)b|ac)/
** Failers
ac
-/^(?=a(*THEN)b|ac)/
- ac
-
/^(?=a(*PRUNE)b)/
ab
** Failers
@@ -4674,9 +4665,6 @@
/^(?=a(*ACCEPT)b)/
ac
-/^(?(?!a(*SKIP)b))/
- ac
-
/(?>a\Kb)/
ab
@@ -4899,33 +4887,15 @@ however, we need the complication for Perl. ---/
/(A (A|B(*ACCEPT)|C) D)(E)/x
AB
-/\A.*?(?:a|b(*THEN)c)/
- ba
-
-/\A.*?(?:a|bc)/
- ba
-
-/\A.*?(a|b(*THEN)c)/
- ba
-
/\A.*?(a|bc)/
ba
-/\A.*?(?:a|b(*THEN)c)++/
- ba
-
/\A.*?(?:a|bc)++/
ba
-/\A.*?(a|b(*THEN)c)++/
- ba
-
/\A.*?(a|bc)++/
ba
-/\A.*?(?:a|b(*THEN)c|d)/
- ba
-
/\A.*?(?:a|bc|d)/
ba
@@ -5253,9 +5223,6 @@ name were given. ---/
/(a(*COMMIT)b){0}a(?1)|aac/
aac
-/(?!a(*COMMIT)b)ac|cd/
- ac
-
/((?:a?)*)*c/
aac
@@ -5303,4 +5270,400 @@ name were given. ---/
"(?>.*?)foo"
abcdfooxyz
+/(?:(a(*PRUNE)b)){0}(?:(?1)|ac)/
+ ac
+
+/(?:(a(*SKIP)b)){0}(?:(?1)|ac)/
+ ac
+
+/(?<=(*SKIP)ac)a/
+ aa
+
+/A(*MARK:A)A+(*SKIP:B)(B|Z) | AC/xK
+ AAAC
+
+/a(*SKIP:m)x|ac(*:n)(*SKIP:n)d|ac/K
+ acacd
+
+/A(*SKIP:m)x|A(*SKIP:n)x|AB/K
+ AB
+
+/((*SKIP:r)d){0}a(*SKIP:m)x|ac(*:n)|ac/K
+ acacd
+
+/-- Tests that try to figure out how Perl works. My hypothesis is that the
+ first verb that is backtracked onto is the one that acts. This seems to be
+ the case almost all the time, but there is one exception that is perhaps a
+ bug. --/
+
+/-- This matches "aaaac"; each PRUNE advances one character until the subject
+ no longer starts with 5 'a's. --/
+
+/aaaaa(*PRUNE)b|a+c/
+ aaaaaac
+
+/-- Putting SKIP in front of PRUNE makes no difference, as it is never
+backtracked onto, whether or not it has a label. --/
+
+/aaaaa(*SKIP)(*PRUNE)b|a+c/
+ aaaaaac
+
+/aaaaa(*SKIP:N)(*PRUNE)b|a+c/
+ aaaaaac
+
+/aaaa(*:N)a(*SKIP:N)(*PRUNE)b|a+c/
+ aaaaaac
+
+/-- Putting THEN in front makes no difference. */
+
+/aaaaa(*THEN)(*PRUNE)b|a+c/
+ aaaaaac
+
+/-- However, putting COMMIT in front of the prune changes it to "no match". I
+ think this is inconsistent and possibly a bug. For the moment, running this
+ test is moved out of the Perl-compatible file. --/
+
+/aaaaa(*COMMIT)(*PRUNE)b|a+c/
+
+
+/---- OK, lets play the same game again using SKIP instead of PRUNE. ----/
+
+/-- This matches "ac" because SKIP forces the next match to start on the
+ sixth "a". --/
+
+/aaaaa(*SKIP)b|a+c/
+ aaaaaac
+
+/-- Putting PRUNE in front makes no difference. --/
+
+/aaaaa(*PRUNE)(*SKIP)b|a+c/
+ aaaaaac
+
+/-- Putting THEN in front makes no difference. --/
+
+/aaaaa(*THEN)(*SKIP)b|a+c/
+ aaaaaac
+
+/-- In this case, neither does COMMIT. This still matches "ac". --/
+
+/aaaaa(*COMMIT)(*SKIP)b|a+c/
+ aaaaaac
+
+/-- This gives "no match", as expected. --/
+
+/aaaaa(*COMMIT)b|a+c/
+ aaaaaac
+
+
+/------ Tests using THEN ------/
+
+/-- This matches "aaaaaac", as expected. --/
+
+/aaaaa(*THEN)b|a+c/
+ aaaaaac
+
+/-- Putting SKIP in front makes no difference. --/
+
+/aaaaa(*SKIP)(*THEN)b|a+c/
+ aaaaaac
+
+/-- Putting PRUNE in front makes no difference. --/
+
+/aaaaa(*PRUNE)(*THEN)b|a+c/
+ aaaaaac
+
+/-- Putting COMMIT in front makes no difference. --/
+
+/aaaaa(*COMMIT)(*THEN)b|a+c/
+ aaaaaac
+
+/-- End of "priority" tests --/
+
+/aaaaa(*:m)(*PRUNE:m)(*SKIP:m)m|a+/
+ aaaaaa
+
+/aaaaa(*:m)(*MARK:m)(*PRUNE)(*SKIP:m)m|a+/
+ aaaaaa
+
+/aaaaa(*:n)(*PRUNE:m)(*SKIP:m)m|a+/
+ aaaaaa
+
+/aaaaa(*:n)(*MARK:m)(*PRUNE)(*SKIP:m)m|a+/
+ aaaaaa
+
+/a(*MARK:A)aa(*PRUNE:A)a(*SKIP:A)b|a+c/
+ aaaac
+
+/a(*MARK:A)aa(*MARK:A)a(*SKIP:A)b|a+c/
+ aaaac
+
+/aaa(*PRUNE:A)a(*SKIP:A)b|a+c/
+ aaaac
+
+/aaa(*MARK:A)a(*SKIP:A)b|a+c/
+ aaaac
+
+/a(*:m)a(*COMMIT)(*SKIP:m)b|a+c/K
+ aaaaaac
+
+/.?(a|b(*THEN)c)/
+ ba
+
+/(a(*COMMIT)b)c|abd/
+ abc
+ abd
+
+/(?=a(*COMMIT)b)abc|abd/
+ abc
+ abd
+
+/(?>a(*COMMIT)b)c|abd/
+ abc
+ abd
+
+/a(?=b(*COMMIT)c)[^d]|abd/
+ abd
+ abc
+
+/a(?=bc).|abd/
+ abd
+ abc
+
+/a(?>b(*COMMIT)c)d|abd/
+ abceabd
+
+/a(?>bc)d|abd/
+ abceabd
+
+/(?>a(*COMMIT)b)c|abd/
+ abd
+
+/(?>a(*COMMIT)c)d|abd/
+ abd
+
+/((?=a(*COMMIT)b)ab|ac){0}(?:(?1)|a(c))/
+ ac
+
+/-- These tests were formerly in test 2, but changes in PCRE and Perl have
+ made them compatible. --/
+
+/^(a)?(?(1)a|b)+$/
+ *** Failers
+ a
+
+/(?=a\Kb)ab/
+ ab
+
+/(?!a\Kb)ac/
+ ac
+
+/^abc(?<=b\Kc)d/
+ abcd
+
+/^abc(?<!b\Kq)d/
+ abcd
+
+
+/A(*PRUNE:A)A+(*SKIP:A)(B|Z) | AC/xK
+ AAAC
+
+/^((abc|abcx)(*THEN)y|abcd)/
+ abcd
+ *** Failers
+ abcxy
+
+/^((yes|no)(*THEN)(*F))?/
+ yes
+
+/(A (.*) C? (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+
+/(A (.*) C? (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+
+/(A (.*) C? (*THEN) | A D) \s* (*FAIL)/x
+AbcdCBefgBhiBqz
+
+/(A (.*) C? (*THEN) | A D) \s* z/x
+AbcdCBefgBhiBqz
+
+/(A (.*) (?:C|) (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+
+/(A (.*) (?:C|) (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+
+/(A (.*) C{0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+
+/(A (.*) C{0,6} (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+
+/(A (.*) (CE){0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCEBefgBhiBqz
+
+/(A (.*) (CE){0,6} (*THEN) | A D) z/x
+AbcdCEBefgBhiBqz
+
+/(A (.*) (CE*){0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+
+/(A (.*) (CE*){0,6} (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+
+/(?=a(*COMMIT)b|ac)ac|ac/
+ ac
+
+/(?=a(*COMMIT)b|(ac)) ac | (a)c/x
+ ac
+
+/--------/
+
+/(?(?!b(*THEN)a)bn|bnn)/
+ bnn
+
+/(?!b(*SKIP)a)bn|bnn/
+ bnn
+
+/(?(?!b(*SKIP)a)bn|bnn)/
+ bnn
+
+/(?!b(*PRUNE)a)bn|bnn/
+ bnn
+
+/(?(?!b(*PRUNE)a)bn|bnn)/
+ bnn
+
+/(?!b(*COMMIT)a)bn|bnn/
+ bnn
+
+/(?(?!b(*COMMIT)a)bn|bnn)/
+ bnn
+
+/(?=b(*SKIP)a)bn|bnn/
+ bnn
+
+/(?=b(*THEN)a)bn|bnn/
+ bnn
+
+ /^(?!a(*SKIP)b)/
+ ac
+
+ /^(?!a(*SKIP)b)../
+ acd
+
+/(?!a(*SKIP)b)../
+ acd
+
+/^(?(?!a(*SKIP)b))/
+ ac
+
+/^(?!a(*PRUNE)b)../
+ acd
+
+/(?!a(*PRUNE)b)../
+ acd
+
+ /(?!a(*COMMIT)b)ac|cd/
+ ac
+
+/\A.*?(?:a|bc)/
+ ba
+
+/^(A(*THEN)B|C(*THEN)D)/
+ CD
+
+/(*:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+
+/(*PRUNE:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+
+/(*SKIP:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+
+/(*THEN:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+
+/^\d*\w{4}/
+ 1234
+ 123
+
+/^[^b]*\w{4}/
+ aaaa
+ aaa
+
+/^[^b]*\w{4}/i
+ aaaa
+ aaa
+
+/^a*\w{4}/
+ aaaa
+ aaa
+
+/^a*\w{4}/i
+ aaaa
+ aaa
+
+/(?(?=ab)ab)/+
+ ca
+ cd
+
+/(?:(?<n>foo)|(?<n>bar))\k<n>/J
+ foofoo
+ barbar
+
+/(?<n>A)(?:(?<n>foo)|(?<n>bar))\k<n>/J
+ AfooA
+ AbarA
+ ** Failers
+ Afoofoo
+ Abarbar
+
+/^(\d+)\s+IN\s+SOA\s+(\S+)\s+(\S+)\s*\(\s*$/
+ 1 IN SOA non-sp1 non-sp2(
+
+/^ (?:(?<A>A)|(?'B'B)(?<A>A)) (?('A')x) (?(<B>)y)$/xJ
+ Ax
+ BAxy
+
+/^A\xZ/
+ A\0Z
+
+/^A\o{123}B/
+ A\123B
+
+/ ^ a + + b $ /x
+ aaaab
+
+/ ^ a + #comment
+ + b $ /x
+ aaaab
+
+/ ^ a + #comment
+ #comment
+ + b $ /x
+ aaaab
+
+/ ^ (?> a + ) b $ /x
+ aaaab
+
+/ ^ ( a + ) + + \w $ /x
+ aaaab
+
+/(?:a\Kb)*+/+
+ ababc
+
+/(?>a\Kb)*/+
+ ababc
+
+/(?:a\Kb)*/+
+ ababc
+
+/(a\Kb)*+/+
+ ababc
+
+/(a\Kb)*/+
+ ababc
+
/-- End of testinput1 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput10 b/ext/pcre/pcrelib/testdata/testinput10
index f20dcb3d18..93ddb3a75b 100644
--- a/ext/pcre/pcrelib/testdata/testinput10
+++ b/ext/pcre/pcrelib/testdata/testinput10
@@ -139,6 +139,12 @@
/^\p{Cf}/8
\x{601}
+ \x{180e}
+ \x{061c}
+ \x{2066}
+ \x{2067}
+ \x{2068}
+ \x{2069}
** Failers
\x{09f}
@@ -199,11 +205,12 @@
/^\p{Mn}/8
\x{300}
+ \x{1a1b}
** Failers
X
\x{903}
-/^\p{Nd}+/8
+/^\p{Nd}+/8O
0123456789\x{660}\x{661}\x{662}\x{663}\x{664}\x{665}\x{666}\x{667}\x{668}\x{669}\x{66a}
\x{6f0}\x{6f1}\x{6f2}\x{6f3}\x{6f4}\x{6f5}\x{6f6}\x{6f7}\x{6f8}\x{6f9}\x{6fa}
\x{966}\x{967}\x{968}\x{969}\x{96a}\x{96b}\x{96c}\x{96d}\x{96e}\x{96f}\x{970}
@@ -243,6 +250,8 @@
]
}
\x{f3b}
+ \x{2309}
+ \x{230b}
** Failers
X
\x{203f}
@@ -250,7 +259,7 @@
[
{
\x{f3c}
-
+
/^\p{Pf}/8
\x{bb}
\x{2019}
@@ -277,6 +286,8 @@
[
{
\x{f3c}
+ \x{2308}
+ \x{230a}
** Failers
X
)
@@ -326,7 +337,6 @@
\ \
\x{a0}
\x{1680}
- \x{180e}
\x{2000}
\x{2001}
** Failers
@@ -423,23 +433,23 @@
** Failers
1234
-/\D+/8
+/\D+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/\P{Nd}+/8
+/\P{Nd}+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\D]+/8
+/[\D]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\P{Nd}]+/8
+/[\P{Nd}]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\D\P{Nd}]+/8
+/[\D\P{Nd}]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -886,19 +896,19 @@
** Failers
\x{0b}
-/^>\p{Xsp}+/8
+/^>\p{Xsp}+/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
-/^>\p{Xsp}*/8
+/^>\p{Xsp}*/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
-/^>\p{Xsp}{2,9}/8
+/^>\p{Xsp}{2,9}/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
-/^>[\p{Xsp}]/8
+/^>[\p{Xsp}]/8O
>\x{2028}\x{0b}
-/^>[\p{Xsp}]+/8
+/^>[\p{Xsp}]+/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
/^>\p{Xps}/8
@@ -1334,4 +1344,76 @@
/is{2}t/8i
iskt
+/^\p{Xuc}/8
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+ ** Failers
+ abc
+
+/^\p{Xuc}+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}+?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}+?\*/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}++/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}{3,5}/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}{3,5}?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^[\p{Xuc}]/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^[\p{Xuc}]+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\P{Xuc}/8
+ abc
+ ** Failers
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+
+/^[\P{Xuc}]/8
+ abc
+ ** Failers
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+
+/^A\s+Z/8W
+ A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+
+/^A[\s]+Z/8W
+ A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+
/-- End of testinput10 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput11 b/ext/pcre/pcrelib/testdata/testinput11
new file mode 100644
index 0000000000..391ada7aa8
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput11
@@ -0,0 +1,135 @@
+/-- These are a few representative patterns whose lengths and offsets are to be
+shown when the link size is 2. This is just a doublecheck test to ensure the
+sizes don't go horribly wrong when something is changed. The pattern contents
+are all themselves checked in other tests. Unicode, including property support,
+is required for these tests. --/
+
+/((?i)b)/BM
+
+/(?s)(.*X|^B)/BM
+
+/(?s:.*X|^B)/BM
+
+/^[[:alnum:]]/BM
+
+/#/IxMD
+
+/a#/IxMD
+
+/x?+/BM
+
+/x++/BM
+
+/x{1,3}+/BM
+
+/(x)*+/BM
+
+/^((a+)(?U)([ab]+)(?-U)([bc]+)(\w*))/BM
+
+|8J\$WE\<\.rX\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+
+|\$\<\.X\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+
+/(a(?1)b)/BM
+
+/(a(?1)+b)/BM
+
+/a(?P<name1>b|c)d(?P<longername2>e)/BM
+
+/(?:a(?P<c>c(?P<d>d)))(?P<a>a)/BM
+
+/(?P<a>a)...(?P=a)bbb(?P>a)d/BM
+
+/abc(?C255)de(?C)f/BM
+
+/abcde/CBM
+
+/\x{100}/8BM
+
+/\x{1000}/8BM
+
+/\x{10000}/8BM
+
+/\x{100000}/8BM
+
+/\x{10ffff}/8BM
+
+/\x{110000}/8BM
+
+/[\x{ff}]/8BM
+
+/[\x{100}]/8BM
+
+/\x80/8BM
+
+/\xff/8BM
+
+/\x{0041}\x{2262}\x{0391}\x{002e}/D8M
+
+/\x{D55c}\x{ad6d}\x{C5B4}/D8M
+
+/\x{65e5}\x{672c}\x{8a9e}/D8M
+
+/[\x{100}]/8BM
+
+/[Z\x{100}]/8BM
+
+/^[\x{100}\E-\Q\E\x{150}]/B8M
+
+/^[\QÄ€\E-\QÅ\E]/B8M
+
+/^[\QÄ€\E-\QÅ\E/B8M
+
+/[\p{L}]/BM
+
+/[\p{^L}]/BM
+
+/[\P{L}]/BM
+
+/[\P{^L}]/BM
+
+/[abc\p{L}\x{0660}]/8BM
+
+/[\p{Nd}]/8BM
+
+/[\p{Nd}+-]+/8BM
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iBM
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8BM
+
+/[\x{105}-\x{109}]/8iBM
+
+/( ( (?(1)0|) )* )/xBM
+
+/( (?(1)0|)* )/xBM
+
+/[a]/BM
+
+/[a]/8BM
+
+/[\xaa]/BM
+
+/[\xaa]/8BM
+
+/[^a]/BM
+
+/[^a]/8BM
+
+/[^\xaa]/BM
+
+/[^\xaa]/8BM
+
+/[^\d]/8WB
+
+/[[:^alpha:][:^cntrl:]]+/8WB
+
+/[[:^cntrl:][:^alpha:]]+/8WB
+
+/[[:alpha:]]+/8WB
+
+/[[:^alpha:]\S]+/8WB
+
+/abc(d|e)(*THEN)x(123(*THEN)4|567(b|q)(*THEN)xx)/B
+
+/-- End of testinput11 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput12 b/ext/pcre/pcrelib/testdata/testinput12
new file mode 100644
index 0000000000..5d727af26a
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput12
@@ -0,0 +1,90 @@
+/-- This test is run only when JIT support is available. It checks for a
+successful and an unsuccessful JIT compile and save and restore behaviour,
+and a couple of things that are different with JIT. --/
+
+/abc/S+I
+
+/(?(?C1)(?=a)a)/S+I
+
+/(?(?C1)(?=a)a)/S!+I
+
+/abc/S+I>testsavedregex
+
+<testsavedregex
+ abc
+
+/a*/SI
+
+/(?(R)a*(?1)|((?R))b)/S+
+ aaaabcde
+
+/-- Test various compile modes --/
+
+/abcd/S++
+ abcd
+ xyz
+
+/abcd/S+
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++1
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+ xyz\P
+
+/abcd/S++2
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++3
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++4
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++5
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++6
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++7
+ abcd
+ ab\P
+ ab\P\P
+ xyz
+
+/abcd/S++2I
+
+/(*NO_START_OPT)a(*:m)b/KS++
+ a
+
+/^12345678abcd/mS++
+ 12345678abcd
+
+/-- End of testinput12 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput13 b/ext/pcre/pcrelib/testdata/testinput13
new file mode 100644
index 0000000000..c7bc67bb17
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput13
@@ -0,0 +1,9 @@
+/-- This test is run only when JIT support is not available. It checks that an
+attempt to use it has the expected behaviour. It also tests things that
+are different without JIT. --/
+
+/abc/S+I
+
+/a*/SI
+
+/-- End of testinput13 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput14 b/ext/pcre/pcrelib/testdata/testinput14
new file mode 100644
index 0000000000..325ed9e361
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput14
@@ -0,0 +1,343 @@
+/-- This set of tests is run only with the 8-bit library. They do not require
+ UTF-8 or Unicode property support. The file starts with all the tests of
+ the POSIX interface, because that is supported only with the 8-bit library.
+ --/
+
+< forbid 8W
+
+/abc/P
+ abc
+ *** Failers
+
+/^abc|def/P
+ abcdef
+ abcdef\B
+
+/.*((abc)$|(def))/P
+ defabc
+ \Zdefabc
+
+/the quick brown fox/P
+ the quick brown fox
+ *** Failers
+ The Quick Brown Fox
+
+/the quick brown fox/Pi
+ the quick brown fox
+ The Quick Brown Fox
+
+/abc.def/P
+ *** Failers
+ abc\ndef
+
+/abc$/P
+ abc
+ abc\n
+
+/(abc)\2/P
+
+/(abc\1)/P
+ abc
+
+/a*(b+)(z)(z)/P
+ aaaabbbbzzzz
+ aaaabbbbzzzz\O0
+ aaaabbbbzzzz\O1
+ aaaabbbbzzzz\O2
+ aaaabbbbzzzz\O3
+ aaaabbbbzzzz\O4
+ aaaabbbbzzzz\O5
+
+/ab.cd/P
+ ab-cd
+ ab=cd
+ ** Failers
+ ab\ncd
+
+/ab.cd/Ps
+ ab-cd
+ ab=cd
+ ab\ncd
+
+/a(b)c/PN
+ abc
+
+/a(?P<name>b)c/PN
+ abc
+
+/a?|b?/P
+ abc
+ ** Failers
+ ddd\N
+
+/\w+A/P
+ CDAAAAB
+
+/\w+A/PU
+ CDAAAAB
+
+/\Biss\B/I+P
+ Mississippi
+
+/abc/\P
+
+/-- End of POSIX tests --/
+
+/a\Cb/
+ aXb
+ a\nb
+ ** Failers (too big char)
+ A\x{123}B
+ A\o{443}B
+
+/\x{100}/I
+
+/\o{400}/I
+
+/ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional leading comment
+(?: (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address
+| # or
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # one word, optionally followed by....
+(?:
+[^()<>@,;:".\\\[\]\x80-\xff\000-\010\012-\037] | # atom and space parts, or...
+\(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) | # comments, or...
+
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+# quoted strings
+)*
+< (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # leading <
+(?: @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* , (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+)* # further okay, if led by comma
+: # closing colon
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* )? # optional route
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address spec
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* > # trailing >
+# name and address
+) (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional trailing comment
+/xSI
+
+/-- Although this saved pattern was compiled with link-size=2, it does no harm
+to run this test with other link sizes because it is going to generated a
+"compiled in wrong mode" error as soon as it is loaded, so the link size does
+not matter. --/
+
+<!testsaved16
+
+<!testsaved32
+
+/\h/SI
+
+/\H/SI
+
+/\v/SI
+
+/\V/SI
+
+/\R/SI
+
+/[\h]/BZ
+ >\x09<
+
+/[\h]+/BZ
+ >\x09\x20\xa0<
+
+/[\v]/BZ
+
+/[\H]/BZ
+
+/[^\h]/BZ
+
+/[\V]/BZ
+
+/[\x0a\V]/BZ
+
+/\777/I
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF)XX/K
+ XX
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE)XX/K
+ XX
+
+/\u0100/<JS>
+
+/[\u0100-\u0200]/<JS>
+
+/[^\x00-a]{12,}[^b-\xff]*/BZ
+
+/[^\s]*\s* [^\W]+\W+ [^\d]*?\d0 [^\d\w]{4,6}?\w*A/BZ
+
+/-- End of testinput14 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput15 b/ext/pcre/pcrelib/testdata/testinput15
new file mode 100644
index 0000000000..83e2677347
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput15
@@ -0,0 +1,366 @@
+/-- This set of tests is for UTF-8 support but not Unicode property support,
+ and is relevant only to the 8-bit library. --/
+
+< forbid W
+
+/X(\C{3})/8
+ X\x{1234}
+
+/X(\C{4})/8
+ X\x{1234}YZ
+
+/X\C*/8
+ XYZabcdce
+
+/X\C*?/8
+ XYZabcde
+
+/X\C{3,5}/8
+ Xabcdefg
+ X\x{1234}
+ X\x{1234}YZ
+ X\x{1234}\x{512}
+ X\x{1234}\x{512}YZ
+
+/X\C{3,5}?/8
+ Xabcdefg
+ X\x{1234}
+ X\x{1234}YZ
+ X\x{1234}\x{512}
+
+/a\Cb/8
+ aXb
+ a\nb
+
+/a\C\Cb/8
+ a\x{100}b
+
+/ab\Cde/8
+ abXde
+
+/a\C\Cb/8
+ a\x{100}b
+ ** Failers
+ a\x{12257}b
+
+/[Ã]/8
+
+/Ã/8
+
+/ÃÃÃxxx/8
+
+/ÃÃÃxxx/8?DZSSO
+
+/badutf/8
+ \xdf
+ \xef
+ \xef\x80
+ \xf7
+ \xf7\x80
+ \xf7\x80\x80
+ \xfb
+ \xfb\x80
+ \xfb\x80\x80
+ \xfb\x80\x80\x80
+ \xfd
+ \xfd\x80
+ \xfd\x80\x80
+ \xfd\x80\x80\x80
+ \xfd\x80\x80\x80\x80
+ \xdf\x7f
+ \xef\x7f\x80
+ \xef\x80\x7f
+ \xf7\x7f\x80\x80
+ \xf7\x80\x7f\x80
+ \xf7\x80\x80\x7f
+ \xfb\x7f\x80\x80\x80
+ \xfb\x80\x7f\x80\x80
+ \xfb\x80\x80\x7f\x80
+ \xfb\x80\x80\x80\x7f
+ \xfd\x7f\x80\x80\x80\x80
+ \xfd\x80\x7f\x80\x80\x80
+ \xfd\x80\x80\x7f\x80\x80
+ \xfd\x80\x80\x80\x7f\x80
+ \xfd\x80\x80\x80\x80\x7f
+ \xed\xa0\x80
+ \xc0\x8f
+ \xe0\x80\x8f
+ \xf0\x80\x80\x8f
+ \xf8\x80\x80\x80\x8f
+ \xfc\x80\x80\x80\x80\x8f
+ \x80
+ \xfe
+ \xff
+
+/badutf/8
+ \xfb\x80\x80\x80\x80
+ \xfd\x80\x80\x80\x80\x80
+ \xf7\xbf\xbf\xbf
+
+/shortutf/8
+ \P\P\xdf
+ \P\P\xef
+ \P\P\xef\x80
+ \P\P\xf7
+ \P\P\xf7\x80
+ \P\P\xf7\x80\x80
+ \P\P\xfb
+ \P\P\xfb\x80
+ \P\P\xfb\x80\x80
+ \P\P\xfb\x80\x80\x80
+ \P\P\xfd
+ \P\P\xfd\x80
+ \P\P\xfd\x80\x80
+ \P\P\xfd\x80\x80\x80
+ \P\P\xfd\x80\x80\x80\x80
+
+/anything/8
+ \xc0\x80
+ \xc1\x8f
+ \xe0\x9f\x80
+ \xf0\x8f\x80\x80
+ \xf8\x87\x80\x80\x80
+ \xfc\x83\x80\x80\x80\x80
+ \xfe\x80\x80\x80\x80\x80
+ \xff\x80\x80\x80\x80\x80
+ \xc3\x8f
+ \xe0\xaf\x80
+ \xe1\x80\x80
+ \xf0\x9f\x80\x80
+ \xf1\x8f\x80\x80
+ \xf8\x88\x80\x80\x80
+ \xf9\x87\x80\x80\x80
+ \xfc\x84\x80\x80\x80\x80
+ \xfd\x83\x80\x80\x80\x80
+ \?\xf8\x88\x80\x80\x80
+ \?\xf9\x87\x80\x80\x80
+ \?\xfc\x84\x80\x80\x80\x80
+ \?\xfd\x83\x80\x80\x80\x80
+
+/\x{100}/8DZ
+
+/\x{1000}/8DZ
+
+/\x{10000}/8DZ
+
+/\x{100000}/8DZ
+
+/\x{10ffff}/8DZ
+
+/[\x{ff}]/8DZ
+
+/[\x{100}]/8DZ
+
+/\x80/8DZ
+
+/\xff/8DZ
+
+/\x{D55c}\x{ad6d}\x{C5B4}/DZ8
+ \x{D55c}\x{ad6d}\x{C5B4}
+
+/\x{65e5}\x{672c}\x{8a9e}/DZ8
+ \x{65e5}\x{672c}\x{8a9e}
+
+/\x{80}/DZ8
+
+/\x{084}/DZ8
+
+/\x{104}/DZ8
+
+/\x{861}/DZ8
+
+/\x{212ab}/DZ8
+
+/-- This one is here not because it's different to Perl, but because the way
+the captured single-byte is displayed. (In Perl it becomes a character, and you
+can't tell the difference.) --/
+
+/X(\C)(.*)/8
+ X\x{1234}
+ X\nabc
+
+/-- This one is here because Perl gives out a grumbly error message (quite
+correctly, but that messes up comparisons). --/
+
+/a\Cb/8
+ *** Failers
+ a\x{100}b
+
+/[^ab\xC0-\xF0]/8SDZ
+ \x{f1}
+ \x{bf}
+ \x{100}
+ \x{1000}
+ *** Failers
+ \x{c0}
+ \x{f0}
+
+/Ä€{3,4}/8SDZ
+ \x{100}\x{100}\x{100}\x{100\x{100}
+
+/(\x{100}+|x)/8SDZ
+
+/(\x{100}*a|x)/8SDZ
+
+/(\x{100}{0,2}a|x)/8SDZ
+
+/(\x{100}{1,2}a|x)/8SDZ
+
+/\x{100}/8DZ
+
+/a\x{100}\x{101}*/8DZ
+
+/a\x{100}\x{101}+/8DZ
+
+/[^\x{c4}]/DZ
+
+/[\x{100}]/8DZ
+ \x{100}
+ Z\x{100}
+ \x{100}Z
+ *** Failers
+
+/[\xff]/DZ8
+ >\x{ff}<
+
+/[^\xff]/8DZ
+
+/\x{100}abc(xyz(?1))/8DZ
+
+/a\x{1234}b/P8
+ a\x{1234}b
+
+/\777/8I
+ \x{1ff}
+ \777
+
+/\x{100}+\x{200}/8DZ
+
+/\x{100}+X/8DZ
+
+/^[\QÄ€\E-\QÅ\E/BZ8
+
+/-- This tests the stricter UTF-8 check according to RFC 3629. --/
+
+/X/8
+ \x{d800}
+ \x{d800}\?
+ \x{da00}
+ \x{da00}\?
+ \x{dfff}
+ \x{dfff}\?
+ \x{110000}
+ \x{110000}\?
+ \x{2000000}
+ \x{2000000}\?
+ \x{7fffffff}
+ \x{7fffffff}\?
+
+/(*UTF8)\x{1234}/
+ abcd\x{1234}pqr
+
+/(*CRLF)(*UTF)(*BSR_UNICODE)a\Rb/I
+
+/\h/SI8
+ ABC\x{09}
+ ABC\x{20}
+ ABC\x{a0}
+ ABC\x{1680}
+ ABC\x{180e}
+ ABC\x{2000}
+ ABC\x{202f}
+ ABC\x{205f}
+ ABC\x{3000}
+
+/\v/SI8
+ ABC\x{0a}
+ ABC\x{0b}
+ ABC\x{0c}
+ ABC\x{0d}
+ ABC\x{85}
+ ABC\x{2028}
+
+/\h*A/SI8
+ CDBABC
+
+/\v+A/SI8
+
+/\s?xxx\s/8SI
+
+/\sxxx\s/I8ST1
+ AB\x{85}xxx\x{a0}XYZ
+ AB\x{a0}xxx\x{85}XYZ
+
+/\S \S/I8ST1
+ \x{a2} \x{84}
+ A Z
+
+/a+/8
+ a\x{123}aa\>1
+ a\x{123}aa\>2
+ a\x{123}aa\>3
+ a\x{123}aa\>4
+ a\x{123}aa\>5
+ a\x{123}aa\>6
+
+/\x{1234}+/iS8I
+
+/\x{1234}+?/iS8I
+
+/\x{1234}++/iS8I
+
+/\x{1234}{2}/iS8I
+
+/[^\x{c4}]/8DZ
+
+/X+\x{200}/8DZ
+
+/\R/SI8
+
+/\777/8DZ
+
+/\w+\x{C4}/8BZ
+ a\x{C4}\x{C4}
+
+/\w+\x{C4}/8BZT1
+ a\x{C4}\x{C4}
+
+/\W+\x{C4}/8BZ
+ !\x{C4}
+
+/\W+\x{C4}/8BZT1
+ !\x{C4}
+
+/\W+\x{A1}/8BZ
+ !\x{A1}
+
+/\W+\x{A1}/8BZT1
+ !\x{A1}
+
+/X\s+\x{A0}/8BZ
+ X\x20\x{A0}\x{A0}
+
+/X\s+\x{A0}/8BZT1
+ X\x20\x{A0}\x{A0}
+
+/\S+\x{A0}/8BZ
+ X\x{A0}\x{A0}
+
+/\S+\x{A0}/8BZT1
+ X\x{A0}\x{A0}
+
+/\x{a0}+\s!/8BZ
+ \x{a0}\x20!
+
+/\x{a0}+\s!/8BZT1
+ \x{a0}\x20!
+
+/A/8
+ \x{ff000041}
+ \x{7f000041}
+
+/(*UTF8)abc/9
+
+/abc/89
+
+/-- End of testinput15 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput16 b/ext/pcre/pcrelib/testdata/testinput16
new file mode 100644
index 0000000000..e7a05ae0d4
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput16
@@ -0,0 +1,35 @@
+/-- This set of tests is run only with the 8-bit library when Unicode property
+ support is available. It starts with tests of the POSIX interface, because
+ that is supported only with the 8-bit library. --/
+
+/\w/P
+ +++\x{c2}
+
+/\w/WP
+ +++\x{c2}
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iDZ
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8DZ
+
+/AB\x{1fb0}/8DZ
+
+/AB\x{1fb0}/8DZi
+
+/\x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}/8iSI
+ \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+
+/[â±¥]/8iBZ
+
+/[^â±¥]/8iBZ
+
+/\h/SI
+
+/\v/SI
+
+/\R/SI
+
+/[[:blank:]]/WBZ
+
+/-- End of testinput16 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput17 b/ext/pcre/pcrelib/testdata/testinput17
new file mode 100644
index 0000000000..1d933c7942
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput17
@@ -0,0 +1,307 @@
+/-- This set of tests is for the 16- and 32-bit library's basic (non-UTF-16
+ or -32) features that are not compatible with the 8-bit library, or which
+ give different output in 16- or 32-bit mode. --/
+
+< forbid 8W
+
+/a\Cb/
+ aXb
+ a\nb
+
+/[^\x{c4}]/DZ
+
+/\x{100}/I
+
+/ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional leading comment
+(?: (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address
+| # or
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # one word, optionally followed by....
+(?:
+[^()<>@,;:".\\\[\]\x80-\xff\000-\010\012-\037] | # atom and space parts, or...
+\(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) | # comments, or...
+
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+# quoted strings
+)*
+< (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # leading <
+(?: @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* , (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+)* # further okay, if led by comma
+: # closing colon
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* )? # optional route
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address spec
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* > # trailing >
+# name and address
+) (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional trailing comment
+/xSI
+
+/[\h]/BZ
+ >\x09<
+
+/[\h]+/BZ
+ >\x09\x20\xa0<
+
+/[\v]/BZ
+
+/[^\h]/BZ
+
+/\h+/SI
+ \x{1681}\x{200b}\x{1680}\x{2000}\x{202f}\x{3000}
+ \x{3001}\x{2fff}\x{200a}\xa0\x{2000}
+
+/[\h\x{dc00}]+/BZSI
+ \x{1681}\x{200b}\x{1680}\x{2000}\x{202f}\x{3000}
+ \x{3001}\x{2fff}\x{200a}\xa0\x{2000}
+
+/\H+/SI
+ \x{1680}\x{180e}\x{167f}\x{1681}\x{180d}\x{180f}
+ \x{2000}\x{200a}\x{1fff}\x{200b}
+ \x{202f}\x{205f}\x{202e}\x{2030}\x{205e}\x{2060}
+ \xa0\x{3000}\x9f\xa1\x{2fff}\x{3001}
+
+/[\H\x{d800}]+/
+ \x{1680}\x{180e}\x{167f}\x{1681}\x{180d}\x{180f}
+ \x{2000}\x{200a}\x{1fff}\x{200b}
+ \x{202f}\x{205f}\x{202e}\x{2030}\x{205e}\x{2060}
+ \xa0\x{3000}\x9f\xa1\x{2fff}\x{3001}
+
+/\v+/SI
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+
+/[\v\x{dc00}]+/BZSI
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+
+/\V+/SI
+ \x{2028}\x{2029}\x{2027}\x{2030}
+ \x85\x0a\x0b\x0c\x0d\x09\x0e\x84\x86
+
+/[\V\x{d800}]+/
+ \x{2028}\x{2029}\x{2027}\x{2030}
+ \x85\x0a\x0b\x0c\x0d\x09\x0e\x84\x86
+
+/\R+/SI<bsr_unicode>
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+
+/\x{d800}\x{d7ff}\x{dc00}\x{dc00}\x{dcff}\x{dd00}/I
+ \x{d800}\x{d7ff}\x{dc00}\x{dc00}\x{dcff}\x{dd00}
+
+/[^\x{80}][^\x{ff}][^\x{100}][^\x{1000}][^\x{ffff}]/BZ
+
+/[^\x{80}][^\x{ff}][^\x{100}][^\x{1000}][^\x{ffff}]/BZi
+
+/[^\x{100}]*[^\x{1000}]+[^\x{ffff}]??[^\x{8000}]{4,}[^\x{7fff}]{2,9}?[^\x{100}]{5,6}+/BZ
+
+/[^\x{100}]*[^\x{1000}]+[^\x{ffff}]??[^\x{8000}]{4,}[^\x{7fff}]{2,9}?[^\x{100}]{5,6}+/BZi
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF)XX/K
+ XX
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE)XX/K
+ XX
+
+/\u0100/<JS>BZ
+
+/[\u0100-\u0200]/<JS>BZ
+
+/\ud800/<JS>BZ
+
+/^\x{ffff}+/i
+ \x{ffff}
+
+/^\x{ffff}?/i
+ \x{ffff}
+
+/^\x{ffff}*/i
+ \x{ffff}
+
+/^\x{ffff}{3}/i
+ \x{ffff}\x{ffff}\x{ffff}
+
+/^\x{ffff}{0,3}/i
+ \x{ffff}
+
+/[^\x00-a]{12,}[^b-\xff]*/BZ
+
+/[^\s]*\s* [^\W]+\W+ [^\d]*?\d0 [^\d\w]{4,6}?\w*A/BZ
+
+/a*[b-\x{200}]?a#a*[b-\x{200}]?b#[a-f]*[g-\x{200}]*#[g-\x{200}]*[a-c]*#[g-\x{200}]*[a-h]*/BZ
+
+/^[\x{1234}\x{4321}]{2,4}?/
+ \x{1234}\x{1234}\x{1234}
+
+/-- End of testinput17 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput18 b/ext/pcre/pcrelib/testdata/testinput18
new file mode 100644
index 0000000000..abff34e73a
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput18
@@ -0,0 +1,300 @@
+/-- This set of tests is for UTF-16 and UTF-32 support, and is relevant only to
+ the 16- and 32-bit libraries. --/
+
+< forbid W
+
+/ÃÃÃxxx/8?DZSS
+
+/abc/8
+ Ã]
+
+/X(\C{3})/8
+ X\x{11234}Y
+ X\x{11234}YZ
+
+/X(\C{4})/8
+ X\x{11234}YZ
+ X\x{11234}YZW
+
+/X\C*/8
+ XYZabcdce
+
+/X\C*?/8
+ XYZabcde
+
+/X\C{3,5}/8
+ Xabcdefg
+ X\x{11234}Y
+ X\x{11234}YZ
+ X\x{11234}\x{512}
+ X\x{11234}\x{512}YZ
+ X\x{11234}\x{512}\x{11234}Z
+
+/X\C{3,5}?/8
+ Xabcdefg
+ X\x{11234}Y
+ X\x{11234}YZ
+ X\x{11234}\x{512}YZ
+ *** Failers
+ X\x{11234}
+
+/a\Cb/8
+ aXb
+ a\nb
+
+/a\C\Cb/8
+ a\x{12257}b
+ a\x{12257}\x{11234}b
+ ** Failers
+ a\x{100}b
+
+/ab\Cde/8
+ abXde
+
+/-- Check maximum character size --/
+
+/\x{ffff}/8DZ
+
+/\x{10000}/8DZ
+
+/\x{100}/8DZ
+
+/\x{1000}/8DZ
+
+/\x{10000}/8DZ
+
+/\x{100000}/8DZ
+
+/\x{10ffff}/8DZ
+
+/[\x{ff}]/8DZ
+
+/[\x{100}]/8DZ
+
+/\x80/8DZ
+
+/\xff/8DZ
+
+/\x{D55c}\x{ad6d}\x{C5B4}/DZ8
+ \x{D55c}\x{ad6d}\x{C5B4}
+
+/\x{65e5}\x{672c}\x{8a9e}/DZ8
+ \x{65e5}\x{672c}\x{8a9e}
+
+/\x{80}/DZ8
+
+/\x{084}/DZ8
+
+/\x{104}/DZ8
+
+/\x{861}/DZ8
+
+/\x{212ab}/DZ8
+
+/-- This one is here not because it's different to Perl, but because the way
+the captured single-byte is displayed. (In Perl it becomes a character, and you
+can't tell the difference.) --/
+
+/X(\C)(.*)/8
+ X\x{1234}
+ X\nabc
+
+/-- This one is here because Perl gives out a grumbly error message (quite
+correctly, but that messes up comparisons). --/
+
+/a\Cb/8
+ *** Failers
+ a\x{100}b
+
+/[^ab\xC0-\xF0]/8SDZ
+ \x{f1}
+ \x{bf}
+ \x{100}
+ \x{1000}
+ *** Failers
+ \x{c0}
+ \x{f0}
+
+/Ä€{3,4}/8SDZ
+ \x{100}\x{100}\x{100}\x{100\x{100}
+
+/(\x{100}+|x)/8SDZ
+
+/(\x{100}*a|x)/8SDZ
+
+/(\x{100}{0,2}a|x)/8SDZ
+
+/(\x{100}{1,2}a|x)/8SDZ
+
+/\x{100}/8DZ
+
+/a\x{100}\x{101}*/8DZ
+
+/a\x{100}\x{101}+/8DZ
+
+/[^\x{c4}]/DZ
+
+/[\x{100}]/8DZ
+ \x{100}
+ Z\x{100}
+ \x{100}Z
+ *** Failers
+
+/[\xff]/DZ8
+ >\x{ff}<
+
+/[^\xff]/8DZ
+
+/\x{100}abc(xyz(?1))/8DZ
+
+/\777/8I
+ \x{1ff}
+ \777
+
+/\x{100}+\x{200}/8DZ
+
+/\x{100}+X/8DZ
+
+/^[\QÄ€\E-\QÅ\E/BZ8
+
+/X/8
+ \x{d800}
+ \x{d800}\?
+ \x{da00}
+ \x{da00}\?
+ \x{dc00}
+ \x{dc00}\?
+ \x{de00}
+ \x{de00}\?
+ \x{dfff}
+ \x{dfff}\?
+ \x{110000}
+ \x{d800}\x{1234}
+
+/(*UTF16)\x{11234}/
+ abcd\x{11234}pqr
+
+/(*UTF)\x{11234}/I
+ abcd\x{11234}pqr
+
+/(*UTF-32)\x{11234}/
+ abcd\x{11234}pqr
+
+/(*CRLF)(*UTF16)(*BSR_UNICODE)a\Rb/I
+
+/(*CRLF)(*UTF32)(*BSR_UNICODE)a\Rb/I
+
+/\h/SI8
+ ABC\x{09}
+ ABC\x{20}
+ ABC\x{a0}
+ ABC\x{1680}
+ ABC\x{180e}
+ ABC\x{2000}
+ ABC\x{202f}
+ ABC\x{205f}
+ ABC\x{3000}
+
+/\v/SI8
+ ABC\x{0a}
+ ABC\x{0b}
+ ABC\x{0c}
+ ABC\x{0d}
+ ABC\x{85}
+ ABC\x{2028}
+
+/\h*A/SI8
+ CDBABC
+ \x{2000}ABC
+
+/\R*A/SI8
+ CDBABC
+ \x{2028}A
+
+/\v+A/SI8
+
+/\s?xxx\s/8SI
+
+/\sxxx\s/I8ST1
+ AB\x{85}xxx\x{a0}XYZ
+ AB\x{a0}xxx\x{85}XYZ
+
+/\S \S/I8ST1
+ \x{a2} \x{84}
+ A Z
+
+/a+/8
+ a\x{123}aa\>1
+ a\x{123}aa\>2
+ a\x{123}aa\>3
+ a\x{123}aa\>4
+ a\x{123}aa\>5
+ a\x{123}aa\>6
+
+/\x{1234}+/iS8I
+
+/\x{1234}+?/iS8I
+
+/\x{1234}++/iS8I
+
+/\x{1234}{2}/iS8I
+
+/[^\x{c4}]/8DZ
+
+/X+\x{200}/8DZ
+
+/\R/SI8
+
+/-- Check bad offset --/
+
+/a/8
+ \x{10000}\>1
+ \x{10000}ab\>1
+ \x{10000}ab\>2
+ \x{10000}ab\>3
+ \x{10000}ab\>4
+ \x{10000}ab\>5
+
+/í¼€/8
+
+/\w+\x{C4}/8BZ
+ a\x{C4}\x{C4}
+
+/\w+\x{C4}/8BZT1
+ a\x{C4}\x{C4}
+
+/\W+\x{C4}/8BZ
+ !\x{C4}
+
+/\W+\x{C4}/8BZT1
+ !\x{C4}
+
+/\W+\x{A1}/8BZ
+ !\x{A1}
+
+/\W+\x{A1}/8BZT1
+ !\x{A1}
+
+/X\s+\x{A0}/8BZ
+ X\x20\x{A0}\x{A0}
+
+/X\s+\x{A0}/8BZT1
+ X\x20\x{A0}\x{A0}
+
+/\S+\x{A0}/8BZ
+ X\x{A0}\x{A0}
+
+/\S+\x{A0}/8BZT1
+ X\x{A0}\x{A0}
+
+/\x{a0}+\s!/8BZ
+ \x{a0}\x20!
+
+/\x{a0}+\s!/8BZT1
+ \x{a0}\x20!
+
+/(*UTF)abc/9
+
+/abc/89
+
+/-- End of testinput18 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput19 b/ext/pcre/pcrelib/testdata/testinput19
new file mode 100644
index 0000000000..00d80203f0
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput19
@@ -0,0 +1,22 @@
+/-- This set of tests is for Unicode property support, relevant only to the
+ 16- and 32-bit library. --/
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iDZ
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8DZ
+
+/AB\x{1fb0}/8DZ
+
+/AB\x{1fb0}/8DZi
+
+/\x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}/8iSI
+ \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+
+/[â±¥]/8iBZ
+
+/[^â±¥]/8iBZ
+
+/[[:blank:]]/WBZ
+
+/-- End of testinput19 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput2 b/ext/pcre/pcrelib/testdata/testinput2
index 9670104e6a..00924ee98f 100644
--- a/ext/pcre/pcrelib/testdata/testinput2
+++ b/ext/pcre/pcrelib/testdata/testinput2
@@ -7,6 +7,8 @@
NOTE: This is a non-UTF set of tests. When UTF support is needed, use
test 5, and if Unicode Property Support is needed, use test 7. --/
+
+< forbid 8W
/(a)b|/I
@@ -313,12 +315,6 @@
*** Failers
fooabar
-/This one is here because Perl 5.005_02 doesn't fail it/I
-
-/^(a)?(?(1)a|b)+$/I
- *** Failers
- a
-
/This one is here because Perl behaves differently; see also the following/I
/^(a\1?){4}$/I
@@ -835,7 +831,13 @@
/x++/DZ
-/x{1,3}+/DZ
+/x{1,3}+/BZO
+
+/x{1,3}+/BZOi
+
+/[^x]{1,3}+/BZO
+
+/[^x]{1,3}+/BZOi
/(x)*+/DZ
@@ -1501,6 +1503,8 @@
a2b\CA
** Failers
a1b\CZ\CA
+
+/(?|(?<a>)(?<b>)(?<a>)|(?<a>)(?<b>)(?<a>))/IJ
/^(?P<A>a)(?P<A>b)/IJ
ab\CA
@@ -1941,10 +1945,7 @@ a random value. /Ix
/(?<A> (?'B' abc (?(R) (?(R&A)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
abcabc1Xabc2XabcXabcabc
-/(?<A> (?'B' abc (?(R) (?(R&1)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
-
-/(?<1> (?'B' abc (?(R) (?(R&1)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
- abcabc1Xabc2XabcXabcabc
+/(?<A> (?'B' abc (?(R) (?(R&C)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
/^(?(DEFINE) abc | xyz ) /x
@@ -2061,7 +2062,7 @@ a random value. /Ix
/^(a)\g{3/
-/^(a)\g{4a}/
+/^(a)\g{aa}/
/^a.b/<lf>
a\rb
@@ -2516,7 +2517,10 @@ a random value. /Ix
** Failers
ab
-/a(?!)+b/
+/a(?!)b/BZ
+
+/(?!)?a/BZ
+ ab
/a(*FAIL)+b/
@@ -2541,7 +2545,9 @@ a random value. /Ix
abcxypqr\Y
/(*NO_START_OPT)xyz/C
- abcxyz
+ abcxyz
+
+/(*NO_AUTO_POSSESS)a+b/BZ
/xyz/CY
abcxyz
@@ -2939,7 +2945,7 @@ a random value. /Ix
xxxxabcde\P
xxxxabcde\P\P
-/-- This is not in the Perl >= 5.10 test because Perl seems currently to be
+/-- This is not in the Perl-compatible test because Perl seems currently to be
broken and not behaving as specified in that it *does* bumpalong after
hitting (*COMMIT). --/
@@ -2985,28 +2991,12 @@ a random value. /Ix
/^(?&t)*(?(DEFINE)(?<t>.))$/BZ
-/ -- The first four of these are not in the Perl >= 5.10 test because Perl
- documents that the use of \K in assertions is "not well defined". The
- last is here because Perl gives the match as "b" rather than "ab". I
+/ -- This one is here because Perl gives the match as "b" rather than "ab". I
believe this to be a Perl bug. --/
-/(?=a\Kb)ab/
- ab
-
-/(?!a\Kb)ac/
- ac
-
-/^abc(?<=b\Kc)d/
- abcd
-
-/^abc(?<!b\Kq)d/
- abcd
-
/(?>a\Kb)z|(ab)/
ab
-/----------------------/
-
/(?P<L1>(?P<L2>0|)|(?P>L2)(?P>L1))/
/abc(*MARK:)pqr/
@@ -3021,7 +3011,7 @@ a random value. /Ix
/A(*COMMIT)B/+K
ACABX
-/--- These should be different, but in Perl 5.11 are not, which I think
+/--- These should be different, but in Perl they are not, which I think
is a bug in Perl. ---/
/A(*THEN)B|A(*THEN)C/K
@@ -3030,12 +3020,6 @@ a random value. /Ix
/A(*PRUNE)B|A(*PRUNE)C/K
AC
-/--- This should fail; the SKIP advances by one, but when we get to AC, the
- PRUNE kills it. Perl behaves differently. ---/
-
-/A(*PRUNE:A)A+(*SKIP:A)(B|Z) | AC/xK
- AAAC
-
/--- Mark names can be duplicated. Perl doesn't give a mark for this one,
though PCRE does. ---/
@@ -3061,7 +3045,7 @@ with \Y. ---/
/^(ab (c+(*FAIL)cd) | xyz)/x
abcccd
-/--- Perl 5.11 gets some of these wrong ---/
+/--- Perl gets some of these wrong ---/
/(?>.(*ACCEPT))*?5/
abcde
@@ -3121,14 +3105,6 @@ with \Y. ---/
/X\H++\R/BZ
X\x0d\x0a
-/-- Perl treats this one differently, not failing the second string. I believe
- that is a bug in Perl. --/
-
-/^((abc|abcx)(*THEN)y|abcd)/
- abcd
- *** Failers
- abcxy
-
/(?<=abc)def/
abc\P\P
@@ -3427,7 +3403,7 @@ with \Y. ---/
/\btype\b\W*?\btext\b\W*?\bjavascript\b|\burl\b\W*?\bshell:|<input\b.*?\btype\b\W*?\bimage\b|\bonkeyup\b\W*?\=/IS
-/a(*SKIP)c|b(*ACCEPT)|/+SI
+/a(*SKIP)c|b(*ACCEPT)|/+S!I
a
/a(*SKIP)c|b(*ACCEPT)cd(*ACCEPT)|x/SI
@@ -3453,52 +3429,6 @@ with \Y. ---/
/a(?:.(*THEN:ABC))*?a/ims
\Mabbbbbbbbbbbbbbbbbbbbba
-/-- These tests are in agreement with development Perl 5.015, which has fixed
- some things, but they don't all work with 5.012, so they aren't in the
- Perl-compatible tests. Those after the first come from Perl's own test
- files. --/
-
-/^((yes|no)(*THEN)(*F))?/
- yes
-
-/(A (.*) C? (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-
-/(A (.*) C? (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-
-/(A (.*) C? (*THEN) | A D) \s* (*FAIL)/x
-AbcdCBefgBhiBqz
-
-/(A (.*) C? (*THEN) | A D) \s* z/x
-AbcdCBefgBhiBqz
-
-/(A (.*) (?:C|) (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-
-/(A (.*) (?:C|) (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-
-/(A (.*) C{0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-
-/(A (.*) C{0,6} (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-
-/(A (.*) (CE){0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCEBefgBhiBqz
-
-/(A (.*) (CE){0,6} (*THEN) | A D) z/x
-AbcdCEBefgBhiBqz
-
-/(A (.*) (CE*){0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-
-/(A (.*) (CE*){0,6} (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-
-/-----------------------------------------------/
-
/^(?>a+)(?>(z+))\w/BZ
aaaazzzzb
** Failers
@@ -3564,6 +3494,8 @@ AbcdCBefgBhiBqz
/a[B-\Nc]/
+/a[B\Nc]/
+
/(a)(?2){0,1999}?(b)/
/(a)(?(DEFINE)(b))(?2){0,1999}?(?2)/
@@ -3751,24 +3683,9 @@ replaced by single letters. --/
\r\r\r\P
\r\r\r\P\P
-/-- These two are here because Perl does not match: it seems to allow the
-COMMIT to escape from the assertion. --/
-
-/(?=a(*COMMIT)b|ac)ac|ac/
- ac
-
-/(?=a(*COMMIT)b|(ac)) ac | (a)c/x
- ac
-
"AB(C(D))(E(F))?(?(?=\2)(?=\4))"
ABCDGHI\O03
-/-- This one is here because Perl does not confine the *COMMIT to the
-assertion, and therefore fails the entire subroutine call. --/
-
-/((?=a(*COMMIT)b)ab|ac){0}(?:(?1)|a(c))/
- ac
-
/-- These are all run as real matches in test 1; here we are just checking the
settings of the anchored and startline bits. --/
@@ -3810,4 +3727,322 @@ settings of the anchored and startline bits. --/
/.?/S!I
+/(?:(a)+(?C1)bb|aa(?C2)b)/
+ aab\C+
+
+/(?:(a)++(?C1)bb|aa(?C2)b)/
+ aab\C+
+
+/(?:(?>(a))(?C1)bb|aa(?C2)b)/
+ aab\C+
+
+/(?:(?1)(?C1)x|ab(?C2))((a)){0}/
+ aab\C+
+
+/(?1)(?C1)((a)(?C2)){0}/
+ aab\C+
+
+/(?:(a)+(?C1)bb|aa(?C2)b)++/
+ aab\C+
+ aab\C+\O2
+
+/(ab)x|ab/
+ ab\O3
+ ab\O2
+
+/(ab)/
+ ab\O3
+ ab\O2
+
+/(?<=123)(*MARK:xx)abc/K
+ xxxx123a\P\P
+ xxxx123a\P
+
+/123\Kabc/
+ xxxx123a\P\P
+ xxxx123a\P
+
+/^(?(?=a)aa|bb)/C
+ bb
+
+/(?C1)^(?C2)(?(?C99)(?=(?C3)a(?C4))(?C5)a(?C6)a(?C7)|(?C8)b(?C9)b(?C10))(?C11)/
+ bb
+
+/-- Perl seems to have a bug with this one --/
+
+/aaaaa(*COMMIT)(*PRUNE)b|a+c/
+ aaaaaac
+
+/-- Here are some that Perl treats differently because of the way it handles
+backtracking verbs. --/
+
+ /(?!a(*COMMIT)b)ac|ad/
+ ac
+ ad
+
+/^(?!a(*THEN)b|ac)../
+ ac
+ ad
+
+/^(?=a(*THEN)b|ac)/
+ ac
+
+/\A.*?(?:a|b(*THEN)c)/
+ ba
+
+/\A.*?(?:a|b(*THEN)c)++/
+ ba
+
+/\A.*?(?:a|b(*THEN)c|d)/
+ ba
+
+/(?:(a(*MARK:X)a+(*SKIP:X)b)){0}(?:(?1)|aac)/
+ aac
+
+/\A.*?(a|b(*THEN)c)/
+ ba
+
+/^(A(*THEN)B|A(*THEN)D)/
+ AD
+
+/(?!b(*THEN)a)bn|bnn/
+ bnn
+
+/(?(?=b(*SKIP)a)bn|bnn)/
+ bnn
+
+/(?=b(*THEN)a|)bn|bnn/
+ bnn
+
+/-------------------------/
+
+/(*LIMIT_MATCH=12bc)abc/
+
+/(*LIMIT_MATCH=4294967290)abc/
+
+/(*LIMIT_RECURSION=4294967280)abc/I
+
+/(a+)*zz/
+ aaaaaaaaaaaaaz
+ aaaaaaaaaaaaaz\q3000
+
+/(a+)*zz/S-
+ aaaaaaaaaaaaaz\Q10
+
+/(*LIMIT_MATCH=3000)(a+)*zz/I
+ aaaaaaaaaaaaaz
+ aaaaaaaaaaaaaz\q60000
+
+/(*LIMIT_MATCH=60000)(*LIMIT_MATCH=3000)(a+)*zz/I
+ aaaaaaaaaaaaaz
+
+/(*LIMIT_MATCH=60000)(a+)*zz/I
+ aaaaaaaaaaaaaz
+ aaaaaaaaaaaaaz\q3000
+
+/(*LIMIT_RECURSION=10)(a+)*zz/IS-
+ aaaaaaaaaaaaaz
+ aaaaaaaaaaaaaz\Q1000
+
+/(*LIMIT_RECURSION=10)(*LIMIT_RECURSION=1000)(a+)*zz/IS-
+ aaaaaaaaaaaaaz
+
+/(*LIMIT_RECURSION=1000)(a+)*zz/IS-
+ aaaaaaaaaaaaaz
+ aaaaaaaaaaaaaz\Q10
+
+/-- This test causes a segfault with Perl 5.18.0 --/
+
+/^(?=(a)){0}b(?1)/
+ backgammon
+
+/(?|(?<n>f)|(?<n>b))/JI
+
+/(?<a>abc)(?<a>z)\k<a>()/JDZS
+
+/a*[bcd]/BZ
+
+/[bcd]*a/BZ
+
+/-- A complete set of tests for auto-possessification of character types --/
+
+/\D+\D \D+\d \D+\S \D+\s \D+\W \D+\w \D+. \D+\C \D+\R \D+\H \D+\h \D+\V \D+\v \D+\Z \D+\z \D+$/BZx
+
+/\d+\D \d+\d \d+\S \d+\s \d+\W \d+\w \d+. \d+\C \d+\R \d+\H \d+\h \d+\V \d+\v \d+\Z \d+\z \d+$/BZx
+
+/\S+\D \S+\d \S+\S \S+\s \S+\W \S+\w \S+. \S+\C \S+\R \S+\H \S+\h \S+\V \S+\v \S+\Z \S+\z \S+$/BZx
+
+/\s+\D \s+\d \s+\S \s+\s \s+\W \s+\w \s+. \s+\C \s+\R \s+\H \s+\h \s+\V \s+\v \s+\Z \s+\z \s+$/BZx
+
+/\W+\D \W+\d \W+\S \W+\s \W+\W \W+\w \W+. \W+\C \W+\R \W+\H \W+\h \W+\V \W+\v \W+\Z \W+\z \W+$/BZx
+
+/\w+\D \w+\d \w+\S \w+\s \w+\W \w+\w \w+. \w+\C \w+\R \w+\H \w+\h \w+\V \w+\v \w+\Z \w+\z \w+$/BZx
+
+/\C+\D \C+\d \C+\S \C+\s \C+\W \C+\w \C+. \C+\C \C+\R \C+\H \C+\h \C+\V \C+\v \C+\Z \C+\z \C+$/BZx
+
+/\R+\D \R+\d \R+\S \R+\s \R+\W \R+\w \R+. \R+\C \R+\R \R+\H \R+\h \R+\V \R+\v \R+\Z \R+\z \R+$/BZx
+
+/\H+\D \H+\d \H+\S \H+\s \H+\W \H+\w \H+. \H+\C \H+\R \H+\H \H+\h \H+\V \H+\v \H+\Z \H+\z \H+$/BZx
+
+/\h+\D \h+\d \h+\S \h+\s \h+\W \h+\w \h+. \h+\C \h+\R \h+\H \h+\h \h+\V \h+\v \h+\Z \h+\z \h+$/BZx
+
+/\V+\D \V+\d \V+\S \V+\s \V+\W \V+\w \V+. \V+\C \V+\R \V+\H \V+\h \V+\V \V+\v \V+\Z \V+\z \V+$/BZx
+
+/\v+\D \v+\d \v+\S \v+\s \v+\W \v+\w \v+. \v+\C \v+\R \v+\H \v+\h \v+\V \v+\v \v+\Z \v+\z \v+$/BZx
+
+/ a+\D a+\d a+\S a+\s a+\W a+\w a+. a+\C a+\R a+\H a+\h a+\V a+\v a+\Z a+\z a+$/BZx
+
+/\n+\D \n+\d \n+\S \n+\s \n+\W \n+\w \n+. \n+\C \n+\R \n+\H \n+\h \n+\V \n+\v \n+\Z \n+\z \n+$/BZx
+
+/ .+\D .+\d .+\S .+\s .+\W .+\w .+. .+\C .+\R .+\H .+\h .+\V .+\v .+\Z .+\z .+$/BZx
+
+/ .+\D .+\d .+\S .+\s .+\W .+\w .+. .+\C .+\R .+\H .+\h .+\V .+\v .+\Z .+\z .+$/BZxs
+
+/\D+$ \d+$ \S+$ \s+$ \W+$ \w+$ \C+$ \R+$ \H+$ \h+$ \V+$ \v+$ a+$ \n+$ .+$ .+$/BZxm
+
+/(?=a+)a(a+)++a/BZ
+
+/a+(bb|cc)a+(?:bb|cc)a+(?>bb|cc)a+(?:bb|cc)+a+(aa)a+(?:bb|aa)/BZ
+
+/a+(bb|cc)?#a+(?:bb|cc)??#a+(?:bb|cc)?+#a+(?:bb|cc)*#a+(bb|cc)?a#a+(?:aa)?/BZ
+
+/a+(?:bb)?a#a+(?:|||)#a+(?:|b)a#a+(?:|||)?a/BZ
+
+/[ab]*/BZ
+ aaaa
+
+/[ab]*?/BZ
+ aaaa
+
+/[ab]?/BZ
+ aaaa
+
+/[ab]??/BZ
+ aaaa
+
+/[ab]+/BZ
+ aaaa
+
+/[ab]+?/BZ
+ aaaa
+
+/[ab]{2,3}/BZ
+ aaaa
+
+/[ab]{2,3}?/BZ
+ aaaa
+
+/[ab]{2,}/BZ
+ aaaa
+
+/[ab]{2,}?/BZ
+ aaaa
+
+/\d+\s{0,5}=\s*\S?=\w{0,4}\W*/BZ
+
+/[a-d]{5,12}[e-z0-9]*#[^a-z]+[b-y]*a[2-7]?[^0-9a-z]+/BZ
+
+/[a-z]*\s#[ \t]?\S#[a-c]*\S#[C-G]+?\d#[4-8]*\D#[4-9,]*\D#[!$]{0,5}\w#[M-Xf-l]+\W#[a-c,]?\W/BZ
+
+/a+(aa|bb)*c#a*(bb|cc)*a#a?(bb|cc)*d#[a-f]*(g|hh)*f/BZ
+
+/[a-f]*(g|hh|i)*i#[a-x]{4,}(y{0,6})*y#[a-k]+(ll|mm)+n/BZ
+
+/[a-f]*(?>gg|hh)+#[a-f]*(?>gg|hh)?#[a-f]*(?>gg|hh)*a#[a-f]*(?>gg|hh)*h/BZ
+
+/[a-c]*d/DZS
+
+/[a-c]+d/DZS
+
+/[a-c]?d/DZS
+
+/[a-c]{4,6}d/DZS
+
+/[a-c]{0,6}d/DZS
+
+/-- End of special auto-possessive tests --/
+
+/^A\o{1239}B/
+ A\123B
+
+/^A\oB/
+
+/^A\x{zz}B/
+
+/^A\x{12Z/
+
+/^A\x{/
+
+/[ab]++/BZO
+
+/[^ab]*+/BZO
+
+/a{4}+/BZO
+
+/a{4}+/BZOi
+
+/[a-[:digit:]]+/
+
+/[A-[:digit:]]+/
+
+/[a-[.xxx.]]+/
+
+/[a-[=xxx=]]+/
+
+/[a-[!xxx!]]+/
+
+/[A-[!xxx!]]+/
+ A]]]
+
+/[a-\d]+/
+
+/(?<0abc>xx)/
+
+/(?&1abc)xx(?<1abc>y)/
+
+/(?<ab-cd>xx)/
+
+/(?'0abc'xx)/
+
+/(?P<0abc>xx)/
+
+/\k<5ghj>/
+
+/\k'5ghj'/
+
+/\k{2fgh}/
+
+/(?P=8yuki)/
+
+/\g{4df}/
+
+/(?&1abc)xx(?<1abc>y)/
+
+/(?P>1abc)xx(?<1abc>y)/
+
+/\g'3gh'/
+
+/\g<5fg>/
+
+/(?(<4gh>)abc)/
+
+/(?('4gh')abc)/
+
+/(?(4gh)abc)/
+
+/(?(R&6yh)abc)/
+
+/-- Test the ugly "start or end of word" compatibility syntax --/
+
+/[[:<:]]red[[:>:]]/BZ
+ little red riding hood
+ a /red/ thing
+ red is a colour
+ put it all on red
+ ** Failers
+ no reduction
+ Alfred Winifred
+
+/[a[:<:]] should give error/
+
/-- End of testinput2 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput20 b/ext/pcre/pcrelib/testdata/testinput20
new file mode 100644
index 0000000000..2a6b8f23f4
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput20
@@ -0,0 +1,19 @@
+/-- These DFA tests are for the handling of characters greater than 255 in
+ 16- or 32-bit, non-UTF mode. --/
+
+/^\x{ffff}+/i
+ \x{ffff}
+
+/^\x{ffff}?/i
+ \x{ffff}
+
+/^\x{ffff}*/i
+ \x{ffff}
+
+/^\x{ffff}{3}/i
+ \x{ffff}\x{ffff}\x{ffff}
+
+/^\x{ffff}{0,3}/i
+ \x{ffff}
+
+/-- End of testinput20 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput21 b/ext/pcre/pcrelib/testdata/testinput21
new file mode 100644
index 0000000000..30895eef2d
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput21
@@ -0,0 +1,26 @@
+/-- Tests for reloading pre-compiled patterns. The first one gives an error
+right away, and can be any old pattern compiled in 8-bit mode ("abc" is
+typical). The others require the link size to be 2. */x
+
+<!testsaved8
+
+%-- Generated from:
+ /^[aL](?P<name>(?:[AaLl]+)[^xX-]*?)(?P<other>[\x{150}-\x{250}\x{300}]|
+ [^\x{800}aAs-uS-U\x{d800}-\x{dfff}])++[^#\b\x{500}\x{1000}]{3,5}$
+ /x
+
+ In 16-bit mode with options: S>testdata/saved16LE-1
+ FS>testdata/saved16BE-1
+ In 32-bit mode with options: S>testdata/saved32LE-1
+ FS>testdata/saved32BE-1
+--%x
+
+<!testsaved16LE-1
+
+<!testsaved16BE-1
+
+<!testsaved32LE-1
+
+<!testsaved32BE-1
+
+/-- End of testinput21 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput22 b/ext/pcre/pcrelib/testdata/testinput22
new file mode 100644
index 0000000000..ca408dbee9
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput22
@@ -0,0 +1,23 @@
+/-- Tests for reloading pre-compile patterns with UTF-16 or UTF-32 support. */
+
+%-- Generated from:
+ /(?P<cbra1>[aZ\x{400}-\x{10ffff}]{4,}
+ [\x{f123}\x{10039}\x{20000}-\x{21234}]?|
+ [A-Cx-z\x{100000}-\x{1000a7}\x{101234}])
+ (?<cb2>[^az])/x
+
+ In 16-bit mode with options: S8>testdata/saved16LE-2
+ FS8>testdata/saved16BE-2
+ In 32-bit mode with options: S8>testdata/saved32LE-2
+ FS8>testdata/saved32BE-2
+--%8x
+
+<!testsaved16LE-2
+
+<!testsaved16BE-2
+
+<!testsaved32LE-2
+
+<!testsaved32BE-2
+
+/-- End of testinput22 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput23 b/ext/pcre/pcrelib/testdata/testinput23
new file mode 100644
index 0000000000..0fdbae7c57
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput23
@@ -0,0 +1,20 @@
+/-- Tests for the 16-bit library only */
+
+< forbid 8W
+
+/-- Check maximum non-UTF character size --/
+
+/\x{ffff}/
+ A\x{ffff}B
+
+/\x{10000}/
+
+/\o{20000}/
+
+/-- Check character ranges --/
+
+/[\H]/BZSI
+
+/[\V]/BZSI
+
+/-- End of testinput23 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput24 b/ext/pcre/pcrelib/testdata/testinput24
new file mode 100644
index 0000000000..23eb84e55d
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput24
@@ -0,0 +1,11 @@
+/-- Tests for the 16-bit library with UTF-16 support only */
+
+< forbid W
+
+/bad/8
+ \x{d800}
+
+/short/8
+ \P\P\x{d800}
+
+/-- End of testinput24 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput25 b/ext/pcre/pcrelib/testdata/testinput25
new file mode 100644
index 0000000000..ce9d9e19a4
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput25
@@ -0,0 +1,44 @@
+/-- Tests for the 32-bit library only */
+
+< forbid 8w
+
+/-- Check maximum character size --/
+
+/\x{110000}/
+
+/\x{7fffffff}/
+
+/\x{80000000}/
+
+/\x{ffffffff}/
+
+/\x{100000000}/
+
+/\o{17777777777}/
+
+/\o{20000000000}/
+
+/\o{37777777777}/
+
+/\o{40000000000}/
+
+/\x{7fffffff}\x{7fffffff}/I
+
+/\x{80000000}\x{80000000}/I
+
+/\x{ffffffff}\x{ffffffff}/I
+
+/-- Non-UTF characters --/
+
+/\C{2,3}/
+ \x{400000}\x{400001}\x{400002}\x{400003}
+
+/\x{400000}\x{800000}/iDZ
+
+/-- Check character ranges --/
+
+/[\H]/BZSI
+
+/[\V]/BZSI
+
+/-- End of testinput25 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput26 b/ext/pcre/pcrelib/testdata/testinput26
new file mode 100644
index 0000000000..6b56ac1cc5
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinput26
@@ -0,0 +1,14 @@
+/-- Tests for the 32-bit library with UTF-32 support only */
+
+< forbid W
+
+/-- Non-UTF characters --/
+
+/\x{110000}/8
+
+/\o{4200000}/8
+
+/\C/8
+ \x{110000}
+
+/-- End of testinput26 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput3 b/ext/pcre/pcrelib/testdata/testinput3
index 6fea2f5b3b..1d2e855386 100644
--- a/ext/pcre/pcrelib/testdata/testinput3
+++ b/ext/pcre/pcrelib/testdata/testinput3
@@ -1,6 +1,8 @@
/-- This set of tests checks local-specific features, using the fr_FR locale.
It is not Perl-compatible. There is different version called wintestinput3
f or use on Windows, where the locale is called "french". --/
+
+< forbid 8W
/^[\w]+/
*** Failers
diff --git a/ext/pcre/pcrelib/testdata/testinput4 b/ext/pcre/pcrelib/testdata/testinput4
index c7bb370cfd..983f7a119b 100644
--- a/ext/pcre/pcrelib/testdata/testinput4
+++ b/ext/pcre/pcrelib/testdata/testinput4
@@ -1,6 +1,8 @@
/-- This set of tests is for UTF support, excluding Unicode properties. It is
compatible with all versions of Perl >= 5.10 and both the 8-bit and 16-bit
PCRE libraries. --/
+
+< forbid 9?=ABCDEFfGILMNPTUWXZ<
/a.b/8
acb
@@ -621,4 +623,97 @@
/a(*:a£b)/8K
abc
+/-- Noncharacters --/
+
+/./8
+ \x{fffe}
+ \x{ffff}
+ \x{1fffe}
+ \x{1ffff}
+ \x{2fffe}
+ \x{2ffff}
+ \x{3fffe}
+ \x{3ffff}
+ \x{4fffe}
+ \x{4ffff}
+ \x{5fffe}
+ \x{5ffff}
+ \x{6fffe}
+ \x{6ffff}
+ \x{7fffe}
+ \x{7ffff}
+ \x{8fffe}
+ \x{8ffff}
+ \x{9fffe}
+ \x{9ffff}
+ \x{afffe}
+ \x{affff}
+ \x{bfffe}
+ \x{bffff}
+ \x{cfffe}
+ \x{cffff}
+ \x{dfffe}
+ \x{dffff}
+ \x{efffe}
+ \x{effff}
+ \x{ffffe}
+ \x{fffff}
+ \x{10fffe}
+ \x{10ffff}
+ \x{fdd0}
+ \x{fdd1}
+ \x{fdd2}
+ \x{fdd3}
+ \x{fdd4}
+ \x{fdd5}
+ \x{fdd6}
+ \x{fdd7}
+ \x{fdd8}
+ \x{fdd9}
+ \x{fdda}
+ \x{fddb}
+ \x{fddc}
+ \x{fddd}
+ \x{fdde}
+ \x{fddf}
+ \x{fde0}
+ \x{fde1}
+ \x{fde2}
+ \x{fde3}
+ \x{fde4}
+ \x{fde5}
+ \x{fde6}
+ \x{fde7}
+ \x{fde8}
+ \x{fde9}
+ \x{fdea}
+ \x{fdeb}
+ \x{fdec}
+ \x{fded}
+ \x{fdee}
+ \x{fdef}
+
+/^\d*\w{4}/8
+ 1234
+ 123
+
+/^[^b]*\w{4}/8
+ aaaa
+ aaa
+
+/^[^b]*\w{4}/8i
+ aaaa
+ aaa
+
+/^\x{100}*.{4}/8
+ \x{100}\x{100}\x{100}\x{100}
+ \x{100}\x{100}\x{100}
+
+/^\x{100}*.{4}/8i
+ \x{100}\x{100}\x{100}\x{100}
+ \x{100}\x{100}\x{100}
+
+/^a+[a\x{200}]/8
+ aa
+
/-- End of testinput4 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput5 b/ext/pcre/pcrelib/testdata/testinput5
index 642749c315..9e9a22a1a1 100644
--- a/ext/pcre/pcrelib/testdata/testinput5
+++ b/ext/pcre/pcrelib/testdata/testinput5
@@ -1,21 +1,37 @@
/-- This set of tests checks the API, internals, and non-Perl stuff for UTF
support, excluding Unicode properties. However, tests that give different
results in 8-bit and 16-bit modes are excluded (see tests 16 and 17). --/
+
+< forbid W
/\x{110000}/8DZ
+/\o{4200000}/8DZ
+
/\x{ffffffff}/8
+/\o{37777777777}/8
+
/\x{100000000}/8
+/\o{77777777777}/8
+
/\x{d800}/8
+/\o{154000}/8
+
/\x{dfff}/8
+/\o{157777}/8
+
/\x{d7ff}/8
+/\o{153777}/8
+
/\x{e000}/8
+/\o{170000}/8
+
/^\x{100}a\x{1234}/8
\x{100}a\x{1234}bcd
@@ -769,4 +785,7 @@
/\ud800/<JS>8
+/^a+[a\x{200}]/8BZ
+ aa
+
/-- End of testinput5 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput6 b/ext/pcre/pcrelib/testdata/testinput6
index a4bfb3c19b..1e450be04d 100644
--- a/ext/pcre/pcrelib/testdata/testinput6
+++ b/ext/pcre/pcrelib/testdata/testinput6
@@ -1,5 +1,7 @@
/-- This set of tests is for Unicode property support. It is compatible with
Perl >= 5.15. --/
+
+< forbid 9?=ABCDEFfGILMNPTUXZ<
/^\pC\pL\pM\pN\pP\pS\pZ</8
\x7f\x{c0}\x{30f}\x{660}\x{66c}\x{f01}\x{1680}<
@@ -325,12 +327,6 @@
** Failers
abc
-/\p{Lu}/8i
- A
- aZ
- ** Failers
- abc
-
/\p{Ll}/8
a
Az
@@ -425,6 +421,7 @@
/^[\p{Arabic}]/8
\x{06e9}
\x{060b}
+ \x{061c}
** Failers
X\x{06e9}
@@ -882,6 +879,15 @@
\x{1111}\x{ae4c}\x{1111}\x{ae4c}\x{1111}\x{ae4c}X
\x{1111}\x{ae4c}\x{1111}\x{ae4c}\x{1111}\x{ae4c}\x{1111}\x{ae4c}X
+/\X*Z/8Y
+ A\x{300}
+
+/\X*(.)/8Y
+ A\x{1111}\x{ae4c}\x{1169}
+
+/\X?abc/8Y
+\xff\x7f\x00\x00\x03\x00\x41\xcc\x80\x41\x{300}\x61\x62\x63\x00\>06\?
+
/-- --/
/\x{1e9e}+/8i
@@ -1316,4 +1322,166 @@
/\x{017f}+/8i
\x{0053}\x{0073}\x{017f}
+/^\p{Any}*\d{4}/8
+ 1234
+ 123
+
+/^\X*\w{4}/8
+ 1234
+ 123
+
+/^A\s+Z/8W
+ A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+
+/^A[\s]+Z/8W
+ A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+
+/^[[:graph:]]+$/8W
+ Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ ** Failers
+ \x{09}
+ \x{0a}
+ \x{1D}
+ \x{20}
+ \x{85}
+ \x{a0}
+ \x{61c}
+ \x{1680}
+ \x{180e}
+ \x{2028}
+ \x{2029}
+ \x{202f}
+ \x{2065}
+ \x{2066}
+ \x{2067}
+ \x{2068}
+ \x{2069}
+ \x{3000}
+ \x{e0002}
+ \x{e001f}
+ \x{e0080}
+
+/^[[:print:]]+$/8W
+ Space: \x{a0}
+ \x{1680}\x{2000}\x{2001}\x{2002}\x{2003}\x{2004}\x{2005}
+ \x{2006}\x{2007}\x{2008}\x{2009}\x{200a}
+ \x{202f}\x{205f}
+ \x{3000}
+ Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{180e}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{202f}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ ** Failers
+ \x{09}
+ \x{1D}
+ \x{85}
+ \x{61c}
+ \x{2028}
+ \x{2029}
+ \x{2065}
+ \x{2066}
+ \x{2067}
+ \x{2068}
+ \x{2069}
+ \x{e0002}
+ \x{e001f}
+ \x{e0080}
+
+/^[[:punct:]]+$/8W
+ \$+<=>^`|~
+ !\"#%&'()*,-./:;?@[\\]_{}
+ \x{a1}\x{a7}
+ \x{37e}
+ ** Failers
+ abcde
+
+/^[[:^graph:]]+$/8W
+ \x{09}\x{0a}\x{1D}\x{20}\x{85}\x{a0}\x{61c}\x{1680}\x{180e}
+ \x{2028}\x{2029}\x{202f}\x{2065}\x{2066}\x{2067}\x{2068}\x{2069}
+ \x{3000}\x{e0002}\x{e001f}\x{e0080}
+ ** Failers
+ Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+
+/^[[:^print:]]+$/8W
+ \x{09}\x{1D}\x{85}\x{61c}\x{2028}\x{2029}\x{2065}\x{2066}\x{2067}
+ \x{2068}\x{2069}\x{e0002}\x{e001f}\x{e0080}
+ ** Failers
+ Space: \x{a0}
+ \x{1680}\x{2000}\x{2001}\x{2002}\x{2003}\x{2004}\x{2005}
+ \x{2006}\x{2007}\x{2008}\x{2009}\x{200a}
+ \x{202f}\x{205f}
+ \x{3000}
+ Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{180e}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{202f}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+
+/^[[:^punct:]]+$/8W
+ abcde
+ ** Failers
+ \$+<=>^`|~
+ !\"#%&'()*,-./:;?@[\\]_{}
+ \x{a1}\x{a7}
+ \x{37e}
+
/-- End of testinput6 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput7 b/ext/pcre/pcrelib/testdata/testinput7
index b265f1f9ac..9d14543635 100644
--- a/ext/pcre/pcrelib/testdata/testinput7
+++ b/ext/pcre/pcrelib/testdata/testinput7
@@ -100,11 +100,30 @@
/\p{Cc}{2}+/8BZ
+/^\p{Cf}/8
+ \x{180e}
+ \x{061c}
+ \x{2066}
+ \x{2067}
+ \x{2068}
+ \x{2069}
+
/^\p{Cs}/8
\?\x{dfff}
** Failers
\x{09f}
+/^\p{Mn}/8
+ \x{1a1b}
+
+/^\p{Pe}/8
+ \x{2309}
+ \x{230b}
+
+/^\p{Ps}/8
+ \x{2308}
+ \x{230a}
+
/^\p{Sc}+/8
$\x{a2}\x{a3}\x{a4}\x{a5}\x{a6}
\x{9f2}
@@ -116,15 +135,15 @@
\ \
\x{a0}
\x{1680}
- \x{180e}
\x{2000}
\x{2001}
** Failers
\x{2028}
\x{200d}
-/-- These four are here rather than in test 6 because Perl has problems with
- the negative versions of the properties. --/
+/-- These are here rather than in test 6 because Perl has problems with
+ the negative versions of the properties and behaves has changed how
+ it behaves for caseless matching. --/
/\p{^Lu}/8i
1234
@@ -149,6 +168,12 @@
a
\x{1d00}
+/\p{Lu}/8i
+ A
+ aZ
+ ** Failers
+ abc
+
/[\x{c0}\x{391}]/8i
\x{c0}
\x{e0}
@@ -668,5 +693,140 @@ of case for anything other than the ASCII letters. --/
/is{2}t/8i
iskt
+
+/-- This property is a PCRE special --/
+
+/^\p{Xuc}/8
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+ ** Failers
+ abc
+
+/^\p{Xuc}+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}+?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}+?\*/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}++/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}{3,5}/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\p{Xuc}{3,5}?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^[\p{Xuc}]/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^[\p{Xuc}]+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ ** Failers
+ \x{9f}
+
+/^\P{Xuc}/8
+ abc
+ ** Failers
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+
+/^[\P{Xuc}]/8
+ abc
+ ** Failers
+ $abc
+ @abc
+ `abc
+ \x{1234}abc
+
+/-- Some auto-possessification tests --/
+
+/\pN+\z/BZ
+
+/\PN+\z/BZ
+
+/\pN+/BZ
+
+/\PN+/BZ
+
+/\p{Any}+\p{Any} \p{Any}+\P{Any} \p{Any}+\p{L&} \p{Any}+\p{L} \p{Any}+\p{Lu} \p{Any}+\p{Han} \p{Any}+\p{Xan} \p{Any}+\p{Xsp} \p{Any}+\p{Xps} \p{Xwd}+\p{Any} \p{Any}+\p{Xuc}/BWZx
+
+/\p{L&}+\p{Any} \p{L&}+\p{L&} \P{L&}+\p{L&} \p{L&}+\p{L} \p{L&}+\p{Lu} \p{L&}+\p{Han} \p{L&}+\p{Xan} \p{L&}+\P{Xan} \p{L&}+\p{Xsp} \p{L&}+\p{Xps} \p{Xwd}+\p{L&} \p{L&}+\p{Xuc}/BWZx
+
+/\p{N}+\p{Any} \p{N}+\p{L&} \p{N}+\p{L} \p{N}+\P{L} \p{N}+\P{N} \p{N}+\p{Lu} \p{N}+\p{Han} \p{N}+\p{Xan} \p{N}+\p{Xsp} \p{N}+\p{Xps} \p{Xwd}+\p{N} \p{N}+\p{Xuc}/BWZx
+
+/\p{Lu}+\p{Any} \p{Lu}+\p{L&} \p{Lu}+\p{L} \p{Lu}+\p{Lu} \P{Lu}+\p{Lu} \p{Lu}+\p{Nd} \p{Lu}+\P{Nd} \p{Lu}+\p{Han} \p{Lu}+\p{Xan} \p{Lu}+\p{Xsp} \p{Lu}+\p{Xps} \p{Xwd}+\p{Lu} \p{Lu}+\p{Xuc}/BWZx
+
+/\p{Han}+\p{Lu} \p{Han}+\p{L&} \p{Han}+\p{L} \p{Han}+\p{Lu} \p{Han}+\p{Arabic} \p{Arabic}+\p{Arabic} \p{Han}+\p{Xan} \p{Han}+\p{Xsp} \p{Han}+\p{Xps} \p{Xwd}+\p{Han} \p{Han}+\p{Xuc}/BWZx
+
+/\p{Xan}+\p{Any} \p{Xan}+\p{L&} \P{Xan}+\p{L&} \p{Xan}+\p{L} \p{Xan}+\p{Lu} \p{Xan}+\p{Han} \p{Xan}+\p{Xan} \p{Xan}+\P{Xan} \p{Xan}+\p{Xsp} \p{Xan}+\p{Xps} \p{Xwd}+\p{Xan} \p{Xan}+\p{Xuc}/BWZx
+
+/\p{Xsp}+\p{Any} \p{Xsp}+\p{L&} \p{Xsp}+\p{L} \p{Xsp}+\p{Lu} \p{Xsp}+\p{Han} \p{Xsp}+\p{Xan} \p{Xsp}+\p{Xsp} \P{Xsp}+\p{Xsp} \p{Xsp}+\p{Xps} \p{Xwd}+\p{Xsp} \p{Xsp}+\p{Xuc}/BWZx
+
+/\p{Xwd}+\p{Any} \p{Xwd}+\p{L&} \p{Xwd}+\p{L} \p{Xwd}+\p{Lu} \p{Xwd}+\p{Han} \p{Xwd}+\p{Xan} \p{Xwd}+\p{Xsp} \p{Xwd}+\p{Xps} \p{Xwd}+\p{Xwd} \p{Xwd}+\P{Xwd} \p{Xwd}+\p{Xuc}/BWZx
+
+/\p{Xuc}+\p{Any} \p{Xuc}+\p{L&} \p{Xuc}+\p{L} \p{Xuc}+\p{Lu} \p{Xuc}+\p{Han} \p{Xuc}+\p{Xan} \p{Xuc}+\p{Xsp} \p{Xuc}+\p{Xps} \p{Xwd}+\p{Xuc} \p{Xuc}+\p{Xuc} \p{Xuc}+\P{Xuc}/BWZx
+
+/\p{N}+\p{Ll} \p{N}+\p{Nd} \p{N}+\P{Nd}/BWZx
+
+/\p{Xan}+\p{L} \p{Xan}+\p{N} \p{Xan}+\p{C} \p{Xan}+\P{L} \P{Xan}+\p{N} \p{Xan}+\P{C}/BWZx
+
+/\p{L}+\p{Xan} \p{N}+\p{Xan} \p{C}+\p{Xan} \P{L}+\p{Xan} \p{N}+\p{Xan} \P{C}+\p{Xan} \p{L}+\P{Xan}/BWZx
+
+/\p{Xan}+\p{Lu} \p{Xan}+\p{Nd} \p{Xan}+\p{Cc} \p{Xan}+\P{Ll} \P{Xan}+\p{No} \p{Xan}+\P{Cf}/BWZx
+
+/\p{Lu}+\p{Xan} \p{Nd}+\p{Xan} \p{Cs}+\p{Xan} \P{Lt}+\p{Xan} \p{Nl}+\p{Xan} \P{Cc}+\p{Xan} \p{Lt}+\P{Xan}/BWZx
+
+/\w+\p{P} \w+\p{Po} \w+\s \p{Xan}+\s \s+\p{Xan} \s+\w/BWZx
+
+/\w+\P{P} \W+\p{Po} \w+\S \P{Xan}+\s \s+\P{Xan} \s+\W/BWZx
+
+/\w+\p{Po} \w+\p{Pc} \W+\p{Po} \W+\p{Pc} \w+\P{Po} \w+\P{Pc}/BWZx
+
+/\p{Nl}+\p{Xan} \P{Nl}+\p{Xan} \p{Nl}+\P{Xan} \P{Nl}+\P{Xan}/BWZx
+
+/\p{Xan}+\p{Nl} \P{Xan}+\p{Nl} \p{Xan}+\P{Nl} \P{Xan}+\P{Nl}/BWZx
+
+/\p{Xan}+\p{Nd} \P{Xan}+\p{Nd} \p{Xan}+\P{Nd} \P{Xan}+\P{Nd}/BWZx
+
+/-- End auto-possessification tests --/
+
+/\w+/8CWBZ
+ abcd
+
+/[\p{N}]?+/BZO
+
+/[\p{L}ab]{2,3}+/BZO
+
+/\D+\X \d+\X \S+\X \s+\X \W+\X \w+\X \C+\X \R+\X \H+\X \h+\X \V+\X \v+\X a+\X \n+\X .+\X/BZx
+
+/.+\X/BZxs
+
+/\X+$/BZxm
+
+/\X+\D \X+\d \X+\S \X+\s \X+\W \X+\w \X+. \X+\C \X+\R \X+\H \X+\h \X+\V \X+\v \X+\X \X+\Z \X+\z \X+$/BZx
+
+/\d+\s{0,5}=\s*\S?=\w{0,4}\W*/8WBZ
/-- End of testinput7 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput8 b/ext/pcre/pcrelib/testdata/testinput8
index e235445e01..bb2747b120 100644
--- a/ext/pcre/pcrelib/testdata/testinput8
+++ b/ext/pcre/pcrelib/testdata/testinput8
@@ -1,5 +1,8 @@
-/-- This set of tests check the DFA matching functionality of pcre_dfa_exec().
- The -dfa flag must be used with pcretest when running it. --/
+/-- This set of tests check the DFA matching functionality of pcre_dfa_exec(),
+ excluding UTF and Unicode property support. The -dfa flag must be used with
+ pcretest when running it. --/
+
+< forbid 8W
/abc/
abc
@@ -16,7 +19,7 @@
ac
ab
-/a*/
+/a*/O
a
aaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -177,19 +180,19 @@
ayzq
axyzq
-/[^a]+/
+/[^a]+/O
bac
bcdefax
*** Failers
aaaaa
-/[^a]*/
+/[^a]*/O
bac
bcdefax
*** Failers
aaaaa
-/[^a]{3,5}/
+/[^a]{3,5}/O
xyz
awxyza
abcdefa
@@ -937,16 +940,16 @@
*** Failers
the abc
-/^[ab]{1,3}(ab*|b)/
+/^[ab]{1,3}(ab*|b)/O
aabbbbb
-/^[ab]{1,3}?(ab*|b)/
+/^[ab]{1,3}?(ab*|b)/O
aabbbbb
-/^[ab]{1,3}?(ab*?|b)/
+/^[ab]{1,3}?(ab*?|b)/O
aabbbbb
-/^[ab]{1,3}(ab*?|b)/
+/^[ab]{1,3}(ab*?|b)/O
aabbbbb
/ (?: [\040\t] | \(
@@ -1923,14 +1926,16 @@
abc\100\060
abc\100\60
-/abc\81/
- abc\081
- abc\0\x38\x31
-
-/abc\91/
- abc\091
- abc\0\x39\x31
-
+/^A\8B\9C$/
+ A8B9C
+ *** Failers
+ A\08B\09C
+
+/^[A\8B\9C]+$/
+ A8B9C
+ *** Failers
+ A8B9C\x00
+
/(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k)\12\123/
abcdefghijk\12S
@@ -2049,13 +2054,13 @@
/foo(.*?)bar/
The food is under the bar in the barn.
-/(.*)(\d*)/
+/(.*)(\d*)/O
I have 2 numbers: 53147
/(.*)(\d+)/
I have 2 numbers: 53147
-/(.*?)(\d*)/
+/(.*?)(\d*)/O
I have 2 numbers: 53147
/(.*?)(\d+)/
@@ -3825,13 +3830,6 @@
/a*/g
abbab
-/^[a-\d]/
- abcde
- -things
- 0digit
- *** Failers
- bcdef
-
/^[\d-a]/
abcde
-things
@@ -4699,7 +4697,7 @@
/(?(R)a*(?1)|((?R))b)/
aaaabcde
-/(a+)/
+/(a+)/O
\O6aaaa
\O8aaaa
@@ -4798,4 +4796,39 @@
xxxxxxxxabcd
xx\xa0xxxxxabcd
+/abcd/
+ abcd\O0
+
+/-- These tests show up auto-possessification --/
+
+/[ab]*/
+ aaaa
+
+/[ab]*?/
+ aaaa
+
+/[ab]?/
+ aaaa
+
+/[ab]??/
+ aaaa
+
+/[ab]+/
+ aaaa
+
+/[ab]+?/
+ aaaa
+
+/[ab]{2,3}/
+ aaaa
+
+/[ab]{2,3}?/
+ aaaa
+
+/[ab]{2,}/
+ aaaa
+
+/[ab]{2,}?/
+ aaaa
+
/-- End of testinput8 --/
diff --git a/ext/pcre/pcrelib/testdata/testinput9 b/ext/pcre/pcrelib/testdata/testinput9
index 766c9c0fb6..4575ffe319 100644
--- a/ext/pcre/pcrelib/testdata/testinput9
+++ b/ext/pcre/pcrelib/testdata/testinput9
@@ -1,6 +1,8 @@
/-- This set of tests checks UTF-8 support with the DFA matching functionality
- of pcre_dfa_exec(). The -dfa flag must be used with pcretest when running
- it. --/
+ of pcre_dfa_exec(), excluding Unicode property support. The -dfa flag must
+ be used with pcretest when running it. --/
+
+< forbid W
/\x{100}ab/8
\x{100}ab
@@ -239,16 +241,16 @@
/\x{100}{3,5}/8
abcd\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}XX
-/\x{100}{3,}/8
+/\x{100}{3,}/8O
abcd\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}XX
/(?<=a\x{100}{2}b)X/8
Xyyya\x{100}\x{100}bXzzz
-/\D*/8
+/\D*/8O
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/\D*/8
+/\D*/8O
\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
/\D/8
@@ -584,16 +586,16 @@
a\n\n\n\rb
a\r
-/\h+\V?\v{3,4}/8
+/\h+\V?\v{3,4}/8O
\x09\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
-/\V?\v{3,4}/8
+/\V?\v{3,4}/8O
\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
-/\h+\V?\v{3,4}/8
+/\h+\V?\v{3,4}/8O
>\x09\x20\x{a0}X\x0a\x0a\x0a<
-/\V?\v{3,4}/8
+/\V?\v{3,4}/8O
>\x09\x20\x{a0}X\x0a\x0a\x0a<
/\H\h\V\v/8
@@ -602,7 +604,7 @@
** Failers
\x{a0} X\x0a
-/\H*\h+\V?\v{3,4}/8
+/\H*\h+\V?\v{3,4}/8O
\x09\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
\x09\x20\x{a0}\x0a\x0b\x0c\x0d\x0a
\x09\x20\x{a0}\x0a\x0b\x0c
@@ -615,7 +617,7 @@
** Failers
\x{2009} X\x0a
-/\H*\h+\V?\v{3,4}/8
+/\H*\h+\V?\v{3,4}/8O
\x{1680}\x{180e}\x{2007}X\x{2028}\x{2029}\x0c\x0d\x0a
\x09\x{205f}\x{a0}\x0a\x{2029}\x0c\x{2028}\x0a
\x09\x20\x{202f}\x0a\x0b\x0c
diff --git a/ext/pcre/pcrelib/testdata/testinputEBC b/ext/pcre/pcrelib/testdata/testinputEBC
new file mode 100644
index 0000000000..56efcd00aa
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testinputEBC
@@ -0,0 +1,121 @@
+/-- This is a specialized test for checking, when PCRE is compiled with the
+EBCDIC option but in an ASCII environment, that newline and white space
+functionality is working. It catches cases where explicit values such as 0x0a
+have been used instead of names like CHAR_LF. Needless to say, it is not a
+genuine EBCDIC test! In patterns, alphabetic characters that follow a backslash
+must be in EBCDIC code. In data, newlines and other spacing characters must be
+in EBCDIC, but can be specified as escapes. --/
+
+/-- Test default newline and variations --/
+
+/^A/m
+ ABC
+ 12\x15ABC
+
+/^A/m<any>
+ 12\x15ABC
+ 12\x0dABC
+ 12\x0d\x15ABC
+ 12\x25ABC
+
+/^A/m<anycrlf>
+ 12\x15ABC
+ 12\x0dABC
+ 12\x0d\x15ABC
+ ** Fail
+ 12\x25ABC
+
+/-- Test \h --/
+
+/^A\ˆ/
+ A B
+
+/-- Test \H --/
+
+/^A\È/
+ AB
+ ** Fail
+ A B
+
+/-- Test \R --/
+
+/^A\Ù/
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+ ** Fail
+ A B
+
+/-- Test \v --/
+
+/^A\¥/
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+ ** Fail
+ A B
+
+/-- Test \V --/
+
+/^A\å/
+ A B
+ ** Fail
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+
+/-- For repeated items, use an atomic group so that the output is the same
+for DFA matching (otherwise it may show multiple matches). --/
+
+/-- Test \h+ --/
+
+/^A(?>\ˆ+)/
+ A B
+
+/-- Test \H+ --/
+
+/^A(?>\È+)/
+ AB
+ ** Fail
+ A B
+
+/-- Test \R+ --/
+
+/^A(?>\Ù+)/
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+ ** Fail
+ A B
+
+/-- Test \v+ --/
+
+/^A(?>\¥+)/
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+ ** Fail
+ A B
+
+/-- Test \V+ --/
+
+/^A(?>\å+)/
+ A B
+ ** Fail
+ A\x15B
+ A\x0dB
+ A\x25B
+ A\x0bB
+ A\x0cB
+
+/-- End --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput1 b/ext/pcre/pcrelib/testdata/testoutput1
index 8310e94618..4dafc0496a 100644
--- a/ext/pcre/pcrelib/testdata/testoutput1
+++ b/ext/pcre/pcrelib/testdata/testoutput1
@@ -1,6 +1,8 @@
/-- This set of tests is for features that are compatible with all versions of
- Perl >= 5.10, in non-UTF-8 mode. It should run clean for both the 8-bit and
- 16-bit PCRE libraries. --/
+ Perl >= 5.10, in non-UTF-8 mode. It should run clean for the 8-bit, 16-bit,
+ and 32-bit PCRE libraries. --/
+
+< forbid 89?=ABCDEFfGILMNPTUWXZ<
/the quick brown fox/
the quick brown fox
@@ -2149,18 +2151,35 @@ No match
abc\100\60
0: abc@0
1: abc
-
-/abc\81/
- abc\081
- 0: abc\x0081
- abc\0\x38\x31
- 0: abc\x0081
-
-/abc\91/
- abc\091
- 0: abc\x0091
- abc\0\x39\x31
- 0: abc\x0091
+
+/^A\8B\9C$/
+ A8B9C
+ 0: A8B9C
+ *** Failers
+No match
+ A\08B\09C
+No match
+
+/^(A)(B)(C)(D)(E)(F)(G)(H)(I)\8\9$/
+ ABCDEFGHIHI
+ 0: ABCDEFGHIHI
+ 1: A
+ 2: B
+ 3: C
+ 4: D
+ 5: E
+ 6: F
+ 7: G
+ 8: H
+ 9: I
+
+/^[A\8B\9C]+$/
+ A8B9C
+ 0: A8B9C
+ *** Failers
+No match
+ A8B9C\x00
+No match
/(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k)(l)\12\123/
abcdefghijkllS
@@ -5972,18 +5991,6 @@ No match
0:
0:
-/^[a-\d]/
- abcde
- 0: a
- -things
- 0: -
- 0digit
- 0: 0
- *** Failers
-No match
- bcdef
-No match
-
/^[\d-a]/
abcde
0: a
@@ -6006,15 +6013,15 @@ No match
/[\s]+/
> \x09\x0a\x0c\x0d\x0b<
- 0: \x09\x0a\x0c\x0d
+ 0: \x09\x0a\x0c\x0d\x0b
/\s+/
> \x09\x0a\x0c\x0d\x0b<
- 0: \x09\x0a\x0c\x0d
+ 0: \x09\x0a\x0c\x0d\x0b
/a b/x
ab
-No match
+ 0: ab
/(?!\A)x/m
a\nxb\n
@@ -6160,11 +6167,9 @@ No match
1: bc
2: bc
-/-- This tests for an IPv6 address in the form where it can have up to --/
-/-- eight components, one and only one of which is empty. This must be --/
-No match
-/-- an internal component. --/
-No match
+/-- This tests for an IPv6 address in the form where it can have up to
+ eight components, one and only one of which is empty. This must be
+ an internal component. --/
/^(?!:) # colon disallowed at start
(?: # start of item
@@ -6906,10 +6911,6 @@ No match
bc
0: b
-/^(?=(a)){0}b(?1)/
- backgammon
- 0: ba
-
/^(?=(?1))?[az]([abc])d/
abd
0: abd
@@ -7770,20 +7771,12 @@ No match
1: (ab(cd)ef)
2: ef
-/^(?!a(*SKIP)b)/
- ac
- 0:
-
/^(?=a(*SKIP)b|ac)/
** Failers
No match
ac
No match
-/^(?=a(*THEN)b|ac)/
- ac
- 0:
-
/^(?=a(*PRUNE)b)/
ab
0:
@@ -7796,10 +7789,6 @@ No match
ac
0:
-/^(?(?!a(*SKIP)b))/
- ac
- 0:
-
/(?>a\Kb)/
ab
0: b
@@ -8169,46 +8158,20 @@ No match
1: AB
2: B
-/\A.*?(?:a|b(*THEN)c)/
- ba
- 0: ba
-
-/\A.*?(?:a|bc)/
- ba
- 0: ba
-
-/\A.*?(a|b(*THEN)c)/
- ba
- 0: ba
- 1: a
-
/\A.*?(a|bc)/
ba
0: ba
1: a
-/\A.*?(?:a|b(*THEN)c)++/
- ba
- 0: ba
-
/\A.*?(?:a|bc)++/
ba
0: ba
-/\A.*?(a|b(*THEN)c)++/
- ba
- 0: ba
- 1: a
-
/\A.*?(a|bc)++/
ba
0: ba
1: a
-/\A.*?(?:a|b(*THEN)c|d)/
- ba
- 0: ba
-
/\A.*?(?:a|bc|d)/
ba
0: ba
@@ -8719,10 +8682,6 @@ No match
aac
0: aac
-/(?!a(*COMMIT)b)ac|cd/
- ac
- 0: ac
-
/((?:a?)*)*c/
aac
0: aac
@@ -8795,4 +8754,563 @@ No match
abcdfooxyz
0: foo
+/(?:(a(*PRUNE)b)){0}(?:(?1)|ac)/
+ ac
+ 0: ac
+
+/(?:(a(*SKIP)b)){0}(?:(?1)|ac)/
+ ac
+ 0: ac
+
+/(?<=(*SKIP)ac)a/
+ aa
+No match
+
+/A(*MARK:A)A+(*SKIP:B)(B|Z) | AC/xK
+ AAAC
+ 0: AC
+
+/a(*SKIP:m)x|ac(*:n)(*SKIP:n)d|ac/K
+ acacd
+ 0: acd
+MK: n
+
+/A(*SKIP:m)x|A(*SKIP:n)x|AB/K
+ AB
+ 0: AB
+
+/((*SKIP:r)d){0}a(*SKIP:m)x|ac(*:n)|ac/K
+ acacd
+ 0: ac
+MK: n
+
+/-- Tests that try to figure out how Perl works. My hypothesis is that the
+ first verb that is backtracked onto is the one that acts. This seems to be
+ the case almost all the time, but there is one exception that is perhaps a
+ bug. --/
+
+/-- This matches "aaaac"; each PRUNE advances one character until the subject
+ no longer starts with 5 'a's. --/
+
+/aaaaa(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/-- Putting SKIP in front of PRUNE makes no difference, as it is never
+backtracked onto, whether or not it has a label. --/
+
+/aaaaa(*SKIP)(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/aaaaa(*SKIP:N)(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/aaaa(*:N)a(*SKIP:N)(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/-- Putting THEN in front makes no difference. */
+
+/aaaaa(*THEN)(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/-- However, putting COMMIT in front of the prune changes it to "no match". I
+ think this is inconsistent and possibly a bug. For the moment, running this
+ test is moved out of the Perl-compatible file. --/
+
+/aaaaa(*COMMIT)(*PRUNE)b|a+c/
+
+
+/---- OK, lets play the same game again using SKIP instead of PRUNE. ----/
+
+/-- This matches "ac" because SKIP forces the next match to start on the
+ sixth "a". --/
+
+/aaaaa(*SKIP)b|a+c/
+ aaaaaac
+ 0: ac
+
+/-- Putting PRUNE in front makes no difference. --/
+
+/aaaaa(*PRUNE)(*SKIP)b|a+c/
+ aaaaaac
+ 0: ac
+
+/-- Putting THEN in front makes no difference. --/
+
+/aaaaa(*THEN)(*SKIP)b|a+c/
+ aaaaaac
+ 0: ac
+
+/-- In this case, neither does COMMIT. This still matches "ac". --/
+
+/aaaaa(*COMMIT)(*SKIP)b|a+c/
+ aaaaaac
+ 0: ac
+
+/-- This gives "no match", as expected. --/
+
+/aaaaa(*COMMIT)b|a+c/
+ aaaaaac
+No match
+
+
+/------ Tests using THEN ------/
+
+/-- This matches "aaaaaac", as expected. --/
+
+/aaaaa(*THEN)b|a+c/
+ aaaaaac
+ 0: aaaaaac
+
+/-- Putting SKIP in front makes no difference. --/
+
+/aaaaa(*SKIP)(*THEN)b|a+c/
+ aaaaaac
+ 0: aaaaaac
+
+/-- Putting PRUNE in front makes no difference. --/
+
+/aaaaa(*PRUNE)(*THEN)b|a+c/
+ aaaaaac
+ 0: aaaaaac
+
+/-- Putting COMMIT in front makes no difference. --/
+
+/aaaaa(*COMMIT)(*THEN)b|a+c/
+ aaaaaac
+ 0: aaaaaac
+
+/-- End of "priority" tests --/
+
+/aaaaa(*:m)(*PRUNE:m)(*SKIP:m)m|a+/
+ aaaaaa
+ 0: a
+
+/aaaaa(*:m)(*MARK:m)(*PRUNE)(*SKIP:m)m|a+/
+ aaaaaa
+ 0: a
+
+/aaaaa(*:n)(*PRUNE:m)(*SKIP:m)m|a+/
+ aaaaaa
+ 0: aaaa
+
+/aaaaa(*:n)(*MARK:m)(*PRUNE)(*SKIP:m)m|a+/
+ aaaaaa
+ 0: a
+
+/a(*MARK:A)aa(*PRUNE:A)a(*SKIP:A)b|a+c/
+ aaaac
+ 0: aac
+
+/a(*MARK:A)aa(*MARK:A)a(*SKIP:A)b|a+c/
+ aaaac
+ 0: ac
+
+/aaa(*PRUNE:A)a(*SKIP:A)b|a+c/
+ aaaac
+ 0: aac
+
+/aaa(*MARK:A)a(*SKIP:A)b|a+c/
+ aaaac
+ 0: ac
+
+/a(*:m)a(*COMMIT)(*SKIP:m)b|a+c/K
+ aaaaaac
+ 0: ac
+
+/.?(a|b(*THEN)c)/
+ ba
+ 0: ba
+ 1: a
+
+/(a(*COMMIT)b)c|abd/
+ abc
+ 0: abc
+ 1: ab
+ abd
+No match
+
+/(?=a(*COMMIT)b)abc|abd/
+ abc
+ 0: abc
+ abd
+ 0: abd
+
+/(?>a(*COMMIT)b)c|abd/
+ abc
+ 0: abc
+ abd
+ 0: abd
+
+/a(?=b(*COMMIT)c)[^d]|abd/
+ abd
+No match
+ abc
+ 0: ab
+
+/a(?=bc).|abd/
+ abd
+ 0: abd
+ abc
+ 0: ab
+
+/a(?>b(*COMMIT)c)d|abd/
+ abceabd
+No match
+
+/a(?>bc)d|abd/
+ abceabd
+ 0: abd
+
+/(?>a(*COMMIT)b)c|abd/
+ abd
+ 0: abd
+
+/(?>a(*COMMIT)c)d|abd/
+ abd
+No match
+
+/((?=a(*COMMIT)b)ab|ac){0}(?:(?1)|a(c))/
+ ac
+ 0: ac
+ 1: <unset>
+ 2: c
+
+/-- These tests were formerly in test 2, but changes in PCRE and Perl have
+ made them compatible. --/
+
+/^(a)?(?(1)a|b)+$/
+ *** Failers
+No match
+ a
+No match
+
+/(?=a\Kb)ab/
+ ab
+ 0: b
+
+/(?!a\Kb)ac/
+ ac
+ 0: ac
+
+/^abc(?<=b\Kc)d/
+ abcd
+ 0: cd
+
+/^abc(?<!b\Kq)d/
+ abcd
+ 0: abcd
+
+
+/A(*PRUNE:A)A+(*SKIP:A)(B|Z) | AC/xK
+ AAAC
+No match, mark = A
+
+/^((abc|abcx)(*THEN)y|abcd)/
+ abcd
+ 0: abcd
+ 1: abcd
+ *** Failers
+No match
+ abcxy
+No match
+
+/^((yes|no)(*THEN)(*F))?/
+ yes
+No match
+
+/(A (.*) C? (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) C? (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) C? (*THEN) | A D) \s* (*FAIL)/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) C? (*THEN) | A D) \s* z/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) (?:C|) (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) (?:C|) (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) C{0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) C{0,6} (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) (CE){0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCEBefgBhiBqz
+No match
+
+/(A (.*) (CE){0,6} (*THEN) | A D) z/x
+AbcdCEBefgBhiBqz
+No match
+
+/(A (.*) (CE*){0,6} (*THEN) | A D) (*FAIL)/x
+AbcdCBefgBhiBqz
+No match
+
+/(A (.*) (CE*){0,6} (*THEN) | A D) z/x
+AbcdCBefgBhiBqz
+No match
+
+/(?=a(*COMMIT)b|ac)ac|ac/
+ ac
+No match
+
+/(?=a(*COMMIT)b|(ac)) ac | (a)c/x
+ ac
+No match
+
+/--------/
+
+/(?(?!b(*THEN)a)bn|bnn)/
+ bnn
+ 0: bn
+
+/(?!b(*SKIP)a)bn|bnn/
+ bnn
+ 0: bn
+
+/(?(?!b(*SKIP)a)bn|bnn)/
+ bnn
+ 0: bn
+
+/(?!b(*PRUNE)a)bn|bnn/
+ bnn
+ 0: bn
+
+/(?(?!b(*PRUNE)a)bn|bnn)/
+ bnn
+ 0: bn
+
+/(?!b(*COMMIT)a)bn|bnn/
+ bnn
+ 0: bn
+
+/(?(?!b(*COMMIT)a)bn|bnn)/
+ bnn
+ 0: bn
+
+/(?=b(*SKIP)a)bn|bnn/
+ bnn
+No match
+
+/(?=b(*THEN)a)bn|bnn/
+ bnn
+ 0: bnn
+
+ /^(?!a(*SKIP)b)/
+ ac
+ 0:
+
+ /^(?!a(*SKIP)b)../
+ acd
+ 0: ac
+
+/(?!a(*SKIP)b)../
+ acd
+ 0: ac
+
+/^(?(?!a(*SKIP)b))/
+ ac
+ 0:
+
+/^(?!a(*PRUNE)b)../
+ acd
+ 0: ac
+
+/(?!a(*PRUNE)b)../
+ acd
+ 0: ac
+
+ /(?!a(*COMMIT)b)ac|cd/
+ ac
+ 0: ac
+
+/\A.*?(?:a|bc)/
+ ba
+ 0: ba
+
+/^(A(*THEN)B|C(*THEN)D)/
+ CD
+ 0: CD
+ 1: CD
+
+/(*:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+ 0: b
+MK: m(m
+
+/(*PRUNE:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+ 0: b
+MK: m(m
+
+/(*SKIP:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+ 0: b
+
+/(*THEN:m(m)(?&y)(?(DEFINE)(?<y>b))/K
+ abc
+ 0: b
+MK: m(m
+
+/^\d*\w{4}/
+ 1234
+ 0: 1234
+ 123
+No match
+
+/^[^b]*\w{4}/
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/^[^b]*\w{4}/i
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/^a*\w{4}/
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/^a*\w{4}/i
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/(?(?=ab)ab)/+
+ ca
+ 0:
+ 0+ ca
+ cd
+ 0:
+ 0+ cd
+
+/(?:(?<n>foo)|(?<n>bar))\k<n>/J
+ foofoo
+ 0: foofoo
+ 1: foo
+ barbar
+ 0: barbar
+ 1: <unset>
+ 2: bar
+
+/(?<n>A)(?:(?<n>foo)|(?<n>bar))\k<n>/J
+ AfooA
+ 0: AfooA
+ 1: A
+ 2: foo
+ AbarA
+ 0: AbarA
+ 1: A
+ 2: <unset>
+ 3: bar
+ ** Failers
+No match
+ Afoofoo
+No match
+ Abarbar
+No match
+
+/^(\d+)\s+IN\s+SOA\s+(\S+)\s+(\S+)\s*\(\s*$/
+ 1 IN SOA non-sp1 non-sp2(
+ 0: 1 IN SOA non-sp1 non-sp2(
+ 1: 1
+ 2: non-sp1
+ 3: non-sp2
+
+/^ (?:(?<A>A)|(?'B'B)(?<A>A)) (?('A')x) (?(<B>)y)$/xJ
+ Ax
+ 0: Ax
+ 1: A
+ BAxy
+ 0: BAxy
+ 1: <unset>
+ 2: B
+ 3: A
+
+/^A\xZ/
+ A\0Z
+ 0: A\x00Z
+
+/^A\o{123}B/
+ A\123B
+ 0: ASB
+
+/ ^ a + + b $ /x
+ aaaab
+ 0: aaaab
+
+/ ^ a + #comment
+ + b $ /x
+ aaaab
+ 0: aaaab
+
+/ ^ a + #comment
+ #comment
+ + b $ /x
+ aaaab
+ 0: aaaab
+
+/ ^ (?> a + ) b $ /x
+ aaaab
+ 0: aaaab
+
+/ ^ ( a + ) + + \w $ /x
+ aaaab
+ 0: aaaab
+ 1: aaaa
+
+/(?:a\Kb)*+/+
+ ababc
+ 0: b
+ 0+ c
+
+/(?>a\Kb)*/+
+ ababc
+ 0: b
+ 0+ c
+
+/(?:a\Kb)*/+
+ ababc
+ 0: b
+ 0+ c
+
+/(a\Kb)*+/+
+ ababc
+ 0: b
+ 0+ c
+ 1: ab
+
+/(a\Kb)*/+
+ ababc
+ 0: b
+ 0+ c
+ 1: ab
+
/-- End of testinput1 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput10 b/ext/pcre/pcrelib/testdata/testoutput10
index 049d446314..b89169cdd3 100644
--- a/ext/pcre/pcrelib/testdata/testoutput10
+++ b/ext/pcre/pcrelib/testdata/testoutput10
@@ -39,9 +39,6 @@ No match
/^\pL+/8
abcd
0: abcd
- 1: abc
- 2: ab
- 3: a
a
0: a
*** Failers
@@ -50,45 +47,24 @@ No match
/^\PL+/8
1234
0: 1234
- 1: 123
- 2: 12
- 3: 1
=
0: =
*** Failers
0: ***
- 1: ***
- 2: **
- 3: *
abcd
No match
/^\X+/8
abcdA\x{300}\x{301}\x{302}
0: abcdA\x{300}\x{301}\x{302}
- 1: abcd
- 2: abc
- 3: ab
- 4: a
A\x{300}\x{301}\x{302}
0: A\x{300}\x{301}\x{302}
A\x{300}\x{301}\x{302}A\x{300}\x{301}\x{302}
0: A\x{300}\x{301}\x{302}A\x{300}\x{301}\x{302}
- 1: A\x{300}\x{301}\x{302}
a
0: a
*** Failers
0: *** Failers
- 1: *** Failer
- 2: *** Faile
- 3: *** Fail
- 4: *** Fai
- 5: *** Fa
- 6: *** F
- 7: ***
- 8: ***
- 9: **
-10: *
\x{300}\x{301}\x{302}
0: \x{300}\x{301}\x{302}
@@ -255,6 +231,18 @@ No match
/^\p{Cf}/8
\x{601}
0: \x{601}
+ \x{180e}
+ 0: \x{180e}
+ \x{061c}
+ 0: \x{61c}
+ \x{2066}
+ 0: \x{2066}
+ \x{2067}
+ 0: \x{2067}
+ \x{2068}
+ 0: \x{2068}
+ \x{2069}
+ 0: \x{2069}
** Failers
No match
\x{09f}
@@ -353,6 +341,8 @@ No match
/^\p{Mn}/8
\x{300}
0: \x{300}
+ \x{1a1b}
+ 0: \x{1a1b}
** Failers
No match
X
@@ -360,7 +350,7 @@ No match
\x{903}
No match
-/^\p{Nd}+/8
+/^\p{Nd}+/8O
0123456789\x{660}\x{661}\x{662}\x{663}\x{664}\x{665}\x{666}\x{667}\x{668}\x{669}\x{66a}
0: 0123456789\x{660}\x{661}\x{662}\x{663}\x{664}\x{665}\x{666}\x{667}\x{668}\x{669}
1: 0123456789\x{660}\x{661}\x{662}\x{663}\x{664}\x{665}\x{666}\x{667}\x{668}
@@ -466,6 +456,10 @@ No match
0: }
\x{f3b}
0: \x{f3b}
+ \x{2309}
+ 0: \x{2309}
+ \x{230b}
+ 0: \x{230b}
** Failers
No match
X
@@ -480,7 +474,7 @@ No match
No match
\x{f3c}
No match
-
+
/^\p{Pf}/8
\x{bb}
0: \x{bb}
@@ -526,6 +520,10 @@ No match
0: {
\x{f3c}
0: \x{f3c}
+ \x{2308}
+ 0: \x{2308}
+ \x{230a}
+ 0: \x{230a}
** Failers
No match
X
@@ -542,10 +540,6 @@ No match
/^\p{Sc}+/8
$\x{a2}\x{a3}\x{a4}\x{a5}\x{a6}
0: $\x{a2}\x{a3}\x{a4}\x{a5}
- 1: $\x{a2}\x{a3}\x{a4}
- 2: $\x{a2}\x{a3}
- 3: $\x{a2}
- 4: $
\x{9f2}
0: \x{9f2}
** Failers
@@ -568,11 +562,6 @@ No match
/^\p{Sm}+/8
+<|~\x{ac}\x{2044}
0: +<|~\x{ac}\x{2044}
- 1: +<|~\x{ac}
- 2: +<|~
- 3: +<|
- 4: +<
- 5: +
** Failers
No match
X
@@ -619,8 +608,6 @@ No match
0: \x{a0}
\x{1680}
0: \x{1680}
- \x{180e}
- 0: \x{180e}
\x{2000}
0: \x{2000}
\x{2001}
@@ -767,23 +754,10 @@ No match
/[\p{Nd}+-]+/8
1234
0: 1234
- 1: 123
- 2: 12
- 3: 1
12-34
0: 12-34
- 1: 12-3
- 2: 12-
- 3: 12
- 4: 1
12+\x{661}-34
0: 12+\x{661}-34
- 1: 12+\x{661}-3
- 2: 12+\x{661}-
- 3: 12+\x{661}
- 4: 12+
- 5: 12
- 6: 1
** Failers
No match
abcd
@@ -792,28 +766,16 @@ No match
/[\P{Nd}]+/8
abcd
0: abcd
- 1: abc
- 2: ab
- 3: a
** Failers
0: ** Failers
- 1: ** Failer
- 2: ** Faile
- 3: ** Fail
- 4: ** Fai
- 5: ** Fa
- 6: ** F
- 7: **
- 8: **
- 9: *
1234
No match
-/\D+/8
+/\D+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
No match
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -837,11 +799,11 @@ Matched, but too many subsidiary matches
20: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
21: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/\P{Nd}+/8
+/\P{Nd}+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
No match
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -865,11 +827,11 @@ Matched, but too many subsidiary matches
20: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
21: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\D]+/8
+/[\D]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
No match
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -893,11 +855,11 @@ Matched, but too many subsidiary matches
20: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
21: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\P{Nd}]+/8
+/[\P{Nd}]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
No match
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -921,11 +883,11 @@ Matched, but too many subsidiary matches
20: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
21: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/[\D\P{Nd}]+/8
+/[\D\P{Nd}]+/8O
11111111111111111111111111111111111111111111111111111111111111111111111
No match
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -1046,10 +1008,6 @@ No match
/\x{391}+/8i
\x{391}\x{3b1}\x{3b1}\x{3b1}\x{391}
0: \x{391}\x{3b1}\x{3b1}\x{3b1}\x{391}
- 1: \x{391}\x{3b1}\x{3b1}\x{3b1}
- 2: \x{391}\x{3b1}\x{3b1}
- 3: \x{391}\x{3b1}
- 4: \x{391}
/\x{391}{3,5}(.)/8i
\x{391}\x{3b1}\x{3b1}\x{3b1}\x{391}X
@@ -1236,8 +1194,6 @@ No match
/^\p{Han}+/8
\x{2e81}\x{3007}\x{2f804}\x{31a0}
0: \x{2e81}\x{3007}\x{2f804}
- 1: \x{2e81}\x{3007}
- 2: \x{2e81}
** Failers
No match
\x{2e7f}
@@ -1248,15 +1204,6 @@ No match
0: \x{3105}
** Failers
0: ** Failers
- 1: ** Failer
- 2: ** Faile
- 3: ** Fail
- 4: ** Fai
- 5: ** Fa
- 6: ** F
- 7: **
- 8: **
- 9: *
\x{30ff}
No match
@@ -1469,12 +1416,8 @@ No match
/^\p{Any}{3,5}/8
abcdefgh
0: abcde
- 1: abcd
- 2: abc
\x{1234}\n\r\x{3456}xyz
0: \x{1234}\x{0a}\x{0d}\x{3456}x
- 1: \x{1234}\x{0a}\x{0d}\x{3456}
- 2: \x{1234}\x{0a}\x{0d}
/^\P{Any}{3,5}?/8
** Failers
@@ -1639,14 +1582,10 @@ No match
/\x{c0}+\x{116}+/8i
\x{c0}\x{e0}\x{116}\x{117}
0: \x{c0}\x{e0}\x{116}\x{117}
- 1: \x{c0}\x{e0}\x{116}
/[\x{c0}\x{116}]+/8i
\x{c0}\x{e0}\x{116}\x{117}
0: \x{c0}\x{e0}\x{116}\x{117}
- 1: \x{c0}\x{e0}\x{116}
- 2: \x{c0}\x{e0}
- 3: \x{c0}
/Check property support in non-UTF-8 mode/
@@ -1693,16 +1632,6 @@ No match
/^\p{Xan}+/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 1: ABCD1234\x{6ca}\x{a6c}
- 2: ABCD1234\x{6ca}
- 3: ABCD1234
- 4: ABCD123
- 5: ABCD12
- 6: ABCD1
- 7: ABCD
- 8: ABC
- 9: AB
-10: A
** Failers
No match
_ABC
@@ -1711,28 +1640,10 @@ No match
/^\p{Xan}*/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 1: ABCD1234\x{6ca}\x{a6c}
- 2: ABCD1234\x{6ca}
- 3: ABCD1234
- 4: ABCD123
- 5: ABCD12
- 6: ABCD1
- 7: ABCD
- 8: ABC
- 9: AB
-10: A
-11:
/^\p{Xan}{2,9}/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}
- 1: ABCD1234
- 2: ABCD123
- 3: ABCD12
- 4: ABCD1
- 5: ABCD
- 6: ABC
- 7: AB
/^[\p{Xan}]/8
ABCD1234_
@@ -1753,16 +1664,6 @@ No match
/^[\p{Xan}]+/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 1: ABCD1234\x{6ca}\x{a6c}
- 2: ABCD1234\x{6ca}
- 3: ABCD1234
- 4: ABCD123
- 5: ABCD12
- 6: ABCD1
- 7: ABCD
- 8: ABC
- 9: AB
-10: A
** Failers
No match
_ABC
@@ -1776,53 +1677,57 @@ No match
\x{0b}
No match
-/^>\p{Xsp}+/8
+/^>\p{Xsp}+/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}
- 4: > \x{09}\x{0a}\x{0c}
- 5: > \x{09}\x{0a}
- 6: > \x{09}
- 7: >
-
-/^>\p{Xsp}*/8
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
+ 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
+ 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
+ 4: > \x{09}\x{0a}\x{0c}\x{0d}
+ 5: > \x{09}\x{0a}\x{0c}
+ 6: > \x{09}\x{0a}
+ 7: > \x{09}
+ 8: >
+
+/^>\p{Xsp}*/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}
- 4: > \x{09}\x{0a}\x{0c}
- 5: > \x{09}\x{0a}
- 6: > \x{09}
- 7: >
- 8: >
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
+ 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
+ 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
+ 4: > \x{09}\x{0a}\x{0c}\x{0d}
+ 5: > \x{09}\x{0a}\x{0c}
+ 6: > \x{09}\x{0a}
+ 7: > \x{09}
+ 8: >
+ 9: >
-/^>\p{Xsp}{2,9}/8
+/^>\p{Xsp}{2,9}/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}
- 4: > \x{09}\x{0a}\x{0c}
- 5: > \x{09}\x{0a}
- 6: > \x{09}
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
+ 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
+ 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
+ 4: > \x{09}\x{0a}\x{0c}\x{0d}
+ 5: > \x{09}\x{0a}\x{0c}
+ 6: > \x{09}\x{0a}
+ 7: > \x{09}
-/^>[\p{Xsp}]/8
+/^>[\p{Xsp}]/8O
>\x{2028}\x{0b}
0: >\x{2028}
-/^>[\p{Xsp}]+/8
+/^>[\p{Xsp}]+/8O
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}
- 4: > \x{09}\x{0a}\x{0c}
- 5: > \x{09}\x{0a}
- 6: > \x{09}
- 7: >
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
+ 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
+ 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
+ 4: > \x{09}\x{0a}\x{0c}\x{0d}
+ 5: > \x{09}\x{0a}\x{0c}
+ 6: > \x{09}\x{0a}
+ 7: > \x{09}
+ 8: >
/^>\p{Xps}/8
>\x{1680}\x{2028}\x{0b}
@@ -1837,14 +1742,6 @@ No match
/^>\p{Xps}+/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 4: > \x{09}\x{0a}\x{0c}\x{0d}
- 5: > \x{09}\x{0a}\x{0c}
- 6: > \x{09}\x{0a}
- 7: > \x{09}
- 8: >
/^>\p{Xps}+?/8
>\x{1680}\x{2028}\x{0b}
@@ -1855,26 +1752,10 @@ No match
/^>\p{Xps}*/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 4: > \x{09}\x{0a}\x{0c}\x{0d}
- 5: > \x{09}\x{0a}\x{0c}
- 6: > \x{09}\x{0a}
- 7: > \x{09}
- 8: >
- 9: >
/^>\p{Xps}{2,9}/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 4: > \x{09}\x{0a}\x{0c}\x{0d}
- 5: > \x{09}\x{0a}\x{0c}
- 6: > \x{09}\x{0a}
- 7: > \x{09}
/^>\p{Xps}{2,9}?/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
@@ -1894,14 +1775,6 @@ No match
/^>[\p{Xps}]+/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 1: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
- 2: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}
- 3: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}
- 4: > \x{09}\x{0a}\x{0c}\x{0d}
- 5: > \x{09}\x{0a}\x{0c}
- 6: > \x{09}\x{0a}
- 7: > \x{09}
- 8: >
/^\p{Xwd}/8
ABCD
@@ -1924,42 +1797,14 @@ No match
/^\p{Xwd}+/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}_
- 1: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 2: ABCD1234\x{6ca}\x{a6c}
- 3: ABCD1234\x{6ca}
- 4: ABCD1234
- 5: ABCD123
- 6: ABCD12
- 7: ABCD1
- 8: ABCD
- 9: ABC
-10: AB
-11: A
/^\p{Xwd}*/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}_
- 1: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 2: ABCD1234\x{6ca}\x{a6c}
- 3: ABCD1234\x{6ca}
- 4: ABCD1234
- 5: ABCD123
- 6: ABCD12
- 7: ABCD1
- 8: ABCD
- 9: ABC
-10: AB
-11: A
-12:
/^\p{Xwd}{2,9}/8
A_12\x{6ca}\x{a6c}\x{10a7}
0: A_12\x{6ca}\x{a6c}\x{10a7}
- 1: A_12\x{6ca}\x{a6c}
- 2: A_12\x{6ca}
- 3: A_12
- 4: A_1
- 5: A_
/^[\p{Xwd}]/8
ABCD1234_
@@ -1982,17 +1827,6 @@ No match
/^[\p{Xwd}]+/8
ABCD1234\x{6ca}\x{a6c}\x{10a7}_
0: ABCD1234\x{6ca}\x{a6c}\x{10a7}_
- 1: ABCD1234\x{6ca}\x{a6c}\x{10a7}
- 2: ABCD1234\x{6ca}\x{a6c}
- 3: ABCD1234\x{6ca}
- 4: ABCD1234
- 5: ABCD123
- 6: ABCD12
- 7: ABCD1
- 8: ABCD
- 9: ABC
-10: AB
-11: A
/-- Unicode properties for \b abd \B --/
@@ -2043,7 +1877,6 @@ No match
/[^\x{100}]+/8i
\x{100}\x{101}XX
0: XX
- 1: X
/^\X/8
A\P
@@ -2090,7 +1923,6 @@ Partial match: A\x{300}\x{301}A\x{300}\x{301}
/^\X+/8
AA\P
0: AA
- 1: A
AA\P\P
Partial match: AA
@@ -2271,435 +2103,299 @@ Partial match: AA
/\x{1e9e}+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/[z\x{1e9e}]+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/\x{00df}+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/[z\x{00df}]+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/\x{1f88}+/8i
\x{1f88}\x{1f80}
0: \x{1f88}\x{1f80}
- 1: \x{1f88}
/[z\x{1f88}]+/8i
\x{1f88}\x{1f80}
0: \x{1f88}\x{1f80}
- 1: \x{1f88}
/-- Perl matches these --/
/\x{00b5}+/8i
\x{00b5}\x{039c}\x{03bc}
0: \x{b5}\x{39c}\x{3bc}
- 1: \x{b5}\x{39c}
- 2: \x{b5}
/\x{039c}+/8i
\x{00b5}\x{039c}\x{03bc}
0: \x{b5}\x{39c}\x{3bc}
- 1: \x{b5}\x{39c}
- 2: \x{b5}
/\x{03bc}+/8i
\x{00b5}\x{039c}\x{03bc}
0: \x{b5}\x{39c}\x{3bc}
- 1: \x{b5}\x{39c}
- 2: \x{b5}
/\x{00c5}+/8i
\x{00c5}\x{00e5}\x{212b}
0: \x{c5}\x{e5}\x{212b}
- 1: \x{c5}\x{e5}
- 2: \x{c5}
/\x{00e5}+/8i
\x{00c5}\x{00e5}\x{212b}
0: \x{c5}\x{e5}\x{212b}
- 1: \x{c5}\x{e5}
- 2: \x{c5}
/\x{212b}+/8i
\x{00c5}\x{00e5}\x{212b}
0: \x{c5}\x{e5}\x{212b}
- 1: \x{c5}\x{e5}
- 2: \x{c5}
/\x{01c4}+/8i
\x{01c4}\x{01c5}\x{01c6}
0: \x{1c4}\x{1c5}\x{1c6}
- 1: \x{1c4}\x{1c5}
- 2: \x{1c4}
/\x{01c5}+/8i
\x{01c4}\x{01c5}\x{01c6}
0: \x{1c4}\x{1c5}\x{1c6}
- 1: \x{1c4}\x{1c5}
- 2: \x{1c4}
/\x{01c6}+/8i
\x{01c4}\x{01c5}\x{01c6}
0: \x{1c4}\x{1c5}\x{1c6}
- 1: \x{1c4}\x{1c5}
- 2: \x{1c4}
/\x{01c7}+/8i
\x{01c7}\x{01c8}\x{01c9}
0: \x{1c7}\x{1c8}\x{1c9}
- 1: \x{1c7}\x{1c8}
- 2: \x{1c7}
/\x{01c8}+/8i
\x{01c7}\x{01c8}\x{01c9}
0: \x{1c7}\x{1c8}\x{1c9}
- 1: \x{1c7}\x{1c8}
- 2: \x{1c7}
/\x{01c9}+/8i
\x{01c7}\x{01c8}\x{01c9}
0: \x{1c7}\x{1c8}\x{1c9}
- 1: \x{1c7}\x{1c8}
- 2: \x{1c7}
/\x{01ca}+/8i
\x{01ca}\x{01cb}\x{01cc}
0: \x{1ca}\x{1cb}\x{1cc}
- 1: \x{1ca}\x{1cb}
- 2: \x{1ca}
/\x{01cb}+/8i
\x{01ca}\x{01cb}\x{01cc}
0: \x{1ca}\x{1cb}\x{1cc}
- 1: \x{1ca}\x{1cb}
- 2: \x{1ca}
/\x{01cc}+/8i
\x{01ca}\x{01cb}\x{01cc}
0: \x{1ca}\x{1cb}\x{1cc}
- 1: \x{1ca}\x{1cb}
- 2: \x{1ca}
/\x{01f1}+/8i
\x{01f1}\x{01f2}\x{01f3}
0: \x{1f1}\x{1f2}\x{1f3}
- 1: \x{1f1}\x{1f2}
- 2: \x{1f1}
/\x{01f2}+/8i
\x{01f1}\x{01f2}\x{01f3}
0: \x{1f1}\x{1f2}\x{1f3}
- 1: \x{1f1}\x{1f2}
- 2: \x{1f1}
/\x{01f3}+/8i
\x{01f1}\x{01f2}\x{01f3}
0: \x{1f1}\x{1f2}\x{1f3}
- 1: \x{1f1}\x{1f2}
- 2: \x{1f1}
/\x{0345}+/8i
\x{0345}\x{0399}\x{03b9}\x{1fbe}
0: \x{345}\x{399}\x{3b9}\x{1fbe}
- 1: \x{345}\x{399}\x{3b9}
- 2: \x{345}\x{399}
- 3: \x{345}
/\x{0399}+/8i
\x{0345}\x{0399}\x{03b9}\x{1fbe}
0: \x{345}\x{399}\x{3b9}\x{1fbe}
- 1: \x{345}\x{399}\x{3b9}
- 2: \x{345}\x{399}
- 3: \x{345}
/\x{03b9}+/8i
\x{0345}\x{0399}\x{03b9}\x{1fbe}
0: \x{345}\x{399}\x{3b9}\x{1fbe}
- 1: \x{345}\x{399}\x{3b9}
- 2: \x{345}\x{399}
- 3: \x{345}
/\x{1fbe}+/8i
\x{0345}\x{0399}\x{03b9}\x{1fbe}
0: \x{345}\x{399}\x{3b9}\x{1fbe}
- 1: \x{345}\x{399}\x{3b9}
- 2: \x{345}\x{399}
- 3: \x{345}
/\x{0392}+/8i
\x{0392}\x{03b2}\x{03d0}
0: \x{392}\x{3b2}\x{3d0}
- 1: \x{392}\x{3b2}
- 2: \x{392}
/\x{03b2}+/8i
\x{0392}\x{03b2}\x{03d0}
0: \x{392}\x{3b2}\x{3d0}
- 1: \x{392}\x{3b2}
- 2: \x{392}
/\x{03d0}+/8i
\x{0392}\x{03b2}\x{03d0}
0: \x{392}\x{3b2}\x{3d0}
- 1: \x{392}\x{3b2}
- 2: \x{392}
/\x{0395}+/8i
\x{0395}\x{03b5}\x{03f5}
0: \x{395}\x{3b5}\x{3f5}
- 1: \x{395}\x{3b5}
- 2: \x{395}
/\x{03b5}+/8i
\x{0395}\x{03b5}\x{03f5}
0: \x{395}\x{3b5}\x{3f5}
- 1: \x{395}\x{3b5}
- 2: \x{395}
/\x{03f5}+/8i
\x{0395}\x{03b5}\x{03f5}
0: \x{395}\x{3b5}\x{3f5}
- 1: \x{395}\x{3b5}
- 2: \x{395}
/\x{0398}+/8i
\x{0398}\x{03b8}\x{03d1}\x{03f4}
0: \x{398}\x{3b8}\x{3d1}\x{3f4}
- 1: \x{398}\x{3b8}\x{3d1}
- 2: \x{398}\x{3b8}
- 3: \x{398}
/\x{03b8}+/8i
\x{0398}\x{03b8}\x{03d1}\x{03f4}
0: \x{398}\x{3b8}\x{3d1}\x{3f4}
- 1: \x{398}\x{3b8}\x{3d1}
- 2: \x{398}\x{3b8}
- 3: \x{398}
/\x{03d1}+/8i
\x{0398}\x{03b8}\x{03d1}\x{03f4}
0: \x{398}\x{3b8}\x{3d1}\x{3f4}
- 1: \x{398}\x{3b8}\x{3d1}
- 2: \x{398}\x{3b8}
- 3: \x{398}
/\x{03f4}+/8i
\x{0398}\x{03b8}\x{03d1}\x{03f4}
0: \x{398}\x{3b8}\x{3d1}\x{3f4}
- 1: \x{398}\x{3b8}\x{3d1}
- 2: \x{398}\x{3b8}
- 3: \x{398}
/\x{039a}+/8i
\x{039a}\x{03ba}\x{03f0}
0: \x{39a}\x{3ba}\x{3f0}
- 1: \x{39a}\x{3ba}
- 2: \x{39a}
/\x{03ba}+/8i
\x{039a}\x{03ba}\x{03f0}
0: \x{39a}\x{3ba}\x{3f0}
- 1: \x{39a}\x{3ba}
- 2: \x{39a}
/\x{03f0}+/8i
\x{039a}\x{03ba}\x{03f0}
0: \x{39a}\x{3ba}\x{3f0}
- 1: \x{39a}\x{3ba}
- 2: \x{39a}
/\x{03a0}+/8i
\x{03a0}\x{03c0}\x{03d6}
0: \x{3a0}\x{3c0}\x{3d6}
- 1: \x{3a0}\x{3c0}
- 2: \x{3a0}
/\x{03c0}+/8i
\x{03a0}\x{03c0}\x{03d6}
0: \x{3a0}\x{3c0}\x{3d6}
- 1: \x{3a0}\x{3c0}
- 2: \x{3a0}
/\x{03d6}+/8i
\x{03a0}\x{03c0}\x{03d6}
0: \x{3a0}\x{3c0}\x{3d6}
- 1: \x{3a0}\x{3c0}
- 2: \x{3a0}
/\x{03a1}+/8i
\x{03a1}\x{03c1}\x{03f1}
0: \x{3a1}\x{3c1}\x{3f1}
- 1: \x{3a1}\x{3c1}
- 2: \x{3a1}
/\x{03c1}+/8i
\x{03a1}\x{03c1}\x{03f1}
0: \x{3a1}\x{3c1}\x{3f1}
- 1: \x{3a1}\x{3c1}
- 2: \x{3a1}
/\x{03f1}+/8i
\x{03a1}\x{03c1}\x{03f1}
0: \x{3a1}\x{3c1}\x{3f1}
- 1: \x{3a1}\x{3c1}
- 2: \x{3a1}
/\x{03a3}+/8i
\x{03A3}\x{03C2}\x{03C3}
0: \x{3a3}\x{3c2}\x{3c3}
- 1: \x{3a3}\x{3c2}
- 2: \x{3a3}
/\x{03c2}+/8i
\x{03A3}\x{03C2}\x{03C3}
0: \x{3a3}\x{3c2}\x{3c3}
- 1: \x{3a3}\x{3c2}
- 2: \x{3a3}
/\x{03c3}+/8i
\x{03A3}\x{03C2}\x{03C3}
0: \x{3a3}\x{3c2}\x{3c3}
- 1: \x{3a3}\x{3c2}
- 2: \x{3a3}
/\x{03a6}+/8i
\x{03a6}\x{03c6}\x{03d5}
0: \x{3a6}\x{3c6}\x{3d5}
- 1: \x{3a6}\x{3c6}
- 2: \x{3a6}
/\x{03c6}+/8i
\x{03a6}\x{03c6}\x{03d5}
0: \x{3a6}\x{3c6}\x{3d5}
- 1: \x{3a6}\x{3c6}
- 2: \x{3a6}
/\x{03d5}+/8i
\x{03a6}\x{03c6}\x{03d5}
0: \x{3a6}\x{3c6}\x{3d5}
- 1: \x{3a6}\x{3c6}
- 2: \x{3a6}
/\x{03c9}+/8i
\x{03c9}\x{03a9}\x{2126}
0: \x{3c9}\x{3a9}\x{2126}
- 1: \x{3c9}\x{3a9}
- 2: \x{3c9}
/\x{03a9}+/8i
\x{03c9}\x{03a9}\x{2126}
0: \x{3c9}\x{3a9}\x{2126}
- 1: \x{3c9}\x{3a9}
- 2: \x{3c9}
/\x{2126}+/8i
\x{03c9}\x{03a9}\x{2126}
0: \x{3c9}\x{3a9}\x{2126}
- 1: \x{3c9}\x{3a9}
- 2: \x{3c9}
/\x{1e60}+/8i
\x{1e60}\x{1e61}\x{1e9b}
0: \x{1e60}\x{1e61}\x{1e9b}
- 1: \x{1e60}\x{1e61}
- 2: \x{1e60}
/\x{1e61}+/8i
\x{1e60}\x{1e61}\x{1e9b}
0: \x{1e60}\x{1e61}\x{1e9b}
- 1: \x{1e60}\x{1e61}
- 2: \x{1e60}
/\x{1e9b}+/8i
\x{1e60}\x{1e61}\x{1e9b}
0: \x{1e60}\x{1e61}\x{1e9b}
- 1: \x{1e60}\x{1e61}
- 2: \x{1e60}
/\x{1e9e}+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/\x{00df}+/8i
\x{1e9e}\x{00df}
0: \x{1e9e}\x{df}
- 1: \x{1e9e}
/\x{1f88}+/8i
\x{1f88}\x{1f80}
0: \x{1f88}\x{1f80}
- 1: \x{1f88}
/\x{1f80}+/8i
\x{1f88}\x{1f80}
0: \x{1f88}\x{1f80}
- 1: \x{1f88}
/\x{004b}+/8i
\x{004b}\x{006b}\x{212a}
0: Kk\x{212a}
- 1: Kk
- 2: K
/\x{006b}+/8i
\x{004b}\x{006b}\x{212a}
0: Kk\x{212a}
- 1: Kk
- 2: K
/\x{212a}+/8i
\x{004b}\x{006b}\x{212a}
0: Kk\x{212a}
- 1: Kk
- 2: K
/\x{0053}+/8i
\x{0053}\x{0073}\x{017f}
0: Ss\x{17f}
- 1: Ss
- 2: S
/\x{0073}+/8i
\x{0053}\x{0073}\x{017f}
0: Ss\x{17f}
- 1: Ss
- 2: S
/\x{017f}+/8i
\x{0053}\x{0073}\x{017f}
0: Ss\x{17f}
- 1: Ss
- 2: S
/ist/8i
ikt
@@ -2723,4 +2419,129 @@ No match
iskt
No match
+/^\p{Xuc}/8
+ $abc
+ 0: $
+ @abc
+ 0: @
+ `abc
+ 0: `
+ \x{1234}abc
+ 0: \x{1234}
+ ** Failers
+No match
+ abc
+No match
+
+/^\p{Xuc}+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}+?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ 1: $@`\x{a0}\x{1234}
+ 2: $@`\x{a0}
+ 3: $@`
+ 4: $@
+ 5: $
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}+?\*/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}*
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}++/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}{3,5}/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}{3,5}?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}
+ 1: $@`\x{a0}
+ 2: $@`
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^[\p{Xuc}]/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^[\p{Xuc}]+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\P{Xuc}/8
+ abc
+ 0: a
+ ** Failers
+ 0: *
+ $abc
+No match
+ @abc
+No match
+ `abc
+No match
+ \x{1234}abc
+No match
+
+/^[\P{Xuc}]/8
+ abc
+ 0: a
+ ** Failers
+ 0: *
+ $abc
+No match
+ @abc
+No match
+ `abc
+No match
+ \x{1234}abc
+No match
+
+/^A\s+Z/8W
+ A\x{2005}Z
+ 0: A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+ 0: A\x{85}\x{180e}\x{2005}Z
+
+/^A[\s]+Z/8W
+ A\x{2005}Z
+ 0: A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+ 0: A\x{85}\x{180e}\x{2005}Z
+
/-- End of testinput10 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput11-16 b/ext/pcre/pcrelib/testdata/testoutput11-16
new file mode 100644
index 0000000000..f1ad8887b4
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput11-16
@@ -0,0 +1,712 @@
+/-- These are a few representative patterns whose lengths and offsets are to be
+shown when the link size is 2. This is just a doublecheck test to ensure the
+sizes don't go horribly wrong when something is changed. The pattern contents
+are all themselves checked in other tests. Unicode, including property support,
+is required for these tests. --/
+
+/((?i)b)/BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 5 CBra 1
+ 5 /i b
+ 7 5 Ket
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/(?s)(.*X|^B)/BM
+Memory allocation (code space): 38
+------------------------------------------------------------------
+ 0 16 Bra
+ 2 7 CBra 1
+ 5 AllAny*
+ 7 X
+ 9 5 Alt
+ 11 ^
+ 12 B
+ 14 12 Ket
+ 16 16 Ket
+ 18 End
+------------------------------------------------------------------
+
+/(?s:.*X|^B)/BM
+Memory allocation (code space): 36
+------------------------------------------------------------------
+ 0 15 Bra
+ 2 6 Bra
+ 4 AllAny*
+ 6 X
+ 8 5 Alt
+ 10 ^
+ 11 B
+ 13 11 Ket
+ 15 15 Ket
+ 17 End
+------------------------------------------------------------------
+
+/^[[:alnum:]]/BM
+Memory allocation (code space): 46
+------------------------------------------------------------------
+ 0 20 Bra
+ 2 ^
+ 3 [0-9A-Za-z]
+ 20 20 Ket
+ 22 End
+------------------------------------------------------------------
+
+/#/IxMD
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 2 Bra
+ 2 2 Ket
+ 4 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+May match empty string
+Options: extended
+No first char
+No need char
+
+/a#/IxMD
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: extended
+First char = 'a'
+No need char
+
+/x?+/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 x?+
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/x++/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 x++
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/x{1,3}+/BM
+Memory allocation (code space): 20
+------------------------------------------------------------------
+ 0 7 Bra
+ 2 x
+ 4 x{0,2}+
+ 7 7 Ket
+ 9 End
+------------------------------------------------------------------
+
+/(x)*+/BM
+Memory allocation (code space): 26
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 Braposzero
+ 3 5 CBraPos 1
+ 6 x
+ 8 5 KetRpos
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^((a+)(?U)([ab]+)(?-U)([bc]+)(\w*))/BM
+Memory allocation (code space): 142
+------------------------------------------------------------------
+ 0 68 Bra
+ 2 ^
+ 3 63 CBra 1
+ 6 5 CBra 2
+ 9 a+
+ 11 5 Ket
+ 13 21 CBra 3
+ 16 [ab]+?
+ 34 21 Ket
+ 36 21 CBra 4
+ 39 [bc]+
+ 57 21 Ket
+ 59 5 CBra 5
+ 62 \w*+
+ 64 5 Ket
+ 66 63 Ket
+ 68 68 Ket
+ 70 End
+------------------------------------------------------------------
+
+|8J\$WE\<\.rX\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 1648
+------------------------------------------------------------------
+ 0 821 Bra
+ 2 8J$WE<.rX+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+820 \b
+821 821 Ket
+823 End
+------------------------------------------------------------------
+
+|\$\<\.X\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 1628
+------------------------------------------------------------------
+ 0 811 Bra
+ 2 $<.X+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+810 \b
+811 811 Ket
+813 End
+------------------------------------------------------------------
+
+/(a(?1)b)/BM
+Memory allocation (code space): 32
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 9 CBra 1
+ 5 a
+ 7 2 Recurse
+ 9 b
+ 11 9 Ket
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/(a(?1)+b)/BM
+Memory allocation (code space): 40
+------------------------------------------------------------------
+ 0 17 Bra
+ 2 13 CBra 1
+ 5 a
+ 7 4 Once
+ 9 2 Recurse
+ 11 4 KetRmax
+ 13 b
+ 15 13 Ket
+ 17 17 Ket
+ 19 End
+------------------------------------------------------------------
+
+/a(?P<name1>b|c)d(?P<longername2>e)/BM
+Memory allocation (code space): 80
+------------------------------------------------------------------
+ 0 24 Bra
+ 2 a
+ 4 5 CBra 1
+ 7 b
+ 9 4 Alt
+ 11 c
+ 13 9 Ket
+ 15 d
+ 17 5 CBra 2
+ 20 e
+ 22 5 Ket
+ 24 24 Ket
+ 26 End
+------------------------------------------------------------------
+
+/(?:a(?P<c>c(?P<d>d)))(?P<a>a)/BM
+Memory allocation (code space): 73
+------------------------------------------------------------------
+ 0 29 Bra
+ 2 18 Bra
+ 4 a
+ 6 12 CBra 1
+ 9 c
+ 11 5 CBra 2
+ 14 d
+ 16 5 Ket
+ 18 12 Ket
+ 20 18 Ket
+ 22 5 CBra 3
+ 25 a
+ 27 5 Ket
+ 29 29 Ket
+ 31 End
+------------------------------------------------------------------
+
+/(?P<a>a)...(?P=a)bbb(?P>a)d/BM
+Memory allocation (code space): 57
+------------------------------------------------------------------
+ 0 24 Bra
+ 2 5 CBra 1
+ 5 a
+ 7 5 Ket
+ 9 Any
+ 10 Any
+ 11 Any
+ 12 \1
+ 14 bbb
+ 20 2 Recurse
+ 22 d
+ 24 24 Ket
+ 26 End
+------------------------------------------------------------------
+
+/abc(?C255)de(?C)f/BM
+Memory allocation (code space): 50
+------------------------------------------------------------------
+ 0 22 Bra
+ 2 abc
+ 8 Callout 255 10 1
+ 12 de
+ 16 Callout 0 16 1
+ 20 f
+ 22 22 Ket
+ 24 End
+------------------------------------------------------------------
+
+/abcde/CBM
+Memory allocation (code space): 78
+------------------------------------------------------------------
+ 0 36 Bra
+ 2 Callout 255 0 1
+ 6 a
+ 8 Callout 255 1 1
+ 12 b
+ 14 Callout 255 2 1
+ 18 c
+ 20 Callout 255 3 1
+ 24 d
+ 26 Callout 255 4 1
+ 30 e
+ 32 Callout 255 5 0
+ 36 36 Ket
+ 38 End
+------------------------------------------------------------------
+
+/\x{100}/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{1000}/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{1000}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{10000}/8BM
+Memory allocation (code space): 16
+------------------------------------------------------------------
+ 0 5 Bra
+ 2 \x{10000}
+ 5 5 Ket
+ 7 End
+------------------------------------------------------------------
+
+/\x{100000}/8BM
+Memory allocation (code space): 16
+------------------------------------------------------------------
+ 0 5 Bra
+ 2 \x{100000}
+ 5 5 Ket
+ 7 End
+------------------------------------------------------------------
+
+/\x{10ffff}/8BM
+Memory allocation (code space): 16
+------------------------------------------------------------------
+ 0 5 Bra
+ 2 \x{10ffff}
+ 5 5 Ket
+ 7 End
+------------------------------------------------------------------
+
+/\x{110000}/8BM
+Failed: character value in \x{} or \o{} is too large at offset 9
+
+/[\x{ff}]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{ff}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\x{100}]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x80/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x80
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\xff/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{ff}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{0041}\x{2262}\x{0391}\x{002e}/D8M
+Memory allocation (code space): 26
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 A\x{2262}\x{391}.
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = '.'
+
+/\x{D55c}\x{ad6d}\x{C5B4}/D8M
+Memory allocation (code space): 22
+------------------------------------------------------------------
+ 0 8 Bra
+ 2 \x{d55c}\x{ad6d}\x{c5b4}
+ 8 8 Ket
+ 10 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d55c}
+Need char = \x{c5b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/D8M
+Memory allocation (code space): 22
+------------------------------------------------------------------
+ 0 8 Bra
+ 2 \x{65e5}\x{672c}\x{8a9e}
+ 8 8 Ket
+ 10 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{65e5}
+Need char = \x{8a9e}
+
+/[\x{100}]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[Z\x{100}]/8BM
+Memory allocation (code space): 54
+------------------------------------------------------------------
+ 0 24 Bra
+ 2 [Z\x{100}]
+ 24 24 Ket
+ 26 End
+------------------------------------------------------------------
+
+/^[\x{100}\E-\Q\E\x{150}]/B8M
+Memory allocation (code space): 26
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 ^
+ 3 [\x{100}-\x{150}]
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E]/B8M
+Memory allocation (code space): 26
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 ^
+ 3 [\x{100}-\x{150}]
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E/B8M
+Failed: missing terminating ] for character class at offset 13
+
+/[\p{L}]/BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\p{^L}]/BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\P{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\P{L}]/BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\P{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\P{^L}]/BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[abc\p{L}\x{0660}]/8BM
+Memory allocation (code space): 60
+------------------------------------------------------------------
+ 0 27 Bra
+ 2 [a-c\p{L}\x{660}]
+ 27 27 Ket
+ 29 End
+------------------------------------------------------------------
+
+/[\p{Nd}]/8BM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{Nd}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\p{Nd}+-]+/8BM
+Memory allocation (code space): 58
+------------------------------------------------------------------
+ 0 26 Bra
+ 2 [+\-\p{Nd}]++
+ 26 26 Ket
+ 28 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iBM
+Memory allocation (code space): 32
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 /i A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8BM
+Memory allocation (code space): 32
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/[\x{105}-\x{109}]/8iBM
+Memory allocation (code space): 24
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\x{104}-\x{109}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/( ( (?(1)0|) )* )/xBM
+Memory allocation (code space): 52
+------------------------------------------------------------------
+ 0 23 Bra
+ 2 19 CBra 1
+ 5 Brazero
+ 6 13 SCBra 2
+ 9 6 Cond
+ 11 1 Cond ref
+ 13 0
+ 15 2 Alt
+ 17 8 Ket
+ 19 13 KetRmax
+ 21 19 Ket
+ 23 23 Ket
+ 25 End
+------------------------------------------------------------------
+
+/( (?(1)0|)* )/xBM
+Memory allocation (code space): 42
+------------------------------------------------------------------
+ 0 18 Bra
+ 2 14 CBra 1
+ 5 Brazero
+ 6 6 SCond
+ 8 1 Cond ref
+ 10 0
+ 12 2 Alt
+ 14 8 KetRmax
+ 16 14 Ket
+ 18 18 Ket
+ 20 End
+------------------------------------------------------------------
+
+/[a]/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[a]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\xaa]/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{aa}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\xaa]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{aa}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^a]/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^a]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^a]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^a]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\xaa]/BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^\x{aa}]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\xaa]/8BM
+Memory allocation (code space): 14
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^\x{aa}]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\d]/8WB
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [^\p{Nd}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[[:^alpha:][:^cntrl:]]+/8WB
+------------------------------------------------------------------
+ 0 26 Bra
+ 2 [ -~\x80-\xff\P{L}]++
+ 26 26 Ket
+ 28 End
+------------------------------------------------------------------
+
+/[[:^cntrl:][:^alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 26 Bra
+ 2 [ -~\x80-\xff\P{L}]++
+ 26 26 Ket
+ 28 End
+------------------------------------------------------------------
+
+/[[:alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 [\p{L}]++
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/[[:^alpha:]\S]+/8WB
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 [\P{L}\P{Xsp}]++
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/abc(d|e)(*THEN)x(123(*THEN)4|567(b|q)(*THEN)xx)/B
+------------------------------------------------------------------
+ 0 60 Bra
+ 2 abc
+ 8 5 CBra 1
+ 11 d
+ 13 4 Alt
+ 15 e
+ 17 9 Ket
+ 19 *THEN
+ 20 x
+ 22 12 CBra 2
+ 25 123
+ 31 *THEN
+ 32 4
+ 34 24 Alt
+ 36 567
+ 42 5 CBra 3
+ 45 b
+ 47 4 Alt
+ 49 q
+ 51 9 Ket
+ 53 *THEN
+ 54 xx
+ 58 36 Ket
+ 60 60 Ket
+ 62 End
+------------------------------------------------------------------
+
+/-- End of testinput11 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput11-32 b/ext/pcre/pcrelib/testdata/testoutput11-32
new file mode 100644
index 0000000000..266e55d067
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput11-32
@@ -0,0 +1,712 @@
+/-- These are a few representative patterns whose lengths and offsets are to be
+shown when the link size is 2. This is just a doublecheck test to ensure the
+sizes don't go horribly wrong when something is changed. The pattern contents
+are all themselves checked in other tests. Unicode, including property support,
+is required for these tests. --/
+
+/((?i)b)/BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 5 CBra 1
+ 5 /i b
+ 7 5 Ket
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/(?s)(.*X|^B)/BM
+Memory allocation (code space): 76
+------------------------------------------------------------------
+ 0 16 Bra
+ 2 7 CBra 1
+ 5 AllAny*
+ 7 X
+ 9 5 Alt
+ 11 ^
+ 12 B
+ 14 12 Ket
+ 16 16 Ket
+ 18 End
+------------------------------------------------------------------
+
+/(?s:.*X|^B)/BM
+Memory allocation (code space): 72
+------------------------------------------------------------------
+ 0 15 Bra
+ 2 6 Bra
+ 4 AllAny*
+ 6 X
+ 8 5 Alt
+ 10 ^
+ 11 B
+ 13 11 Ket
+ 15 15 Ket
+ 17 End
+------------------------------------------------------------------
+
+/^[[:alnum:]]/BM
+Memory allocation (code space): 60
+------------------------------------------------------------------
+ 0 12 Bra
+ 2 ^
+ 3 [0-9A-Za-z]
+ 12 12 Ket
+ 14 End
+------------------------------------------------------------------
+
+/#/IxMD
+Memory allocation (code space): 20
+------------------------------------------------------------------
+ 0 2 Bra
+ 2 2 Ket
+ 4 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+May match empty string
+Options: extended
+No first char
+No need char
+
+/a#/IxMD
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: extended
+First char = 'a'
+No need char
+
+/x?+/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 x?+
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/x++/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 x++
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/x{1,3}+/BM
+Memory allocation (code space): 40
+------------------------------------------------------------------
+ 0 7 Bra
+ 2 x
+ 4 x{0,2}+
+ 7 7 Ket
+ 9 End
+------------------------------------------------------------------
+
+/(x)*+/BM
+Memory allocation (code space): 52
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 Braposzero
+ 3 5 CBraPos 1
+ 6 x
+ 8 5 KetRpos
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^((a+)(?U)([ab]+)(?-U)([bc]+)(\w*))/BM
+Memory allocation (code space): 220
+------------------------------------------------------------------
+ 0 52 Bra
+ 2 ^
+ 3 47 CBra 1
+ 6 5 CBra 2
+ 9 a+
+ 11 5 Ket
+ 13 13 CBra 3
+ 16 [ab]+?
+ 26 13 Ket
+ 28 13 CBra 4
+ 31 [bc]+
+ 41 13 Ket
+ 43 5 CBra 5
+ 46 \w*+
+ 48 5 Ket
+ 50 47 Ket
+ 52 52 Ket
+ 54 End
+------------------------------------------------------------------
+
+|8J\$WE\<\.rX\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 3296
+------------------------------------------------------------------
+ 0 821 Bra
+ 2 8J$WE<.rX+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+820 \b
+821 821 Ket
+823 End
+------------------------------------------------------------------
+
+|\$\<\.X\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 3256
+------------------------------------------------------------------
+ 0 811 Bra
+ 2 $<.X+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+810 \b
+811 811 Ket
+813 End
+------------------------------------------------------------------
+
+/(a(?1)b)/BM
+Memory allocation (code space): 64
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 9 CBra 1
+ 5 a
+ 7 2 Recurse
+ 9 b
+ 11 9 Ket
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/(a(?1)+b)/BM
+Memory allocation (code space): 80
+------------------------------------------------------------------
+ 0 17 Bra
+ 2 13 CBra 1
+ 5 a
+ 7 4 Once
+ 9 2 Recurse
+ 11 4 KetRmax
+ 13 b
+ 15 13 Ket
+ 17 17 Ket
+ 19 End
+------------------------------------------------------------------
+
+/a(?P<name1>b|c)d(?P<longername2>e)/BM
+Memory allocation (code space): 186
+------------------------------------------------------------------
+ 0 24 Bra
+ 2 a
+ 4 5 CBra 1
+ 7 b
+ 9 4 Alt
+ 11 c
+ 13 9 Ket
+ 15 d
+ 17 5 CBra 2
+ 20 e
+ 22 5 Ket
+ 24 24 Ket
+ 26 End
+------------------------------------------------------------------
+
+/(?:a(?P<c>c(?P<d>d)))(?P<a>a)/BM
+Memory allocation (code space): 155
+------------------------------------------------------------------
+ 0 29 Bra
+ 2 18 Bra
+ 4 a
+ 6 12 CBra 1
+ 9 c
+ 11 5 CBra 2
+ 14 d
+ 16 5 Ket
+ 18 12 Ket
+ 20 18 Ket
+ 22 5 CBra 3
+ 25 a
+ 27 5 Ket
+ 29 29 Ket
+ 31 End
+------------------------------------------------------------------
+
+/(?P<a>a)...(?P=a)bbb(?P>a)d/BM
+Memory allocation (code space): 117
+------------------------------------------------------------------
+ 0 24 Bra
+ 2 5 CBra 1
+ 5 a
+ 7 5 Ket
+ 9 Any
+ 10 Any
+ 11 Any
+ 12 \1
+ 14 bbb
+ 20 2 Recurse
+ 22 d
+ 24 24 Ket
+ 26 End
+------------------------------------------------------------------
+
+/abc(?C255)de(?C)f/BM
+Memory allocation (code space): 100
+------------------------------------------------------------------
+ 0 22 Bra
+ 2 abc
+ 8 Callout 255 10 1
+ 12 de
+ 16 Callout 0 16 1
+ 20 f
+ 22 22 Ket
+ 24 End
+------------------------------------------------------------------
+
+/abcde/CBM
+Memory allocation (code space): 156
+------------------------------------------------------------------
+ 0 36 Bra
+ 2 Callout 255 0 1
+ 6 a
+ 8 Callout 255 1 1
+ 12 b
+ 14 Callout 255 2 1
+ 18 c
+ 20 Callout 255 3 1
+ 24 d
+ 26 Callout 255 4 1
+ 30 e
+ 32 Callout 255 5 0
+ 36 36 Ket
+ 38 End
+------------------------------------------------------------------
+
+/\x{100}/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{1000}/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{1000}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{10000}/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{10000}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{100000}/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100000}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{10ffff}/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{10ffff}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{110000}/8BM
+Failed: character value in \x{} or \o{} is too large at offset 9
+
+/[\x{ff}]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{ff}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\x{100}]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x80/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x80
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\xff/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{ff}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/\x{0041}\x{2262}\x{0391}\x{002e}/D8M
+Memory allocation (code space): 52
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 A\x{2262}\x{391}.
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = '.'
+
+/\x{D55c}\x{ad6d}\x{C5B4}/D8M
+Memory allocation (code space): 44
+------------------------------------------------------------------
+ 0 8 Bra
+ 2 \x{d55c}\x{ad6d}\x{c5b4}
+ 8 8 Ket
+ 10 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d55c}
+Need char = \x{c5b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/D8M
+Memory allocation (code space): 44
+------------------------------------------------------------------
+ 0 8 Bra
+ 2 \x{65e5}\x{672c}\x{8a9e}
+ 8 8 Ket
+ 10 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{65e5}
+Need char = \x{8a9e}
+
+/[\x{100}]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{100}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[Z\x{100}]/8BM
+Memory allocation (code space): 76
+------------------------------------------------------------------
+ 0 16 Bra
+ 2 [Z\x{100}]
+ 16 16 Ket
+ 18 End
+------------------------------------------------------------------
+
+/^[\x{100}\E-\Q\E\x{150}]/B8M
+Memory allocation (code space): 52
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 ^
+ 3 [\x{100}-\x{150}]
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E]/B8M
+Memory allocation (code space): 52
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 ^
+ 3 [\x{100}-\x{150}]
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E/B8M
+Failed: missing terminating ] for character class at offset 13
+
+/[\p{L}]/BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\p{^L}]/BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\P{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\P{L}]/BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\P{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\P{^L}]/BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{L}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[abc\p{L}\x{0660}]/8BM
+Memory allocation (code space): 88
+------------------------------------------------------------------
+ 0 19 Bra
+ 2 [a-c\p{L}\x{660}]
+ 19 19 Ket
+ 21 End
+------------------------------------------------------------------
+
+/[\p{Nd}]/8BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\p{Nd}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[\p{Nd}+-]+/8BM
+Memory allocation (code space): 84
+------------------------------------------------------------------
+ 0 18 Bra
+ 2 [+\-\p{Nd}]++
+ 18 18 Ket
+ 20 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iBM
+Memory allocation (code space): 60
+------------------------------------------------------------------
+ 0 12 Bra
+ 2 /i A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 12 12 Ket
+ 14 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8BM
+Memory allocation (code space): 60
+------------------------------------------------------------------
+ 0 12 Bra
+ 2 A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 12 12 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[\x{105}-\x{109}]/8iBM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [\x{104}-\x{109}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/( ( (?(1)0|) )* )/xBM
+Memory allocation (code space): 104
+------------------------------------------------------------------
+ 0 23 Bra
+ 2 19 CBra 1
+ 5 Brazero
+ 6 13 SCBra 2
+ 9 6 Cond
+ 11 1 Cond ref
+ 13 0
+ 15 2 Alt
+ 17 8 Ket
+ 19 13 KetRmax
+ 21 19 Ket
+ 23 23 Ket
+ 25 End
+------------------------------------------------------------------
+
+/( (?(1)0|)* )/xBM
+Memory allocation (code space): 84
+------------------------------------------------------------------
+ 0 18 Bra
+ 2 14 CBra 1
+ 5 Brazero
+ 6 6 SCond
+ 8 1 Cond ref
+ 10 0
+ 12 2 Alt
+ 14 8 KetRmax
+ 16 14 Ket
+ 18 18 Ket
+ 20 End
+------------------------------------------------------------------
+
+/[a]/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[a]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 a
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\xaa]/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{aa}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[\xaa]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 \x{aa}
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^a]/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^a]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^a]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^a]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\xaa]/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^\x{aa}]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\xaa]/8BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 4 Bra
+ 2 [^\x{aa}]
+ 4 4 Ket
+ 6 End
+------------------------------------------------------------------
+
+/[^\d]/8WB
+------------------------------------------------------------------
+ 0 9 Bra
+ 2 [^\p{Nd}]
+ 9 9 Ket
+ 11 End
+------------------------------------------------------------------
+
+/[[:^alpha:][:^cntrl:]]+/8WB
+------------------------------------------------------------------
+ 0 18 Bra
+ 2 [ -~\x80-\xff\P{L}]++
+ 18 18 Ket
+ 20 End
+------------------------------------------------------------------
+
+/[[:^cntrl:][:^alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 18 Bra
+ 2 [ -~\x80-\xff\P{L}]++
+ 18 18 Ket
+ 20 End
+------------------------------------------------------------------
+
+/[[:alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 10 Bra
+ 2 [\p{L}]++
+ 10 10 Ket
+ 12 End
+------------------------------------------------------------------
+
+/[[:^alpha:]\S]+/8WB
+------------------------------------------------------------------
+ 0 13 Bra
+ 2 [\P{L}\P{Xsp}]++
+ 13 13 Ket
+ 15 End
+------------------------------------------------------------------
+
+/abc(d|e)(*THEN)x(123(*THEN)4|567(b|q)(*THEN)xx)/B
+------------------------------------------------------------------
+ 0 60 Bra
+ 2 abc
+ 8 5 CBra 1
+ 11 d
+ 13 4 Alt
+ 15 e
+ 17 9 Ket
+ 19 *THEN
+ 20 x
+ 22 12 CBra 2
+ 25 123
+ 31 *THEN
+ 32 4
+ 34 24 Alt
+ 36 567
+ 42 5 CBra 3
+ 45 b
+ 47 4 Alt
+ 49 q
+ 51 9 Ket
+ 53 *THEN
+ 54 xx
+ 58 36 Ket
+ 60 60 Ket
+ 62 End
+------------------------------------------------------------------
+
+/-- End of testinput11 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput11-8 b/ext/pcre/pcrelib/testdata/testoutput11-8
new file mode 100644
index 0000000000..d4a21334e3
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput11-8
@@ -0,0 +1,712 @@
+/-- These are a few representative patterns whose lengths and offsets are to be
+shown when the link size is 2. This is just a doublecheck test to ensure the
+sizes don't go horribly wrong when something is changed. The pattern contents
+are all themselves checked in other tests. Unicode, including property support,
+is required for these tests. --/
+
+/((?i)b)/BM
+Memory allocation (code space): 17
+------------------------------------------------------------------
+ 0 13 Bra
+ 3 7 CBra 1
+ 8 /i b
+ 10 7 Ket
+ 13 13 Ket
+ 16 End
+------------------------------------------------------------------
+
+/(?s)(.*X|^B)/BM
+Memory allocation (code space): 25
+------------------------------------------------------------------
+ 0 21 Bra
+ 3 9 CBra 1
+ 8 AllAny*
+ 10 X
+ 12 6 Alt
+ 15 ^
+ 16 B
+ 18 15 Ket
+ 21 21 Ket
+ 24 End
+------------------------------------------------------------------
+
+/(?s:.*X|^B)/BM
+Memory allocation (code space): 23
+------------------------------------------------------------------
+ 0 19 Bra
+ 3 7 Bra
+ 6 AllAny*
+ 8 X
+ 10 6 Alt
+ 13 ^
+ 14 B
+ 16 13 Ket
+ 19 19 Ket
+ 22 End
+------------------------------------------------------------------
+
+/^[[:alnum:]]/BM
+Memory allocation (code space): 41
+------------------------------------------------------------------
+ 0 37 Bra
+ 3 ^
+ 4 [0-9A-Za-z]
+ 37 37 Ket
+ 40 End
+------------------------------------------------------------------
+
+/#/IxMD
+Memory allocation (code space): 7
+------------------------------------------------------------------
+ 0 3 Bra
+ 3 3 Ket
+ 6 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+May match empty string
+Options: extended
+No first char
+No need char
+
+/a#/IxMD
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 a
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: extended
+First char = 'a'
+No need char
+
+/x?+/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 x?+
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/x++/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 x++
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/x{1,3}+/BM
+Memory allocation (code space): 13
+------------------------------------------------------------------
+ 0 9 Bra
+ 3 x
+ 5 x{0,2}+
+ 9 9 Ket
+ 12 End
+------------------------------------------------------------------
+
+/(x)*+/BM
+Memory allocation (code space): 18
+------------------------------------------------------------------
+ 0 14 Bra
+ 3 Braposzero
+ 4 7 CBraPos 1
+ 9 x
+ 11 7 KetRpos
+ 14 14 Ket
+ 17 End
+------------------------------------------------------------------
+
+/^((a+)(?U)([ab]+)(?-U)([bc]+)(\w*))/BM
+Memory allocation (code space): 120
+------------------------------------------------------------------
+ 0 116 Bra
+ 3 ^
+ 4 109 CBra 1
+ 9 7 CBra 2
+ 14 a+
+ 16 7 Ket
+ 19 39 CBra 3
+ 24 [ab]+?
+ 58 39 Ket
+ 61 39 CBra 4
+ 66 [bc]+
+100 39 Ket
+103 7 CBra 5
+108 \w*+
+110 7 Ket
+113 109 Ket
+116 116 Ket
+119 End
+------------------------------------------------------------------
+
+|8J\$WE\<\.rX\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 826
+------------------------------------------------------------------
+ 0 822 Bra
+ 3 8J$WE<.rX+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+821 \b
+822 822 Ket
+825 End
+------------------------------------------------------------------
+
+|\$\<\.X\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|BM
+Memory allocation (code space): 816
+------------------------------------------------------------------
+ 0 812 Bra
+ 3 $<.X+ix[d1b!H#?vV0vrK:ZH1=2M>iV;?aPhFB<*vW@QW@sO9}cfZA-i'w%hKd6gt1UJP,15_#QY$M^Mss_U/]&LK9[5vQub^w[KDD<EjmhUZ?.akp2dF>qmj;2}YWFdYx.Ap]hjCPTP(n28k+3;o&WXqs/gOXdr$:r'do0;b4c(f_Gr="\4)[01T7ajQJvL$W~mL_sS/4h:x*[ZN=KLs&L5zX//>it,o:aU(;Z>pW&T7oP'2K^E:x9'c[%z-,64JQ5AeH_G#KijUKghQw^\vea3a?kka_G$8#`*kynsxzBLru']k_[7FrVx}^=$blx>s-N%j;D*aZDnsw:YKZ%Q.Kne9#hP?+b3(SOvL,^;&u5@?5C5Bhb=m-vEh_L15Jl]U)0RP6{q%L^_z5E'Dw6X
+811 \b
+812 812 Ket
+815 End
+------------------------------------------------------------------
+
+/(a(?1)b)/BM
+Memory allocation (code space): 22
+------------------------------------------------------------------
+ 0 18 Bra
+ 3 12 CBra 1
+ 8 a
+ 10 3 Recurse
+ 13 b
+ 15 12 Ket
+ 18 18 Ket
+ 21 End
+------------------------------------------------------------------
+
+/(a(?1)+b)/BM
+Memory allocation (code space): 28
+------------------------------------------------------------------
+ 0 24 Bra
+ 3 18 CBra 1
+ 8 a
+ 10 6 Once
+ 13 3 Recurse
+ 16 6 KetRmax
+ 19 b
+ 21 18 Ket
+ 24 24 Ket
+ 27 End
+------------------------------------------------------------------
+
+/a(?P<name1>b|c)d(?P<longername2>e)/BM
+Memory allocation (code space): 36
+------------------------------------------------------------------
+ 0 32 Bra
+ 3 a
+ 5 7 CBra 1
+ 10 b
+ 12 5 Alt
+ 15 c
+ 17 12 Ket
+ 20 d
+ 22 7 CBra 2
+ 27 e
+ 29 7 Ket
+ 32 32 Ket
+ 35 End
+------------------------------------------------------------------
+
+/(?:a(?P<c>c(?P<d>d)))(?P<a>a)/BM
+Memory allocation (code space): 45
+------------------------------------------------------------------
+ 0 41 Bra
+ 3 25 Bra
+ 6 a
+ 8 17 CBra 1
+ 13 c
+ 15 7 CBra 2
+ 20 d
+ 22 7 Ket
+ 25 17 Ket
+ 28 25 Ket
+ 31 7 CBra 3
+ 36 a
+ 38 7 Ket
+ 41 41 Ket
+ 44 End
+------------------------------------------------------------------
+
+/(?P<a>a)...(?P=a)bbb(?P>a)d/BM
+Memory allocation (code space): 34
+------------------------------------------------------------------
+ 0 30 Bra
+ 3 7 CBra 1
+ 8 a
+ 10 7 Ket
+ 13 Any
+ 14 Any
+ 15 Any
+ 16 \1
+ 19 bbb
+ 25 3 Recurse
+ 28 d
+ 30 30 Ket
+ 33 End
+------------------------------------------------------------------
+
+/abc(?C255)de(?C)f/BM
+Memory allocation (code space): 31
+------------------------------------------------------------------
+ 0 27 Bra
+ 3 abc
+ 9 Callout 255 10 1
+ 15 de
+ 19 Callout 0 16 1
+ 25 f
+ 27 27 Ket
+ 30 End
+------------------------------------------------------------------
+
+/abcde/CBM
+Memory allocation (code space): 53
+------------------------------------------------------------------
+ 0 49 Bra
+ 3 Callout 255 0 1
+ 9 a
+ 11 Callout 255 1 1
+ 17 b
+ 19 Callout 255 2 1
+ 25 c
+ 27 Callout 255 3 1
+ 33 d
+ 35 Callout 255 4 1
+ 41 e
+ 43 Callout 255 5 0
+ 49 49 Ket
+ 52 End
+------------------------------------------------------------------
+
+/\x{100}/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{100}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/\x{1000}/8BM
+Memory allocation (code space): 11
+------------------------------------------------------------------
+ 0 7 Bra
+ 3 \x{1000}
+ 7 7 Ket
+ 10 End
+------------------------------------------------------------------
+
+/\x{10000}/8BM
+Memory allocation (code space): 12
+------------------------------------------------------------------
+ 0 8 Bra
+ 3 \x{10000}
+ 8 8 Ket
+ 11 End
+------------------------------------------------------------------
+
+/\x{100000}/8BM
+Memory allocation (code space): 12
+------------------------------------------------------------------
+ 0 8 Bra
+ 3 \x{100000}
+ 8 8 Ket
+ 11 End
+------------------------------------------------------------------
+
+/\x{10ffff}/8BM
+Memory allocation (code space): 12
+------------------------------------------------------------------
+ 0 8 Bra
+ 3 \x{10ffff}
+ 8 8 Ket
+ 11 End
+------------------------------------------------------------------
+
+/\x{110000}/8BM
+Failed: character value in \x{} or \o{} is too large at offset 9
+
+/[\x{ff}]/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{ff}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/[\x{100}]/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{100}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/\x80/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{80}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/\xff/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{ff}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/\x{0041}\x{2262}\x{0391}\x{002e}/D8M
+Memory allocation (code space): 18
+------------------------------------------------------------------
+ 0 14 Bra
+ 3 A\x{2262}\x{391}.
+ 14 14 Ket
+ 17 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = '.'
+
+/\x{D55c}\x{ad6d}\x{C5B4}/D8M
+Memory allocation (code space): 19
+------------------------------------------------------------------
+ 0 15 Bra
+ 3 \x{d55c}\x{ad6d}\x{c5b4}
+ 15 15 Ket
+ 18 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ed}
+Need char = \x{b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/D8M
+Memory allocation (code space): 19
+------------------------------------------------------------------
+ 0 15 Bra
+ 3 \x{65e5}\x{672c}\x{8a9e}
+ 15 15 Ket
+ 18 End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{e6}
+Need char = \x{9e}
+
+/[\x{100}]/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{100}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/[Z\x{100}]/8BM
+Memory allocation (code space): 47
+------------------------------------------------------------------
+ 0 43 Bra
+ 3 [Z\x{100}]
+ 43 43 Ket
+ 46 End
+------------------------------------------------------------------
+
+/^[\x{100}\E-\Q\E\x{150}]/B8M
+Memory allocation (code space): 18
+------------------------------------------------------------------
+ 0 14 Bra
+ 3 ^
+ 4 [\x{100}-\x{150}]
+ 14 14 Ket
+ 17 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E]/B8M
+Memory allocation (code space): 18
+------------------------------------------------------------------
+ 0 14 Bra
+ 3 ^
+ 4 [\x{100}-\x{150}]
+ 14 14 Ket
+ 17 End
+------------------------------------------------------------------
+
+/^[\QÄ€\E-\QÅ\E/B8M
+Failed: missing terminating ] for character class at offset 15
+
+/[\p{L}]/BM
+Memory allocation (code space): 15
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [\p{L}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[\p{^L}]/BM
+Memory allocation (code space): 15
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [\P{L}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[\P{L}]/BM
+Memory allocation (code space): 15
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [\P{L}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[\P{^L}]/BM
+Memory allocation (code space): 15
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [\p{L}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[abc\p{L}\x{0660}]/8BM
+Memory allocation (code space): 50
+------------------------------------------------------------------
+ 0 46 Bra
+ 3 [a-c\p{L}\x{660}]
+ 46 46 Ket
+ 49 End
+------------------------------------------------------------------
+
+/[\p{Nd}]/8BM
+Memory allocation (code space): 15
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [\p{Nd}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[\p{Nd}+-]+/8BM
+Memory allocation (code space): 48
+------------------------------------------------------------------
+ 0 44 Bra
+ 3 [+\-\p{Nd}]++
+ 44 44 Ket
+ 47 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iBM
+Memory allocation (code space): 25
+------------------------------------------------------------------
+ 0 21 Bra
+ 3 /i A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 21 21 Ket
+ 24 End
+------------------------------------------------------------------
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8BM
+Memory allocation (code space): 25
+------------------------------------------------------------------
+ 0 21 Bra
+ 3 A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ 21 21 Ket
+ 24 End
+------------------------------------------------------------------
+
+/[\x{105}-\x{109}]/8iBM
+Memory allocation (code space): 17
+------------------------------------------------------------------
+ 0 13 Bra
+ 3 [\x{104}-\x{109}]
+ 13 13 Ket
+ 16 End
+------------------------------------------------------------------
+
+/( ( (?(1)0|) )* )/xBM
+Memory allocation (code space): 38
+------------------------------------------------------------------
+ 0 34 Bra
+ 3 28 CBra 1
+ 8 Brazero
+ 9 19 SCBra 2
+ 14 8 Cond
+ 17 1 Cond ref
+ 20 0
+ 22 3 Alt
+ 25 11 Ket
+ 28 19 KetRmax
+ 31 28 Ket
+ 34 34 Ket
+ 37 End
+------------------------------------------------------------------
+
+/( (?(1)0|)* )/xBM
+Memory allocation (code space): 30
+------------------------------------------------------------------
+ 0 26 Bra
+ 3 20 CBra 1
+ 8 Brazero
+ 9 8 SCond
+ 12 1 Cond ref
+ 15 0
+ 17 3 Alt
+ 20 11 KetRmax
+ 23 20 Ket
+ 26 26 Ket
+ 29 End
+------------------------------------------------------------------
+
+/[a]/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 a
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[a]/8BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 a
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[\xaa]/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 \x{aa}
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[\xaa]/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 \x{aa}
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/[^a]/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 [^a]
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[^a]/8BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 [^a]
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[^\xaa]/BM
+Memory allocation (code space): 9
+------------------------------------------------------------------
+ 0 5 Bra
+ 3 [^\x{aa}]
+ 5 5 Ket
+ 8 End
+------------------------------------------------------------------
+
+/[^\xaa]/8BM
+Memory allocation (code space): 10
+------------------------------------------------------------------
+ 0 6 Bra
+ 3 [^\x{aa}]
+ 6 6 Ket
+ 9 End
+------------------------------------------------------------------
+
+/[^\d]/8WB
+------------------------------------------------------------------
+ 0 11 Bra
+ 3 [^\p{Nd}]
+ 11 11 Ket
+ 14 End
+------------------------------------------------------------------
+
+/[[:^alpha:][:^cntrl:]]+/8WB
+------------------------------------------------------------------
+ 0 44 Bra
+ 3 [ -~\x80-\xff\P{L}]++
+ 44 44 Ket
+ 47 End
+------------------------------------------------------------------
+
+/[[:^cntrl:][:^alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 44 Bra
+ 3 [ -~\x80-\xff\P{L}]++
+ 44 44 Ket
+ 47 End
+------------------------------------------------------------------
+
+/[[:alpha:]]+/8WB
+------------------------------------------------------------------
+ 0 12 Bra
+ 3 [\p{L}]++
+ 12 12 Ket
+ 15 End
+------------------------------------------------------------------
+
+/[[:^alpha:]\S]+/8WB
+------------------------------------------------------------------
+ 0 15 Bra
+ 3 [\P{L}\P{Xsp}]++
+ 15 15 Ket
+ 18 End
+------------------------------------------------------------------
+
+/abc(d|e)(*THEN)x(123(*THEN)4|567(b|q)(*THEN)xx)/B
+------------------------------------------------------------------
+ 0 73 Bra
+ 3 abc
+ 9 7 CBra 1
+ 14 d
+ 16 5 Alt
+ 19 e
+ 21 12 Ket
+ 24 *THEN
+ 25 x
+ 27 14 CBra 2
+ 32 123
+ 38 *THEN
+ 39 4
+ 41 29 Alt
+ 44 567
+ 50 7 CBra 3
+ 55 b
+ 57 5 Alt
+ 60 q
+ 62 12 Ket
+ 65 *THEN
+ 66 xx
+ 70 43 Ket
+ 73 73 Ket
+ 76 End
+------------------------------------------------------------------
+
+/-- End of testinput11 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput12 b/ext/pcre/pcrelib/testdata/testoutput12
new file mode 100644
index 0000000000..a76e2aef88
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput12
@@ -0,0 +1,179 @@
+/-- This test is run only when JIT support is available. It checks for a
+successful and an unsuccessful JIT compile and save and restore behaviour,
+and a couple of things that are different with JIT. --/
+
+/abc/S+I
+Capturing subpattern count = 0
+No options
+First char = 'a'
+Need char = 'c'
+Subject length lower bound = 3
+No set of starting bytes
+JIT study was successful
+
+/(?(?C1)(?=a)a)/S+I
+Capturing subpattern count = 0
+May match empty string
+No options
+No first char
+No need char
+Study returned NULL
+JIT study was not successful
+
+/(?(?C1)(?=a)a)/S!+I
+Capturing subpattern count = 0
+May match empty string
+No options
+No first char
+No need char
+Subject length lower bound = -1
+No set of starting bytes
+JIT study was not successful
+
+/abc/S+I>testsavedregex
+Capturing subpattern count = 0
+No options
+First char = 'a'
+Need char = 'c'
+Subject length lower bound = 3
+No set of starting bytes
+JIT study was successful
+Compiled pattern written to testsavedregex
+Study data written to testsavedregex
+
+<testsavedregex
+Compiled pattern loaded from testsavedregex
+Study data loaded from testsavedregex
+ abc
+ 0: abc
+
+/a*/SI
+Capturing subpattern count = 0
+May match empty string
+No options
+No first char
+No need char
+Study returned NULL
+
+/(?(R)a*(?1)|((?R))b)/S+
+ aaaabcde
+Error -27 (JIT stack limit reached)
+
+/-- Test various compile modes --/
+
+/abcd/S++
+ abcd
+ 0: abcd (JIT)
+ xyz
+No match (JIT)
+
+/abcd/S+
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match (JIT)
+
+/abcd/S++
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match (JIT)
+
+/abcd/S++1
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab
+ ab\P\P
+Partial match: ab
+ xyz
+No match (JIT)
+ xyz\P
+No match
+
+/abcd/S++2
+ abcd
+ 0: abcd
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab
+ xyz
+No match
+
+/abcd/S++3
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab
+ xyz
+No match (JIT)
+
+/abcd/S++4
+ abcd
+ 0: abcd
+ ab\P
+Partial match: ab
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match
+
+/abcd/S++5
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match (JIT)
+
+/abcd/S++6
+ abcd
+ 0: abcd
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match
+
+/abcd/S++7
+ abcd
+ 0: abcd (JIT)
+ ab\P
+Partial match: ab (JIT)
+ ab\P\P
+Partial match: ab (JIT)
+ xyz
+No match (JIT)
+
+/abcd/S++2I
+Capturing subpattern count = 0
+No options
+First char = 'a'
+Need char = 'd'
+Subject length lower bound = 4
+No set of starting bytes
+JIT study was successful
+
+/(*NO_START_OPT)a(*:m)b/KS++
+ a
+No match, mark = m (JIT)
+
+/^12345678abcd/mS++
+ 12345678abcd
+ 0: 12345678abcd (JIT)
+
+/-- End of testinput12 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput13 b/ext/pcre/pcrelib/testdata/testoutput13
new file mode 100644
index 0000000000..9f73c5000f
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput13
@@ -0,0 +1,22 @@
+/-- This test is run only when JIT support is not available. It checks that an
+attempt to use it has the expected behaviour. It also tests things that
+are different without JIT. --/
+
+/abc/S+I
+Capturing subpattern count = 0
+No options
+First char = 'a'
+Need char = 'c'
+Subject length lower bound = 3
+No set of starting bytes
+JIT support is not available in this version of PCRE
+
+/a*/SI
+Capturing subpattern count = 0
+May match empty string
+No options
+No first char
+No need char
+Study returned NULL
+
+/-- End of testinput13 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput14 b/ext/pcre/pcrelib/testdata/testoutput14
new file mode 100644
index 0000000000..52680a8f9c
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput14
@@ -0,0 +1,530 @@
+/-- This set of tests is run only with the 8-bit library. They do not require
+ UTF-8 or Unicode property support. The file starts with all the tests of
+ the POSIX interface, because that is supported only with the 8-bit library.
+ --/
+
+< forbid 8W
+
+/abc/P
+ abc
+ 0: abc
+ *** Failers
+No match: POSIX code 17: match failed
+
+/^abc|def/P
+ abcdef
+ 0: abc
+ abcdef\B
+ 0: def
+
+/.*((abc)$|(def))/P
+ defabc
+ 0: defabc
+ 1: abc
+ 2: abc
+ \Zdefabc
+ 0: def
+ 1: def
+ 3: def
+
+/the quick brown fox/P
+ the quick brown fox
+ 0: the quick brown fox
+ *** Failers
+No match: POSIX code 17: match failed
+ The Quick Brown Fox
+No match: POSIX code 17: match failed
+
+/the quick brown fox/Pi
+ the quick brown fox
+ 0: the quick brown fox
+ The Quick Brown Fox
+ 0: The Quick Brown Fox
+
+/abc.def/P
+ *** Failers
+No match: POSIX code 17: match failed
+ abc\ndef
+No match: POSIX code 17: match failed
+
+/abc$/P
+ abc
+ 0: abc
+ abc\n
+ 0: abc
+
+/(abc)\2/P
+Failed: POSIX code 15: bad back reference at offset 7
+
+/(abc\1)/P
+ abc
+No match: POSIX code 17: match failed
+
+/a*(b+)(z)(z)/P
+ aaaabbbbzzzz
+ 0: aaaabbbbzz
+ 1: bbbb
+ 2: z
+ 3: z
+ aaaabbbbzzzz\O0
+ aaaabbbbzzzz\O1
+ 0: aaaabbbbzz
+ aaaabbbbzzzz\O2
+ 0: aaaabbbbzz
+ 1: bbbb
+ aaaabbbbzzzz\O3
+ 0: aaaabbbbzz
+ 1: bbbb
+ 2: z
+ aaaabbbbzzzz\O4
+ 0: aaaabbbbzz
+ 1: bbbb
+ 2: z
+ 3: z
+ aaaabbbbzzzz\O5
+ 0: aaaabbbbzz
+ 1: bbbb
+ 2: z
+ 3: z
+
+/ab.cd/P
+ ab-cd
+ 0: ab-cd
+ ab=cd
+ 0: ab=cd
+ ** Failers
+No match: POSIX code 17: match failed
+ ab\ncd
+No match: POSIX code 17: match failed
+
+/ab.cd/Ps
+ ab-cd
+ 0: ab-cd
+ ab=cd
+ 0: ab=cd
+ ab\ncd
+ 0: ab\x0acd
+
+/a(b)c/PN
+ abc
+Matched with REG_NOSUB
+
+/a(?P<name>b)c/PN
+ abc
+Matched with REG_NOSUB
+
+/a?|b?/P
+ abc
+ 0: a
+ ** Failers
+ 0:
+ ddd\N
+No match: POSIX code 17: match failed
+
+/\w+A/P
+ CDAAAAB
+ 0: CDAAAA
+
+/\w+A/PU
+ CDAAAAB
+ 0: CDA
+
+/\Biss\B/I+P
+ Mississippi
+ 0: iss
+ 0+ issippi
+
+/abc/\P
+Failed: POSIX code 9: bad escape sequence at offset 4
+
+/-- End of POSIX tests --/
+
+/a\Cb/
+ aXb
+ 0: aXb
+ a\nb
+ 0: a\x0ab
+ ** Failers (too big char)
+No match
+ A\x{123}B
+** Character \x{123} is greater than 255 and UTF-8 mode is not enabled.
+** Truncation will probably give the wrong result.
+No match
+ A\o{443}B
+** Character \x{123} is greater than 255 and UTF-8 mode is not enabled.
+** Truncation will probably give the wrong result.
+No match
+
+/\x{100}/I
+Failed: character value in \x{} or \o{} is too large at offset 6
+
+/\o{400}/I
+Failed: character value in \x{} or \o{} is too large at offset 6
+
+/ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional leading comment
+(?: (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address
+| # or
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # one word, optionally followed by....
+(?:
+[^()<>@,;:".\\\[\]\x80-\xff\000-\010\012-\037] | # atom and space parts, or...
+\(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) | # comments, or...
+
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+# quoted strings
+)*
+< (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # leading <
+(?: @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* , (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+)* # further okay, if led by comma
+: # closing colon
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* )? # optional route
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address spec
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* > # trailing >
+# name and address
+) (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional trailing comment
+/xSI
+Capturing subpattern count = 0
+Contains explicit CR or LF match
+Options: extended
+No first char
+No need char
+Subject length lower bound = 3
+Starting byte set: \x09 \x20 ! " # $ % & ' ( * + - / 0 1 2 3 4 5 6 7 8
+ 9 = ? A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ^ _ ` a b c d e
+ f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f
+
+/-- Although this saved pattern was compiled with link-size=2, it does no harm
+to run this test with other link sizes because it is going to generated a
+"compiled in wrong mode" error as soon as it is loaded, so the link size does
+not matter. --/
+
+<!testsaved16
+Compiled pattern loaded from testsaved16
+No study data
+Error -28 from pcre_fullinfo(0)
+Running in 8-bit mode but pattern was compiled in 16-bit mode
+
+<!testsaved32
+Compiled pattern loaded from testsaved32
+No study data
+Error -28 from pcre_fullinfo(0)
+Running in 8-bit mode but pattern was compiled in 32-bit mode
+
+/\h/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xa0
+
+/\H/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\v/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85
+
+/\V/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\R/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85
+
+/[\h]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0]
+ Ket
+ End
+------------------------------------------------------------------
+ >\x09<
+ 0: \x09
+
+/[\h]+/BZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0]++
+ Ket
+ End
+------------------------------------------------------------------
+ >\x09\x20\xa0<
+ 0: \x09 \xa0
+
+/[\v]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x0a-\x0d\x85]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[\H]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0a-\x1f!-\x9f\xa1-\xff]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\h]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0a-\x1f!-\x9f\xa1-\xff] (neg)
+ Ket
+ End
+------------------------------------------------------------------
+
+/[\V]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x09\x0e-\x84\x86-\xff]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[\x0a\V]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x0a\x0e-\x84\x86-\xff]
+ Ket
+ End
+------------------------------------------------------------------
+
+/\777/I
+Failed: octal value is greater than \377 in 8-bit non-UTF-8 mode at offset 3
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF)XX/K
+Failed: name is too long in (*MARK), (*PRUNE), (*SKIP), or (*THEN) at offset 259
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE)XX/K
+ XX
+ 0: XX
+MK: 0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE
+
+/\u0100/<JS>
+Failed: character value in \u.... sequence is too large at offset 5
+
+/[\u0100-\u0200]/<JS>
+Failed: character value in \u.... sequence is too large at offset 6
+
+/[^\x00-a]{12,}[^b-\xff]*/BZ
+------------------------------------------------------------------
+ Bra
+ [b-\xff] (neg){12,}+
+ [\x00-a] (neg)*+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\s]*\s* [^\W]+\W+ [^\d]*?\d0 [^\d\w]{4,6}?\w*A/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0e-\x1f!-\xff] (neg)*+
+ \s*
+
+ [0-9A-Z_a-z]++
+ \W+
+
+ [\x00-/:-\xff] (neg)*+
+ \d
+ 0
+ [\x00-/:-@[-^`{-\xff] (neg){4,6}+
+ \w*
+ A
+ Ket
+ End
+------------------------------------------------------------------
+
+/-- End of testinput14 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput15 b/ext/pcre/pcrelib/testdata/testoutput15
new file mode 100644
index 0000000000..5792be72df
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput15
@@ -0,0 +1,1139 @@
+/-- This set of tests is for UTF-8 support but not Unicode property support,
+ and is relevant only to the 8-bit library. --/
+
+< forbid W
+
+/X(\C{3})/8
+ X\x{1234}
+ 0: X\x{1234}
+ 1: \x{1234}
+
+/X(\C{4})/8
+ X\x{1234}YZ
+ 0: X\x{1234}Y
+ 1: \x{1234}Y
+
+/X\C*/8
+ XYZabcdce
+ 0: XYZabcdce
+
+/X\C*?/8
+ XYZabcde
+ 0: X
+
+/X\C{3,5}/8
+ Xabcdefg
+ 0: Xabcde
+ X\x{1234}
+ 0: X\x{1234}
+ X\x{1234}YZ
+ 0: X\x{1234}YZ
+ X\x{1234}\x{512}
+ 0: X\x{1234}\x{512}
+ X\x{1234}\x{512}YZ
+ 0: X\x{1234}\x{512}
+
+/X\C{3,5}?/8
+ Xabcdefg
+ 0: Xabc
+ X\x{1234}
+ 0: X\x{1234}
+ X\x{1234}YZ
+ 0: X\x{1234}
+ X\x{1234}\x{512}
+ 0: X\x{1234}
+
+/a\Cb/8
+ aXb
+ 0: aXb
+ a\nb
+ 0: a\x{0a}b
+
+/a\C\Cb/8
+ a\x{100}b
+ 0: a\x{100}b
+
+/ab\Cde/8
+ abXde
+ 0: abXde
+
+/a\C\Cb/8
+ a\x{100}b
+ 0: a\x{100}b
+ ** Failers
+No match
+ a\x{12257}b
+No match
+
+/[Ã]/8
+Failed: invalid UTF-8 string at offset 1
+
+/Ã/8
+Failed: invalid UTF-8 string at offset 0
+
+/ÃÃÃxxx/8
+Failed: invalid UTF-8 string at offset 0
+
+/ÃÃÃxxx/8?DZSSO
+------------------------------------------------------------------
+ Bra
+ \X{c0}\X{c0}\X{c0}xxx
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: no_auto_possessify utf no_utf_check
+First char = \x{c3}
+Need char = 'x'
+
+/badutf/8
+ \xdf
+Error -10 (bad UTF-8 string) offset=0 reason=1
+ \xef
+Error -10 (bad UTF-8 string) offset=0 reason=2
+ \xef\x80
+Error -10 (bad UTF-8 string) offset=0 reason=1
+ \xf7
+Error -10 (bad UTF-8 string) offset=0 reason=3
+ \xf7\x80
+Error -10 (bad UTF-8 string) offset=0 reason=2
+ \xf7\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=1
+ \xfb
+Error -10 (bad UTF-8 string) offset=0 reason=4
+ \xfb\x80
+Error -10 (bad UTF-8 string) offset=0 reason=3
+ \xfb\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=2
+ \xfb\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=1
+ \xfd
+Error -10 (bad UTF-8 string) offset=0 reason=5
+ \xfd\x80
+Error -10 (bad UTF-8 string) offset=0 reason=4
+ \xfd\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=3
+ \xfd\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=2
+ \xfd\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=1
+ \xdf\x7f
+Error -10 (bad UTF-8 string) offset=0 reason=6
+ \xef\x7f\x80
+Error -10 (bad UTF-8 string) offset=0 reason=6
+ \xef\x80\x7f
+Error -10 (bad UTF-8 string) offset=0 reason=7
+ \xf7\x7f\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=6
+ \xf7\x80\x7f\x80
+Error -10 (bad UTF-8 string) offset=0 reason=7
+ \xf7\x80\x80\x7f
+Error -10 (bad UTF-8 string) offset=0 reason=8
+ \xfb\x7f\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=6
+ \xfb\x80\x7f\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=7
+ \xfb\x80\x80\x7f\x80
+Error -10 (bad UTF-8 string) offset=0 reason=8
+ \xfb\x80\x80\x80\x7f
+Error -10 (bad UTF-8 string) offset=0 reason=9
+ \xfd\x7f\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=6
+ \xfd\x80\x7f\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=7
+ \xfd\x80\x80\x7f\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=8
+ \xfd\x80\x80\x80\x7f\x80
+Error -10 (bad UTF-8 string) offset=0 reason=9
+ \xfd\x80\x80\x80\x80\x7f
+Error -10 (bad UTF-8 string) offset=0 reason=10
+ \xed\xa0\x80
+Error -10 (bad UTF-8 string) offset=0 reason=14
+ \xc0\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=15
+ \xe0\x80\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=16
+ \xf0\x80\x80\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=17
+ \xf8\x80\x80\x80\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=18
+ \xfc\x80\x80\x80\x80\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=19
+ \x80
+Error -10 (bad UTF-8 string) offset=0 reason=20
+ \xfe
+Error -10 (bad UTF-8 string) offset=0 reason=21
+ \xff
+Error -10 (bad UTF-8 string) offset=0 reason=21
+
+/badutf/8
+ \xfb\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=11
+ \xfd\x80\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=12
+ \xf7\xbf\xbf\xbf
+Error -10 (bad UTF-8 string) offset=0 reason=13
+
+/shortutf/8
+ \P\P\xdf
+Error -25 (short UTF-8 string) offset=0 reason=1
+ \P\P\xef
+Error -25 (short UTF-8 string) offset=0 reason=2
+ \P\P\xef\x80
+Error -25 (short UTF-8 string) offset=0 reason=1
+ \P\P\xf7
+Error -25 (short UTF-8 string) offset=0 reason=3
+ \P\P\xf7\x80
+Error -25 (short UTF-8 string) offset=0 reason=2
+ \P\P\xf7\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=1
+ \P\P\xfb
+Error -25 (short UTF-8 string) offset=0 reason=4
+ \P\P\xfb\x80
+Error -25 (short UTF-8 string) offset=0 reason=3
+ \P\P\xfb\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=2
+ \P\P\xfb\x80\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=1
+ \P\P\xfd
+Error -25 (short UTF-8 string) offset=0 reason=5
+ \P\P\xfd\x80
+Error -25 (short UTF-8 string) offset=0 reason=4
+ \P\P\xfd\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=3
+ \P\P\xfd\x80\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=2
+ \P\P\xfd\x80\x80\x80\x80
+Error -25 (short UTF-8 string) offset=0 reason=1
+
+/anything/8
+ \xc0\x80
+Error -10 (bad UTF-8 string) offset=0 reason=15
+ \xc1\x8f
+Error -10 (bad UTF-8 string) offset=0 reason=15
+ \xe0\x9f\x80
+Error -10 (bad UTF-8 string) offset=0 reason=16
+ \xf0\x8f\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=17
+ \xf8\x87\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=18
+ \xfc\x83\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=19
+ \xfe\x80\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=21
+ \xff\x80\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=21
+ \xc3\x8f
+No match
+ \xe0\xaf\x80
+No match
+ \xe1\x80\x80
+No match
+ \xf0\x9f\x80\x80
+No match
+ \xf1\x8f\x80\x80
+No match
+ \xf8\x88\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=11
+ \xf9\x87\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=11
+ \xfc\x84\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=12
+ \xfd\x83\x80\x80\x80\x80
+Error -10 (bad UTF-8 string) offset=0 reason=12
+ \?\xf8\x88\x80\x80\x80
+No match
+ \?\xf9\x87\x80\x80\x80
+No match
+ \?\xfc\x84\x80\x80\x80\x80
+No match
+ \?\xfd\x83\x80\x80\x80\x80
+No match
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+
+/\x{1000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{1000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{e1}
+Need char = \x{80}
+
+/\x{10000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{f0}
+Need char = \x{80}
+
+/\x{100000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{f4}
+Need char = \x{80}
+
+/\x{10ffff}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10ffff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{f4}
+Need char = \x{bf}
+
+/[\x{ff}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c3}
+Need char = \x{bf}
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+
+/\x80/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{80}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c2}
+Need char = \x{80}
+
+/\xff/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c3}
+Need char = \x{bf}
+
+/\x{D55c}\x{ad6d}\x{C5B4}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{d55c}\x{ad6d}\x{c5b4}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ed}
+Need char = \x{b4}
+ \x{D55c}\x{ad6d}\x{C5B4}
+ 0: \x{d55c}\x{ad6d}\x{c5b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{65e5}\x{672c}\x{8a9e}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{e6}
+Need char = \x{9e}
+ \x{65e5}\x{672c}\x{8a9e}
+ 0: \x{65e5}\x{672c}\x{8a9e}
+
+/\x{80}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{80}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c2}
+Need char = \x{80}
+
+/\x{084}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{84}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c2}
+Need char = \x{84}
+
+/\x{104}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{104}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{84}
+
+/\x{861}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{861}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{e0}
+Need char = \x{a1}
+
+/\x{212ab}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{212ab}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{f0}
+Need char = \x{ab}
+
+/-- This one is here not because it's different to Perl, but because the way
+the captured single-byte is displayed. (In Perl it becomes a character, and you
+can't tell the difference.) --/
+
+/X(\C)(.*)/8
+ X\x{1234}
+ 0: X\x{1234}
+ 1: \x{e1}
+ 2: \x{88}\x{b4}
+ X\nabc
+ 0: X\x{0a}abc
+ 1: \x{0a}
+ 2: abc
+
+/-- This one is here because Perl gives out a grumbly error message (quite
+correctly, but that messes up comparisons). --/
+
+/a\Cb/8
+ *** Failers
+No match
+ a\x{100}b
+No match
+
+/[^ab\xC0-\xF0]/8SDZ
+------------------------------------------------------------------
+ Bra
+ [\x00-`c-\xbf\xf1-\xff] (neg)
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x09 \x0a
+ \x0b \x0c \x0d \x0e \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19
+ \x1a \x1b \x1c \x1d \x1e \x1f \x20 ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4
+ 5 6 7 8 9 : ; < = > ? @ A B C D E F G H I J K L M N O P Q R S T U V W X Y
+ Z [ \ ] ^ _ ` c d e f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f
+ \xc2 \xc3 \xc4 \xc5 \xc6 \xc7 \xc8 \xc9 \xca \xcb \xcc \xcd \xce \xcf \xd0
+ \xd1 \xd2 \xd3 \xd4 \xd5 \xd6 \xd7 \xd8 \xd9 \xda \xdb \xdc \xdd \xde \xdf
+ \xe0 \xe1 \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee
+ \xef \xf0 \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb \xfc \xfd
+ \xfe \xff
+ \x{f1}
+ 0: \x{f1}
+ \x{bf}
+ 0: \x{bf}
+ \x{100}
+ 0: \x{100}
+ \x{1000}
+ 0: \x{1000}
+ *** Failers
+ 0: *
+ \x{c0}
+No match
+ \x{f0}
+No match
+
+/Ä€{3,4}/8SDZ
+------------------------------------------------------------------
+ Bra
+ \x{100}{3}
+ \x{100}?+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+Subject length lower bound = 3
+No set of starting bytes
+ \x{100}\x{100}\x{100}\x{100\x{100}
+ 0: \x{100}\x{100}\x{100}
+
+/(\x{100}+|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}++
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xc4
+
+/(\x{100}*a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}*+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xc4
+
+/(\x{100}{0,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}{0,2}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xc4
+
+/(\x{100}{1,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}
+ \x{100}{0,1}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xc4
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+
+/a\x{100}\x{101}*/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}*+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{80}
+
+/a\x{100}\x{101}+/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}++
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{81}
+
+/[^\x{c4}]/DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+ \x{100}
+ 0: \x{100}
+ Z\x{100}
+ 0: \x{100}
+ \x{100}Z
+ 0: \x{100}
+ *** Failers
+No match
+
+/[\xff]/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c3}
+Need char = \x{bf}
+ >\x{ff}<
+ 0: \x{ff}
+
+/[^\xff]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{ff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/\x{100}abc(xyz(?1))/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}abc
+ CBra 1
+ xyz
+ Recurse
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+First char = \x{c4}
+Need char = 'z'
+
+/a\x{1234}b/P8
+ a\x{1234}b
+ 0: a\x{1234}b
+
+/\777/8I
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c7}
+Need char = \x{bf}
+ \x{1ff}
+ 0: \x{1ff}
+ \777
+ 0: \x{1ff}
+
+/\x{100}+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = \x{80}
+
+/\x{100}+X/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ X
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c4}
+Need char = 'X'
+
+/^[\QÄ€\E-\QÅ\E/BZ8
+Failed: missing terminating ] for character class at offset 15
+
+/-- This tests the stricter UTF-8 check according to RFC 3629. --/
+
+/X/8
+ \x{d800}
+Error -10 (bad UTF-8 string) offset=0 reason=14
+ \x{d800}\?
+No match
+ \x{da00}
+Error -10 (bad UTF-8 string) offset=0 reason=14
+ \x{da00}\?
+No match
+ \x{dfff}
+Error -10 (bad UTF-8 string) offset=0 reason=14
+ \x{dfff}\?
+No match
+ \x{110000}
+Error -10 (bad UTF-8 string) offset=0 reason=13
+ \x{110000}\?
+No match
+ \x{2000000}
+Error -10 (bad UTF-8 string) offset=0 reason=11
+ \x{2000000}\?
+No match
+ \x{7fffffff}
+Error -10 (bad UTF-8 string) offset=0 reason=12
+ \x{7fffffff}\?
+No match
+
+/(*UTF8)\x{1234}/
+ abcd\x{1234}pqr
+ 0: \x{1234}
+
+/(*CRLF)(*UTF)(*BSR_UNICODE)a\Rb/I
+Capturing subpattern count = 0
+Options: bsr_unicode utf
+Forced newline sequence: CRLF
+First char = 'a'
+Need char = 'b'
+
+/\h/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xc2 \xe1 \xe2 \xe3
+ ABC\x{09}
+ 0: \x{09}
+ ABC\x{20}
+ 0:
+ ABC\x{a0}
+ 0: \x{a0}
+ ABC\x{1680}
+ 0: \x{1680}
+ ABC\x{180e}
+ 0: \x{180e}
+ ABC\x{2000}
+ 0: \x{2000}
+ ABC\x{202f}
+ 0: \x{202f}
+ ABC\x{205f}
+ 0: \x{205f}
+ ABC\x{3000}
+ 0: \x{3000}
+
+/\v/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \xc2 \xe2
+ ABC\x{0a}
+ 0: \x{0a}
+ ABC\x{0b}
+ 0: \x{0b}
+ ABC\x{0c}
+ 0: \x{0c}
+ ABC\x{0d}
+ 0: \x{0d}
+ ABC\x{85}
+ 0: \x{85}
+ ABC\x{2028}
+ 0: \x{2028}
+
+/\h*A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 A \xc2 \xe1 \xe2 \xe3
+ CDBABC
+ 0: A
+
+/\v+A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 2
+Starting byte set: \x0a \x0b \x0c \x0d \xc2 \xe2
+
+/\s?xxx\s/8SI
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 4
+Starting byte set: \x09 \x0a \x0b \x0c \x0d \x20 x
+
+/\sxxx\s/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 5
+Starting byte set: \x09 \x0a \x0c \x0d \x20 \xc2
+ AB\x{85}xxx\x{a0}XYZ
+ 0: \x{85}xxx\x{a0}
+ AB\x{a0}xxx\x{85}XYZ
+ 0: \x{a0}xxx\x{85}
+
+/\S \S/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = ' '
+Subject length lower bound = 3
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x0b \x0e
+ \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19 \x1a \x1b \x1c \x1d
+ \x1e \x1f ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4 5 6 7 8 9 : ; < = > ? @
+ A B C D E F G H I J K L M N O P Q R S T U V W X Y Z [ \ ] ^ _ ` a b c d e
+ f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f \xc0 \xc1 \xc2 \xc3
+ \xc4 \xc5 \xc6 \xc7 \xc8 \xc9 \xca \xcb \xcc \xcd \xce \xcf \xd0 \xd1 \xd2
+ \xd3 \xd4 \xd5 \xd6 \xd7 \xd8 \xd9 \xda \xdb \xdc \xdd \xde \xdf \xe0 \xe1
+ \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee \xef \xf0
+ \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb \xfc \xfd \xfe \xff
+ \x{a2} \x{84}
+ 0: \x{a2} \x{84}
+ A Z
+ 0: A Z
+
+/a+/8
+ a\x{123}aa\>1
+ 0: aa
+ a\x{123}aa\>2
+Error -11 (bad UTF-8 offset)
+ a\x{123}aa\>3
+ 0: aa
+ a\x{123}aa\>4
+ 0: a
+ a\x{123}aa\>5
+No match
+ a\x{123}aa\>6
+Error -24 (bad offset value)
+
+/\x{1234}+/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \xe1
+
+/\x{1234}+?/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \xe1
+
+/\x{1234}++/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \xe1
+
+/\x{1234}{2}/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+No first char
+No need char
+Subject length lower bound = 2
+Starting byte set: \xe1
+
+/[^\x{c4}]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/X+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ X++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'X'
+Need char = \x{80}
+
+/\R/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \xc2 \xe2
+
+/\777/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{1ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{c7}
+Need char = \x{bf}
+
+/\w+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \w++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}
+
+/\w+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \w+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}\x{c4}
+
+/\W+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{A1}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/\W+\x{A1}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/X\s+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ X
+ \s++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}
+
+/X\s+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ X
+ \s+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}\x{a0}
+
+/\S+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ \S+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}\x{a0}
+
+/\S+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \S++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}
+
+/\x{a0}+\s!/8BZ
+------------------------------------------------------------------
+ Bra
+ \x{a0}++
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/\x{a0}+\s!/8BZT1
+------------------------------------------------------------------
+ Bra
+ \x{a0}+
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/A/8
+ \x{ff000041}
+** Character \x{ff000041} is greater than 0x7fffffff and so cannot be converted to UTF-8
+ \x{7f000041}
+Error -10 (bad UTF-8 string) offset=0 reason=12
+
+/(*UTF8)abc/9
+Failed: setting UTF is disabled by the application at offset 0
+
+/abc/89
+Failed: setting UTF is disabled by the application at offset 0
+
+/-- End of testinput15 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput16 b/ext/pcre/pcrelib/testdata/testoutput16
new file mode 100644
index 0000000000..1d5f31d929
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput16
@@ -0,0 +1,121 @@
+/-- This set of tests is run only with the 8-bit library when Unicode property
+ support is available. It starts with tests of the POSIX interface, because
+ that is supported only with the 8-bit library. --/
+
+/\w/P
+ +++\x{c2}
+No match: POSIX code 17: match failed
+
+/\w/WP
+ +++\x{c2}
+ 0: \xc2
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iDZ
+------------------------------------------------------------------
+ Bra
+ /i A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: caseless utf
+First char = 'A' (caseless)
+No need char
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8DZ
+------------------------------------------------------------------
+ Bra
+ A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = \x{b0}
+
+/AB\x{1fb0}/8DZ
+------------------------------------------------------------------
+ Bra
+ AB\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = \x{b0}
+
+/AB\x{1fb0}/8DZi
+------------------------------------------------------------------
+ Bra
+ /i AB\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: caseless utf
+First char = 'A' (caseless)
+Need char = 'B' (caseless)
+
+/\x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}/8iSI
+Capturing subpattern count = 0
+Options: caseless utf
+No first char
+No need char
+Subject length lower bound = 17
+Starting byte set: \xd0 \xd1
+ \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ 0: \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+ 0: \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+
+/[â±¥]/8iBZ
+------------------------------------------------------------------
+ Bra
+ /i \x{2c65}
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^â±¥]/8iBZ
+------------------------------------------------------------------
+ Bra
+ /i [^\x{2c65}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/\h/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xa0
+
+/\v/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85
+
+/\R/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85
+
+/[[:blank:]]/WBZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0]
+ Ket
+ End
+------------------------------------------------------------------
+
+/-- End of testinput16 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput17 b/ext/pcre/pcrelib/testdata/testoutput17
new file mode 100644
index 0000000000..9a469c51ae
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput17
@@ -0,0 +1,558 @@
+/-- This set of tests is for the 16- and 32-bit library's basic (non-UTF-16
+ or -32) features that are not compatible with the 8-bit library, or which
+ give different output in 16- or 32-bit mode. --/
+
+< forbid 8W
+
+/a\Cb/
+ aXb
+ 0: aXb
+ a\nb
+ 0: a\x0ab
+
+/[^\x{c4}]/DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+
+/\x{100}/I
+Capturing subpattern count = 0
+No options
+First char = \x{100}
+No need char
+
+/ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional leading comment
+(?: (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address
+| # or
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # one word, optionally followed by....
+(?:
+[^()<>@,;:".\\\[\]\x80-\xff\000-\010\012-\037] | # atom and space parts, or...
+\(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) | # comments, or...
+
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+# quoted strings
+)*
+< (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # leading <
+(?: @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* , (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+)* # further okay, if led by comma
+: # closing colon
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* )? # optional route
+(?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) # initial word
+(?: (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+|
+" (?: # opening quote...
+[^\\\x80-\xff\n\015"] # Anything except backslash and quote
+| # or
+\\ [^\x80-\xff] # Escaped something (something != CR)
+)* " # closing quote
+) )* # further okay, if led by a period
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* @ (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # initial subdomain
+(?: #
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* \. # if led by a period...
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* (?:
+[^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]+ # some number of atom characters...
+(?![^(\040)<>@,;:".\\\[\]\000-\037\x80-\xff]) # ..not followed by something that could be part of an atom
+| \[ # [
+(?: [^\\\x80-\xff\n\015\[\]] | \\ [^\x80-\xff] )* # stuff
+\] # ]
+) # ...further okay
+)*
+# address spec
+(?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* > # trailing >
+# name and address
+) (?: [\040\t] | \(
+(?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] | \( (?: [^\\\x80-\xff\n\015()] | \\ [^\x80-\xff] )* \) )*
+\) )* # optional trailing comment
+/xSI
+Capturing subpattern count = 0
+Contains explicit CR or LF match
+Options: extended
+No first char
+No need char
+Subject length lower bound = 3
+Starting byte set: \x09 \x20 ! " # $ % & ' ( * + - / 0 1 2 3 4 5 6 7 8
+ 9 = ? A B C D E F G H I J K L M N O P Q R S T U V W X Y Z ^ _ ` a b c d e
+ f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f \xff
+
+/[\h]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]
+ Ket
+ End
+------------------------------------------------------------------
+ >\x09<
+ 0: \x09
+
+/[\h]+/BZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]++
+ Ket
+ End
+------------------------------------------------------------------
+ >\x09\x20\xa0<
+ 0: \x09 \xa0
+
+/[\v]/BZ
+------------------------------------------------------------------
+ Bra
+ [\x0a-\x0d\x85\x{2028}-\x{2029}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\h]/BZ
+------------------------------------------------------------------
+ Bra
+ [^\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/\h+/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xa0 \xff
+ \x{1681}\x{200b}\x{1680}\x{2000}\x{202f}\x{3000}
+ 0: \x{1680}\x{2000}\x{202f}\x{3000}
+ \x{3001}\x{2fff}\x{200a}\xa0\x{2000}
+ 0: \x{200a}\xa0\x{2000}
+
+/[\h\x{dc00}]+/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}\x{dc00}]++
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+ \x{1681}\x{200b}\x{1680}\x{2000}\x{202f}\x{3000}
+ 0: \x{1680}\x{2000}\x{202f}\x{3000}
+ \x{3001}\x{2fff}\x{200a}\xa0\x{2000}
+ 0: \x{200a}\xa0\x{2000}
+
+/\H+/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+ \x{1680}\x{180e}\x{167f}\x{1681}\x{180d}\x{180f}
+ 0: \x{167f}\x{1681}\x{180d}\x{180f}
+ \x{2000}\x{200a}\x{1fff}\x{200b}
+ 0: \x{1fff}\x{200b}
+ \x{202f}\x{205f}\x{202e}\x{2030}\x{205e}\x{2060}
+ 0: \x{202e}\x{2030}\x{205e}\x{2060}
+ \xa0\x{3000}\x9f\xa1\x{2fff}\x{3001}
+ 0: \x9f\xa1\x{2fff}\x{3001}
+
+/[\H\x{d800}]+/
+ \x{1680}\x{180e}\x{167f}\x{1681}\x{180d}\x{180f}
+ 0: \x{167f}\x{1681}\x{180d}\x{180f}
+ \x{2000}\x{200a}\x{1fff}\x{200b}
+ 0: \x{1fff}\x{200b}
+ \x{202f}\x{205f}\x{202e}\x{2030}\x{205e}\x{2060}
+ 0: \x{202e}\x{2030}\x{205e}\x{2060}
+ \xa0\x{3000}\x9f\xa1\x{2fff}\x{3001}
+ 0: \x9f\xa1\x{2fff}\x{3001}
+
+/\v+/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ 0: \x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+ 0: \x85\x0a\x0b\x0c\x0d
+
+/[\v\x{dc00}]+/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x0a-\x0d\x85\x{2028}-\x{2029}\x{dc00}]++
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ 0: \x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+ 0: \x85\x0a\x0b\x0c\x0d
+
+/\V+/SI
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+ \x{2028}\x{2029}\x{2027}\x{2030}
+ 0: \x{2027}\x{2030}
+ \x85\x0a\x0b\x0c\x0d\x09\x0e\x84\x86
+ 0: \x09\x0e\x84\x86
+
+/[\V\x{d800}]+/
+ \x{2028}\x{2029}\x{2027}\x{2030}
+ 0: \x{2027}\x{2030}
+ \x85\x0a\x0b\x0c\x0d\x09\x0e\x84\x86
+ 0: \x09\x0e\x84\x86
+
+/\R+/SI<bsr_unicode>
+Capturing subpattern count = 0
+Options: bsr_unicode
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+ \x{2027}\x{2030}\x{2028}\x{2029}
+ 0: \x{2028}\x{2029}
+ \x09\x0e\x84\x86\x85\x0a\x0b\x0c\x0d
+ 0: \x85\x0a\x0b\x0c\x0d
+
+/\x{d800}\x{d7ff}\x{dc00}\x{dc00}\x{dcff}\x{dd00}/I
+Capturing subpattern count = 0
+No options
+First char = \x{d800}
+Need char = \x{dd00}
+ \x{d800}\x{d7ff}\x{dc00}\x{dc00}\x{dcff}\x{dd00}
+ 0: \x{d800}\x{d7ff}\x{dc00}\x{dc00}\x{dcff}\x{dd00}
+
+/[^\x{80}][^\x{ff}][^\x{100}][^\x{1000}][^\x{ffff}]/BZ
+------------------------------------------------------------------
+ Bra
+ [^\x80]
+ [^\x{ff}]
+ [^\x{100}]
+ [^\x{1000}]
+ [^\x{ffff}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\x{80}][^\x{ff}][^\x{100}][^\x{1000}][^\x{ffff}]/BZi
+------------------------------------------------------------------
+ Bra
+ /i [^\x80]
+ /i [^\x{ff}]
+ /i [^\x{100}]
+ /i [^\x{1000}]
+ /i [^\x{ffff}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\x{100}]*[^\x{1000}]+[^\x{ffff}]??[^\x{8000}]{4,}[^\x{7fff}]{2,9}?[^\x{100}]{5,6}+/BZ
+------------------------------------------------------------------
+ Bra
+ [^\x{100}]*
+ [^\x{1000}]+
+ [^\x{ffff}]??
+ [^\x{8000}]{4}
+ [^\x{8000}]*
+ [^\x{7fff}]{2}
+ [^\x{7fff}]{0,7}?
+ [^\x{100}]{5}
+ [^\x{100}]?+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\x{100}]*[^\x{1000}]+[^\x{ffff}]??[^\x{8000}]{4,}[^\x{7fff}]{2,9}?[^\x{100}]{5,6}+/BZi
+------------------------------------------------------------------
+ Bra
+ /i [^\x{100}]*
+ /i [^\x{1000}]+
+ /i [^\x{ffff}]??
+ /i [^\x{8000}]{4}
+ /i [^\x{8000}]*
+ /i [^\x{7fff}]{2}
+ /i [^\x{7fff}]{0,7}?
+ /i [^\x{100}]{5}
+ /i [^\x{100}]?+
+ Ket
+ End
+------------------------------------------------------------------
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF)XX/K
+ XX
+ 0: XX
+MK: 0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF
+
+/(*:0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE)XX/K
+ XX
+ 0: XX
+MK: 0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0123456789ABCDE
+
+/\u0100/<JS>BZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+
+/[\u0100-\u0200]/<JS>BZ
+------------------------------------------------------------------
+ Bra
+ [\x{100}-\x{200}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/\ud800/<JS>BZ
+------------------------------------------------------------------
+ Bra
+ \x{d800}
+ Ket
+ End
+------------------------------------------------------------------
+
+/^\x{ffff}+/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}?/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}*/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}{3}/i
+ \x{ffff}\x{ffff}\x{ffff}
+ 0: \x{ffff}\x{ffff}\x{ffff}
+
+/^\x{ffff}{0,3}/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/[^\x00-a]{12,}[^b-\xff]*/BZ
+------------------------------------------------------------------
+ Bra
+ [b-\xff] (neg){12,}
+ [\x00-a] (neg)*+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^\s]*\s* [^\W]+\W+ [^\d]*?\d0 [^\d\w]{4,6}?\w*A/BZ
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0e-\x1f!-\xff] (neg)*
+ \s*
+
+ [0-9A-Z_a-z]++
+ \W+
+
+ [\x00-/:-\xff] (neg)*?
+ \d
+ 0
+ [\x00-/:-@[-^`{-\xff] (neg){4,6}?
+ \w*
+ A
+ Ket
+ End
+------------------------------------------------------------------
+
+/a*[b-\x{200}]?a#a*[b-\x{200}]?b#[a-f]*[g-\x{200}]*#[g-\x{200}]*[a-c]*#[g-\x{200}]*[a-h]*/BZ
+------------------------------------------------------------------
+ Bra
+ a*
+ [b-\x{200}]?+
+ a#
+ a*+
+ [b-\x{200}]?
+ b#
+ [a-f]*
+ [g-\x{200}]*+
+ #
+ [g-\x{200}]*
+ [a-c]*+
+ #
+ [g-\x{200}]*
+ [a-h]*+
+ Ket
+ End
+------------------------------------------------------------------
+
+/^[\x{1234}\x{4321}]{2,4}?/
+ \x{1234}\x{1234}\x{1234}
+ 0: \x{1234}\x{1234}
+
+/-- End of testinput17 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput18-16 b/ext/pcre/pcrelib/testdata/testoutput18-16
new file mode 100644
index 0000000000..1ca9ee7401
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput18-16
@@ -0,0 +1,1026 @@
+/-- This set of tests is for UTF-16 and UTF-32 support, and is relevant only to
+ the 16- and 32-bit libraries. --/
+
+< forbid W
+
+/ÃÃÃxxx/8?DZSS
+**Failed: invalid UTF-8 string cannot be converted to UTF-16
+
+/abc/8
+ Ã]
+**Failed: invalid UTF-8 string cannot be used as input in UTF mode
+
+/X(\C{3})/8
+ X\x{11234}Y
+ 0: X\x{11234}Y
+ 1: \x{11234}Y
+ X\x{11234}YZ
+ 0: X\x{11234}Y
+ 1: \x{11234}Y
+
+/X(\C{4})/8
+ X\x{11234}YZ
+ 0: X\x{11234}YZ
+ 1: \x{11234}YZ
+ X\x{11234}YZW
+ 0: X\x{11234}YZ
+ 1: \x{11234}YZ
+
+/X\C*/8
+ XYZabcdce
+ 0: XYZabcdce
+
+/X\C*?/8
+ XYZabcde
+ 0: X
+
+/X\C{3,5}/8
+ Xabcdefg
+ 0: Xabcde
+ X\x{11234}Y
+ 0: X\x{11234}Y
+ X\x{11234}YZ
+ 0: X\x{11234}YZ
+ X\x{11234}\x{512}
+ 0: X\x{11234}\x{512}
+ X\x{11234}\x{512}YZ
+ 0: X\x{11234}\x{512}YZ
+ X\x{11234}\x{512}\x{11234}Z
+ 0: X\x{11234}\x{512}\x{11234}
+
+/X\C{3,5}?/8
+ Xabcdefg
+ 0: Xabc
+ X\x{11234}Y
+ 0: X\x{11234}Y
+ X\x{11234}YZ
+ 0: X\x{11234}Y
+ X\x{11234}\x{512}YZ
+ 0: X\x{11234}\x{512}
+ *** Failers
+No match
+ X\x{11234}
+No match
+
+/a\Cb/8
+ aXb
+ 0: aXb
+ a\nb
+ 0: a\x{0a}b
+
+/a\C\Cb/8
+ a\x{12257}b
+ 0: a\x{12257}b
+ a\x{12257}\x{11234}b
+No match
+ ** Failers
+No match
+ a\x{100}b
+No match
+
+/ab\Cde/8
+ abXde
+ 0: abXde
+
+/-- Check maximum character size --/
+
+/\x{ffff}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ffff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ffff}
+No need char
+
+/\x{10000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d800}
+Need char = \x{dc00}
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/\x{1000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{1000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{1000}
+No need char
+
+/\x{10000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d800}
+Need char = \x{dc00}
+
+/\x{100000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{dbc0}
+Need char = \x{dc00}
+
+/\x{10ffff}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10ffff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{dbff}
+Need char = \x{dfff}
+
+/[\x{ff}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/\x80/8DZ
+------------------------------------------------------------------
+ Bra
+ \x80
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{80}
+No need char
+
+/\xff/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+
+/\x{D55c}\x{ad6d}\x{C5B4}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{d55c}\x{ad6d}\x{c5b4}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d55c}
+Need char = \x{c5b4}
+ \x{D55c}\x{ad6d}\x{C5B4}
+ 0: \x{d55c}\x{ad6d}\x{c5b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{65e5}\x{672c}\x{8a9e}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{65e5}
+Need char = \x{8a9e}
+ \x{65e5}\x{672c}\x{8a9e}
+ 0: \x{65e5}\x{672c}\x{8a9e}
+
+/\x{80}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x80
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{80}
+No need char
+
+/\x{084}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{84}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{84}
+No need char
+
+/\x{104}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{104}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{104}
+No need char
+
+/\x{861}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{861}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{861}
+No need char
+
+/\x{212ab}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{212ab}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d844}
+Need char = \x{deab}
+
+/-- This one is here not because it's different to Perl, but because the way
+the captured single-byte is displayed. (In Perl it becomes a character, and you
+can't tell the difference.) --/
+
+/X(\C)(.*)/8
+ X\x{1234}
+ 0: X\x{1234}
+ 1: \x{1234}
+ 2:
+ X\nabc
+ 0: X\x{0a}abc
+ 1: \x{0a}
+ 2: abc
+
+/-- This one is here because Perl gives out a grumbly error message (quite
+correctly, but that messes up comparisons). --/
+
+/a\Cb/8
+ *** Failers
+No match
+ a\x{100}b
+ 0: a\x{100}b
+
+/[^ab\xC0-\xF0]/8SDZ
+------------------------------------------------------------------
+ Bra
+ [\x00-`c-\xbf\xf1-\xff] (neg)
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x09 \x0a
+ \x0b \x0c \x0d \x0e \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19
+ \x1a \x1b \x1c \x1d \x1e \x1f \x20 ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4
+ 5 6 7 8 9 : ; < = > ? @ A B C D E F G H I J K L M N O P Q R S T U V W X Y
+ Z [ \ ] ^ _ ` c d e f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f
+ \x80 \x81 \x82 \x83 \x84 \x85 \x86 \x87 \x88 \x89 \x8a \x8b \x8c \x8d \x8e
+ \x8f \x90 \x91 \x92 \x93 \x94 \x95 \x96 \x97 \x98 \x99 \x9a \x9b \x9c \x9d
+ \x9e \x9f \xa0 \xa1 \xa2 \xa3 \xa4 \xa5 \xa6 \xa7 \xa8 \xa9 \xaa \xab \xac
+ \xad \xae \xaf \xb0 \xb1 \xb2 \xb3 \xb4 \xb5 \xb6 \xb7 \xb8 \xb9 \xba \xbb
+ \xbc \xbd \xbe \xbf \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb
+ \xfc \xfd \xfe \xff
+ \x{f1}
+ 0: \x{f1}
+ \x{bf}
+ 0: \x{bf}
+ \x{100}
+ 0: \x{100}
+ \x{1000}
+ 0: \x{1000}
+ *** Failers
+ 0: *
+ \x{c0}
+No match
+ \x{f0}
+No match
+
+/Ä€{3,4}/8SDZ
+------------------------------------------------------------------
+ Bra
+ \x{100}{3}
+ \x{100}?+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = \x{100}
+Subject length lower bound = 3
+No set of starting bytes
+ \x{100}\x{100}\x{100}\x{100\x{100}
+ 0: \x{100}\x{100}\x{100}
+
+/(\x{100}+|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}++
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xff
+
+/(\x{100}*a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}*+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xff
+
+/(\x{100}{0,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}{0,2}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xff
+
+/(\x{100}{1,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}
+ \x{100}{0,1}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xff
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/a\x{100}\x{101}*/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}*+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{100}
+
+/a\x{100}\x{101}+/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}++
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{101}
+
+/[^\x{c4}]/DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+ \x{100}
+ 0: \x{100}
+ Z\x{100}
+ 0: \x{100}
+ \x{100}Z
+ 0: \x{100}
+ *** Failers
+No match
+
+/[\xff]/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+ >\x{ff}<
+ 0: \x{ff}
+
+/[^\xff]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{ff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/\x{100}abc(xyz(?1))/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}abc
+ CBra 1
+ xyz
+ Recurse
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+First char = \x{100}
+Need char = 'z'
+
+/\777/8I
+Capturing subpattern count = 0
+Options: utf
+First char = \x{1ff}
+No need char
+ \x{1ff}
+ 0: \x{1ff}
+ \777
+ 0: \x{1ff}
+
+/\x{100}+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = \x{200}
+
+/\x{100}+X/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ X
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = 'X'
+
+/^[\QÄ€\E-\QÅ\E/BZ8
+Failed: missing terminating ] for character class at offset 13
+
+/X/8
+ \x{d800}
+Error -10 (bad UTF-16 string) offset=0 reason=1
+ \x{d800}\?
+No match
+ \x{da00}
+Error -10 (bad UTF-16 string) offset=0 reason=1
+ \x{da00}\?
+No match
+ \x{dc00}
+Error -10 (bad UTF-16 string) offset=0 reason=3
+ \x{dc00}\?
+No match
+ \x{de00}
+Error -10 (bad UTF-16 string) offset=0 reason=3
+ \x{de00}\?
+No match
+ \x{dfff}
+Error -10 (bad UTF-16 string) offset=0 reason=3
+ \x{dfff}\?
+No match
+ \x{110000}
+** Failed: character \x{110000} is greater than 0x10ffff and so cannot be converted to UTF-16
+ \x{d800}\x{1234}
+Error -10 (bad UTF-16 string) offset=1 reason=2
+
+/(*UTF16)\x{11234}/
+ abcd\x{11234}pqr
+ 0: \x{11234}
+
+/(*UTF)\x{11234}/I
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d804}
+Need char = \x{de34}
+ abcd\x{11234}pqr
+ 0: \x{11234}
+
+/(*UTF-32)\x{11234}/
+Failed: (*VERB) not recognized or malformed at offset 5
+
+/(*CRLF)(*UTF16)(*BSR_UNICODE)a\Rb/I
+Capturing subpattern count = 0
+Options: bsr_unicode utf
+Forced newline sequence: CRLF
+First char = 'a'
+Need char = 'b'
+
+/(*CRLF)(*UTF32)(*BSR_UNICODE)a\Rb/I
+Failed: (*VERB) not recognized or malformed at offset 12
+
+/\h/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xa0 \xff
+ ABC\x{09}
+ 0: \x{09}
+ ABC\x{20}
+ 0:
+ ABC\x{a0}
+ 0: \x{a0}
+ ABC\x{1680}
+ 0: \x{1680}
+ ABC\x{180e}
+ 0: \x{180e}
+ ABC\x{2000}
+ 0: \x{2000}
+ ABC\x{202f}
+ 0: \x{202f}
+ ABC\x{205f}
+ 0: \x{205f}
+ ABC\x{3000}
+ 0: \x{3000}
+
+/\v/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+ ABC\x{0a}
+ 0: \x{0a}
+ ABC\x{0b}
+ 0: \x{0b}
+ ABC\x{0c}
+ 0: \x{0c}
+ ABC\x{0d}
+ 0: \x{0d}
+ ABC\x{85}
+ 0: \x{85}
+ ABC\x{2028}
+ 0: \x{2028}
+
+/\h*A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 A \xa0 \xff
+ CDBABC
+ 0: A
+ \x{2000}ABC
+ 0: \x{2000}A
+
+/\R*A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d A \x85 \xff
+ CDBABC
+ 0: A
+ \x{2028}A
+ 0: \x{2028}A
+
+/\v+A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 2
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+
+/\s?xxx\s/8SI
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 4
+Starting byte set: \x09 \x0a \x0b \x0c \x0d \x20 x
+
+/\sxxx\s/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 5
+Starting byte set: \x09 \x0a \x0c \x0d \x20 \x85 \xa0
+ AB\x{85}xxx\x{a0}XYZ
+ 0: \x{85}xxx\x{a0}
+ AB\x{a0}xxx\x{85}XYZ
+ 0: \x{a0}xxx\x{85}
+
+/\S \S/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = ' '
+Subject length lower bound = 3
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x0b \x0e
+ \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19 \x1a \x1b \x1c \x1d
+ \x1e \x1f ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4 5 6 7 8 9 : ; < = > ? @
+ A B C D E F G H I J K L M N O P Q R S T U V W X Y Z [ \ ] ^ _ ` a b c d e
+ f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f \x80 \x81 \x82 \x83
+ \x84 \x86 \x87 \x88 \x89 \x8a \x8b \x8c \x8d \x8e \x8f \x90 \x91 \x92 \x93
+ \x94 \x95 \x96 \x97 \x98 \x99 \x9a \x9b \x9c \x9d \x9e \x9f \xa1 \xa2 \xa3
+ \xa4 \xa5 \xa6 \xa7 \xa8 \xa9 \xaa \xab \xac \xad \xae \xaf \xb0 \xb1 \xb2
+ \xb3 \xb4 \xb5 \xb6 \xb7 \xb8 \xb9 \xba \xbb \xbc \xbd \xbe \xbf \xc0 \xc1
+ \xc2 \xc3 \xc4 \xc5 \xc6 \xc7 \xc8 \xc9 \xca \xcb \xcc \xcd \xce \xcf \xd0
+ \xd1 \xd2 \xd3 \xd4 \xd5 \xd6 \xd7 \xd8 \xd9 \xda \xdb \xdc \xdd \xde \xdf
+ \xe0 \xe1 \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee
+ \xef \xf0 \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb \xfc \xfd
+ \xfe \xff
+ \x{a2} \x{84}
+ 0: \x{a2} \x{84}
+ A Z
+ 0: A Z
+
+/a+/8
+ a\x{123}aa\>1
+ 0: aa
+ a\x{123}aa\>2
+ 0: aa
+ a\x{123}aa\>3
+ 0: a
+ a\x{123}aa\>4
+No match
+ a\x{123}aa\>5
+Error -24 (bad offset value)
+ a\x{123}aa\>6
+Error -24 (bad offset value)
+
+/\x{1234}+/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}+?/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}++/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}{2}/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+Need char = \x{1234}
+Subject length lower bound = 2
+No set of starting bytes
+
+/[^\x{c4}]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/X+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ X++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'X'
+Need char = \x{200}
+
+/\R/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+
+/-- Check bad offset --/
+
+/a/8
+ \x{10000}\>1
+Error -11 (bad UTF-16 offset)
+ \x{10000}ab\>1
+Error -11 (bad UTF-16 offset)
+ \x{10000}ab\>2
+ 0: a
+ \x{10000}ab\>3
+No match
+ \x{10000}ab\>4
+No match
+ \x{10000}ab\>5
+Error -24 (bad offset value)
+
+/í¼€/8
+Failed: invalid UTF-16 string at offset 0
+
+/\w+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \w++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}
+
+/\w+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \w+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}\x{c4}
+
+/\W+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{A1}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/\W+\x{A1}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/X\s+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ X
+ \s++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}
+
+/X\s+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ X
+ \s+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}\x{a0}
+
+/\S+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ \S+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}\x{a0}
+
+/\S+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \S++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}
+
+/\x{a0}+\s!/8BZ
+------------------------------------------------------------------
+ Bra
+ \x{a0}++
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/\x{a0}+\s!/8BZT1
+------------------------------------------------------------------
+ Bra
+ \x{a0}+
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/(*UTF)abc/9
+Failed: setting UTF is disabled by the application at offset 0
+
+/abc/89
+Failed: setting UTF is disabled by the application at offset 0
+
+/-- End of testinput18 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput18-32 b/ext/pcre/pcrelib/testdata/testoutput18-32
new file mode 100644
index 0000000000..89be3a4b05
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput18-32
@@ -0,0 +1,1023 @@
+/-- This set of tests is for UTF-16 and UTF-32 support, and is relevant only to
+ the 16- and 32-bit libraries. --/
+
+< forbid W
+
+/ÃÃÃxxx/8?DZSS
+**Failed: invalid UTF-8 string cannot be converted to UTF-32
+
+/abc/8
+ Ã]
+**Failed: invalid UTF-8 string cannot be used as input in UTF mode
+
+/X(\C{3})/8
+ X\x{11234}Y
+No match
+ X\x{11234}YZ
+ 0: X\x{11234}YZ
+ 1: \x{11234}YZ
+
+/X(\C{4})/8
+ X\x{11234}YZ
+No match
+ X\x{11234}YZW
+ 0: X\x{11234}YZW
+ 1: \x{11234}YZW
+
+/X\C*/8
+ XYZabcdce
+ 0: XYZabcdce
+
+/X\C*?/8
+ XYZabcde
+ 0: X
+
+/X\C{3,5}/8
+ Xabcdefg
+ 0: Xabcde
+ X\x{11234}Y
+No match
+ X\x{11234}YZ
+ 0: X\x{11234}YZ
+ X\x{11234}\x{512}
+No match
+ X\x{11234}\x{512}YZ
+ 0: X\x{11234}\x{512}YZ
+ X\x{11234}\x{512}\x{11234}Z
+ 0: X\x{11234}\x{512}\x{11234}Z
+
+/X\C{3,5}?/8
+ Xabcdefg
+ 0: Xabc
+ X\x{11234}Y
+No match
+ X\x{11234}YZ
+ 0: X\x{11234}YZ
+ X\x{11234}\x{512}YZ
+ 0: X\x{11234}\x{512}Y
+ *** Failers
+No match
+ X\x{11234}
+No match
+
+/a\Cb/8
+ aXb
+ 0: aXb
+ a\nb
+ 0: a\x{0a}b
+
+/a\C\Cb/8
+ a\x{12257}b
+No match
+ a\x{12257}\x{11234}b
+ 0: a\x{12257}\x{11234}b
+ ** Failers
+No match
+ a\x{100}b
+No match
+
+/ab\Cde/8
+ abXde
+ 0: abXde
+
+/-- Check maximum character size --/
+
+/\x{ffff}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ffff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ffff}
+No need char
+
+/\x{10000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{10000}
+No need char
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/\x{1000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{1000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{1000}
+No need char
+
+/\x{10000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{10000}
+No need char
+
+/\x{100000}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100000}
+No need char
+
+/\x{10ffff}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{10ffff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{10ffff}
+No need char
+
+/[\x{ff}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/\x80/8DZ
+------------------------------------------------------------------
+ Bra
+ \x80
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{80}
+No need char
+
+/\xff/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+
+/\x{D55c}\x{ad6d}\x{C5B4}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{d55c}\x{ad6d}\x{c5b4}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{d55c}
+Need char = \x{c5b4}
+ \x{D55c}\x{ad6d}\x{C5B4}
+ 0: \x{d55c}\x{ad6d}\x{c5b4}
+
+/\x{65e5}\x{672c}\x{8a9e}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{65e5}\x{672c}\x{8a9e}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{65e5}
+Need char = \x{8a9e}
+ \x{65e5}\x{672c}\x{8a9e}
+ 0: \x{65e5}\x{672c}\x{8a9e}
+
+/\x{80}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x80
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{80}
+No need char
+
+/\x{084}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{84}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{84}
+No need char
+
+/\x{104}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{104}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{104}
+No need char
+
+/\x{861}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{861}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{861}
+No need char
+
+/\x{212ab}/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{212ab}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{212ab}
+No need char
+
+/-- This one is here not because it's different to Perl, but because the way
+the captured single-byte is displayed. (In Perl it becomes a character, and you
+can't tell the difference.) --/
+
+/X(\C)(.*)/8
+ X\x{1234}
+ 0: X\x{1234}
+ 1: \x{1234}
+ 2:
+ X\nabc
+ 0: X\x{0a}abc
+ 1: \x{0a}
+ 2: abc
+
+/-- This one is here because Perl gives out a grumbly error message (quite
+correctly, but that messes up comparisons). --/
+
+/a\Cb/8
+ *** Failers
+No match
+ a\x{100}b
+ 0: a\x{100}b
+
+/[^ab\xC0-\xF0]/8SDZ
+------------------------------------------------------------------
+ Bra
+ [\x00-`c-\xbf\xf1-\xff] (neg)
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x09 \x0a
+ \x0b \x0c \x0d \x0e \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19
+ \x1a \x1b \x1c \x1d \x1e \x1f \x20 ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4
+ 5 6 7 8 9 : ; < = > ? @ A B C D E F G H I J K L M N O P Q R S T U V W X Y
+ Z [ \ ] ^ _ ` c d e f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f
+ \x80 \x81 \x82 \x83 \x84 \x85 \x86 \x87 \x88 \x89 \x8a \x8b \x8c \x8d \x8e
+ \x8f \x90 \x91 \x92 \x93 \x94 \x95 \x96 \x97 \x98 \x99 \x9a \x9b \x9c \x9d
+ \x9e \x9f \xa0 \xa1 \xa2 \xa3 \xa4 \xa5 \xa6 \xa7 \xa8 \xa9 \xaa \xab \xac
+ \xad \xae \xaf \xb0 \xb1 \xb2 \xb3 \xb4 \xb5 \xb6 \xb7 \xb8 \xb9 \xba \xbb
+ \xbc \xbd \xbe \xbf \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb
+ \xfc \xfd \xfe \xff
+ \x{f1}
+ 0: \x{f1}
+ \x{bf}
+ 0: \x{bf}
+ \x{100}
+ 0: \x{100}
+ \x{1000}
+ 0: \x{1000}
+ *** Failers
+ 0: *
+ \x{c0}
+No match
+ \x{f0}
+No match
+
+/Ä€{3,4}/8SDZ
+------------------------------------------------------------------
+ Bra
+ \x{100}{3}
+ \x{100}?+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = \x{100}
+Subject length lower bound = 3
+No set of starting bytes
+ \x{100}\x{100}\x{100}\x{100\x{100}
+ 0: \x{100}\x{100}\x{100}
+
+/(\x{100}+|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}++
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xff
+
+/(\x{100}*a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}*+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xff
+
+/(\x{100}{0,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}{0,2}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: a x \xff
+
+/(\x{100}{1,2}a|x)/8SDZ
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ \x{100}
+ \x{100}{0,1}+
+ a
+ Alt
+ x
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: x \xff
+
+/\x{100}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+
+/a\x{100}\x{101}*/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}*+
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{100}
+
+/a\x{100}\x{101}+/8DZ
+------------------------------------------------------------------
+ Bra
+ a\x{100}
+ \x{101}++
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'a'
+Need char = \x{101}
+
+/[^\x{c4}]/DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+
+/[\x{100}]/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+No need char
+ \x{100}
+ 0: \x{100}
+ Z\x{100}
+ 0: \x{100}
+ \x{100}Z
+ 0: \x{100}
+ *** Failers
+No match
+
+/[\xff]/DZ8
+------------------------------------------------------------------
+ Bra
+ \x{ff}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{ff}
+No need char
+ >\x{ff}<
+ 0: \x{ff}
+
+/[^\xff]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{ff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/\x{100}abc(xyz(?1))/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}abc
+ CBra 1
+ xyz
+ Recurse
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 1
+Options: utf
+First char = \x{100}
+Need char = 'z'
+
+/\777/8I
+Capturing subpattern count = 0
+Options: utf
+First char = \x{1ff}
+No need char
+ \x{1ff}
+ 0: \x{1ff}
+ \777
+ 0: \x{1ff}
+
+/\x{100}+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = \x{200}
+
+/\x{100}+X/8DZ
+------------------------------------------------------------------
+ Bra
+ \x{100}++
+ X
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = \x{100}
+Need char = 'X'
+
+/^[\QÄ€\E-\QÅ\E/BZ8
+Failed: missing terminating ] for character class at offset 13
+
+/X/8
+ \x{d800}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+ \x{d800}\?
+No match
+ \x{da00}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+ \x{da00}\?
+No match
+ \x{dc00}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+ \x{dc00}\?
+No match
+ \x{de00}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+ \x{de00}\?
+No match
+ \x{dfff}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+ \x{dfff}\?
+No match
+ \x{110000}
+Error -10 (bad UTF-32 string) offset=0 reason=3
+ \x{d800}\x{1234}
+Error -10 (bad UTF-32 string) offset=0 reason=1
+
+/(*UTF16)\x{11234}/
+Failed: (*VERB) not recognized or malformed at offset 5
+
+/(*UTF)\x{11234}/I
+Capturing subpattern count = 0
+Options: utf
+First char = \x{11234}
+No need char
+ abcd\x{11234}pqr
+ 0: \x{11234}
+
+/(*UTF-32)\x{11234}/
+Failed: (*VERB) not recognized or malformed at offset 5
+
+/(*CRLF)(*UTF16)(*BSR_UNICODE)a\Rb/I
+Failed: (*VERB) not recognized or malformed at offset 12
+
+/(*CRLF)(*UTF32)(*BSR_UNICODE)a\Rb/I
+Capturing subpattern count = 0
+Options: bsr_unicode utf
+Forced newline sequence: CRLF
+First char = 'a'
+Need char = 'b'
+
+/\h/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 \xa0 \xff
+ ABC\x{09}
+ 0: \x{09}
+ ABC\x{20}
+ 0:
+ ABC\x{a0}
+ 0: \x{a0}
+ ABC\x{1680}
+ 0: \x{1680}
+ ABC\x{180e}
+ 0: \x{180e}
+ ABC\x{2000}
+ 0: \x{2000}
+ ABC\x{202f}
+ 0: \x{202f}
+ ABC\x{205f}
+ 0: \x{205f}
+ ABC\x{3000}
+ 0: \x{3000}
+
+/\v/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+ ABC\x{0a}
+ 0: \x{0a}
+ ABC\x{0b}
+ 0: \x{0b}
+ ABC\x{0c}
+ 0: \x{0c}
+ ABC\x{0d}
+ 0: \x{0d}
+ ABC\x{85}
+ 0: \x{85}
+ ABC\x{2028}
+ 0: \x{2028}
+
+/\h*A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 1
+Starting byte set: \x09 \x20 A \xa0 \xff
+ CDBABC
+ 0: A
+ \x{2000}ABC
+ 0: \x{2000}A
+
+/\R*A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d A \x85 \xff
+ CDBABC
+ 0: A
+ \x{2028}A
+ 0: \x{2028}A
+
+/\v+A/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'A'
+Subject length lower bound = 2
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+
+/\s?xxx\s/8SI
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 4
+Starting byte set: \x09 \x0a \x0b \x0c \x0d \x20 x
+
+/\sxxx\s/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = 'x'
+Subject length lower bound = 5
+Starting byte set: \x09 \x0a \x0c \x0d \x20 \x85 \xa0
+ AB\x{85}xxx\x{a0}XYZ
+ 0: \x{85}xxx\x{a0}
+ AB\x{a0}xxx\x{85}XYZ
+ 0: \x{a0}xxx\x{85}
+
+/\S \S/I8ST1
+Capturing subpattern count = 0
+Options: utf
+No first char
+Need char = ' '
+Subject length lower bound = 3
+Starting byte set: \x00 \x01 \x02 \x03 \x04 \x05 \x06 \x07 \x08 \x0b \x0e
+ \x0f \x10 \x11 \x12 \x13 \x14 \x15 \x16 \x17 \x18 \x19 \x1a \x1b \x1c \x1d
+ \x1e \x1f ! " # $ % & ' ( ) * + , - . / 0 1 2 3 4 5 6 7 8 9 : ; < = > ? @
+ A B C D E F G H I J K L M N O P Q R S T U V W X Y Z [ \ ] ^ _ ` a b c d e
+ f g h i j k l m n o p q r s t u v w x y z { | } ~ \x7f \x80 \x81 \x82 \x83
+ \x84 \x86 \x87 \x88 \x89 \x8a \x8b \x8c \x8d \x8e \x8f \x90 \x91 \x92 \x93
+ \x94 \x95 \x96 \x97 \x98 \x99 \x9a \x9b \x9c \x9d \x9e \x9f \xa1 \xa2 \xa3
+ \xa4 \xa5 \xa6 \xa7 \xa8 \xa9 \xaa \xab \xac \xad \xae \xaf \xb0 \xb1 \xb2
+ \xb3 \xb4 \xb5 \xb6 \xb7 \xb8 \xb9 \xba \xbb \xbc \xbd \xbe \xbf \xc0 \xc1
+ \xc2 \xc3 \xc4 \xc5 \xc6 \xc7 \xc8 \xc9 \xca \xcb \xcc \xcd \xce \xcf \xd0
+ \xd1 \xd2 \xd3 \xd4 \xd5 \xd6 \xd7 \xd8 \xd9 \xda \xdb \xdc \xdd \xde \xdf
+ \xe0 \xe1 \xe2 \xe3 \xe4 \xe5 \xe6 \xe7 \xe8 \xe9 \xea \xeb \xec \xed \xee
+ \xef \xf0 \xf1 \xf2 \xf3 \xf4 \xf5 \xf6 \xf7 \xf8 \xf9 \xfa \xfb \xfc \xfd
+ \xfe \xff
+ \x{a2} \x{84}
+ 0: \x{a2} \x{84}
+ A Z
+ 0: A Z
+
+/a+/8
+ a\x{123}aa\>1
+ 0: aa
+ a\x{123}aa\>2
+ 0: aa
+ a\x{123}aa\>3
+ 0: a
+ a\x{123}aa\>4
+No match
+ a\x{123}aa\>5
+Error -24 (bad offset value)
+ a\x{123}aa\>6
+Error -24 (bad offset value)
+
+/\x{1234}+/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}+?/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}++/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/\x{1234}{2}/iS8I
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{1234}
+Need char = \x{1234}
+Subject length lower bound = 2
+No set of starting bytes
+
+/[^\x{c4}]/8DZ
+------------------------------------------------------------------
+ Bra
+ [^\x{c4}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+
+/X+\x{200}/8DZ
+------------------------------------------------------------------
+ Bra
+ X++
+ \x{200}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'X'
+Need char = \x{200}
+
+/\R/SI8
+Capturing subpattern count = 0
+Options: utf
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: \x0a \x0b \x0c \x0d \x85 \xff
+
+/-- Check bad offset --/
+
+/a/8
+ \x{10000}\>1
+No match
+ \x{10000}ab\>1
+ 0: a
+ \x{10000}ab\>2
+No match
+ \x{10000}ab\>3
+No match
+ \x{10000}ab\>4
+Error -24 (bad offset value)
+ \x{10000}ab\>5
+Error -24 (bad offset value)
+
+/í¼€/8
+**Failed: character value is ill-formed UTF-32
+
+/\w+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \w++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}
+
+/\w+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \w+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ a\x{C4}\x{C4}
+ 0: a\x{c4}\x{c4}
+
+/\W+\x{C4}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{C4}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W++
+ \x{c4}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{C4}
+ 0: !\x{c4}
+
+/\W+\x{A1}/8BZ
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/\W+\x{A1}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \W+
+ \x{a1}
+ Ket
+ End
+------------------------------------------------------------------
+ !\x{A1}
+ 0: !\x{a1}
+
+/X\s+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ X
+ \s++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}
+
+/X\s+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ X
+ \s+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x20\x{A0}\x{A0}
+ 0: X \x{a0}\x{a0}
+
+/\S+\x{A0}/8BZ
+------------------------------------------------------------------
+ Bra
+ \S+
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}\x{a0}
+
+/\S+\x{A0}/8BZT1
+------------------------------------------------------------------
+ Bra
+ \S++
+ \x{a0}
+ Ket
+ End
+------------------------------------------------------------------
+ X\x{A0}\x{A0}
+ 0: X\x{a0}
+
+/\x{a0}+\s!/8BZ
+------------------------------------------------------------------
+ Bra
+ \x{a0}++
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/\x{a0}+\s!/8BZT1
+------------------------------------------------------------------
+ Bra
+ \x{a0}+
+ \s
+ !
+ Ket
+ End
+------------------------------------------------------------------
+ \x{a0}\x20!
+ 0: \x{a0} !
+
+/(*UTF)abc/9
+Failed: setting UTF is disabled by the application at offset 0
+
+/abc/89
+Failed: setting UTF is disabled by the application at offset 0
+
+/-- End of testinput18 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput19 b/ext/pcre/pcrelib/testdata/testoutput19
new file mode 100644
index 0000000000..ccc198cc15
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput19
@@ -0,0 +1,88 @@
+/-- This set of tests is for Unicode property support, relevant only to the
+ 16- and 32-bit library. --/
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8iDZ
+------------------------------------------------------------------
+ Bra
+ /i A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: caseless utf
+First char = 'A' (caseless)
+Need char = \x{1fb0} (caseless)
+
+/A\x{391}\x{10427}\x{ff3a}\x{1fb0}/8DZ
+------------------------------------------------------------------
+ Bra
+ A\x{391}\x{10427}\x{ff3a}\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = \x{1fb0}
+
+/AB\x{1fb0}/8DZ
+------------------------------------------------------------------
+ Bra
+ AB\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: utf
+First char = 'A'
+Need char = \x{1fb0}
+
+/AB\x{1fb0}/8DZi
+------------------------------------------------------------------
+ Bra
+ /i AB\x{1fb0}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: caseless utf
+First char = 'A' (caseless)
+Need char = \x{1fb0} (caseless)
+
+/\x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}/8iSI
+Capturing subpattern count = 0
+Options: caseless utf
+First char = \x{401} (caseless)
+Need char = \x{42f} (caseless)
+Subject length lower bound = 17
+No set of starting bytes
+ \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ 0: \x{401}\x{420}\x{421}\x{422}\x{423}\x{424}\x{425}\x{426}\x{427}\x{428}\x{429}\x{42a}\x{42b}\x{42c}\x{42d}\x{42e}\x{42f}
+ \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+ 0: \x{451}\x{440}\x{441}\x{442}\x{443}\x{444}\x{445}\x{446}\x{447}\x{448}\x{449}\x{44a}\x{44b}\x{44c}\x{44d}\x{44e}\x{44f}
+
+/[â±¥]/8iBZ
+------------------------------------------------------------------
+ Bra
+ /i \x{2c65}
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^â±¥]/8iBZ
+------------------------------------------------------------------
+ Bra
+ /i [^\x{2c65}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[[:blank:]]/WBZ
+------------------------------------------------------------------
+ Bra
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]
+ Ket
+ End
+------------------------------------------------------------------
+
+/-- End of testinput19 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput2 b/ext/pcre/pcrelib/testdata/testoutput2
index e9cddf80d1..844497abcd 100644
--- a/ext/pcre/pcrelib/testdata/testoutput2
+++ b/ext/pcre/pcrelib/testdata/testoutput2
@@ -7,9 +7,12 @@
NOTE: This is a non-UTF set of tests. When UTF support is needed, use
test 5, and if Unicode Property Support is needed, use test 7. --/
+
+< forbid 8W
/(a)b|/I
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
@@ -228,7 +231,7 @@ No options
No first char
No need char
Subject length lower bound = 1
-Starting byte set: \x09 \x0a \x0c \x0d \x20 a b
+Starting byte set: \x09 \x0a \x0b \x0c \x0d \x20 a b
/(ab\2)/
Failed: reference to non-existent subpattern at offset 6
@@ -448,10 +451,10 @@ Need char = '='
/(?<!bar|cattle)foo/I
Capturing subpattern count = 0
+Max lookbehind = 6
No options
First char = 'f'
Need char = 'o'
-Max lookbehind = 6
foo
0: foo
catfoo
@@ -498,6 +501,7 @@ No need char
/(?s).*/I
Capturing subpattern count = 0
+May match empty string
Options: anchored dotall
No first char
No need char
@@ -545,10 +549,10 @@ Failed: conditional group contains more than two branches at offset 13
Failed: conditional group contains more than two branches at offset 12
/(?(1a)/
-Failed: missing ) at offset 6
+Failed: malformed number or name after (?( at offset 4
/(?(1a))/
-Failed: reference to non-existent subpattern at offset 6
+Failed: malformed number or name after (?( at offset 4
/(?(?i))/
Failed: assertion expected after (?( at offset 3
@@ -631,6 +635,7 @@ No match
/\Aabc/Im
Capturing subpattern count = 0
+Max lookbehind = 1
Options: anchored multiline
No first char
No need char
@@ -656,19 +661,19 @@ No need char
/(?<=foo)[ab]/IS
Capturing subpattern count = 0
+Max lookbehind = 3
No options
No first char
No need char
-Max lookbehind = 3
Subject length lower bound = 1
Starting byte set: a b
/(?<!foo)(alpha|omega)/IS
Capturing subpattern count = 1
+Max lookbehind = 3
No options
No first char
Need char = 'a'
-Max lookbehind = 3
Subject length lower bound = 5
Starting byte set: a o
@@ -682,11 +687,11 @@ Starting byte set: a b
/(?<=foo\n)^bar/Im
Capturing subpattern count = 0
+Max lookbehind = 4
Contains explicit CR or LF match
Options: multiline
No first char
Need char = 'r'
-Max lookbehind = 4
foo\nbarbar
0: bar
***Failers
@@ -700,11 +705,11 @@ No match
/^(?<=foo\n)bar/Im
Capturing subpattern count = 0
+Max lookbehind = 4
Contains explicit CR or LF match
Options: multiline
First char at start or follows newline
Need char = 'r'
-Max lookbehind = 4
foo\nbarbar
0: bar
***Failers
@@ -743,10 +748,10 @@ Failed: lookbehind assertion is not fixed length at offset 13
/(?<=bullock|donkey)-cart/I
Capturing subpattern count = 0
+Max lookbehind = 7
No options
First char = '-'
Need char = 't'
-Max lookbehind = 7
the bullock-cart
0: -cart
a donkey-cart race
@@ -760,17 +765,19 @@ No match
/(?<=ab(?i)x|y|z)/I
Capturing subpattern count = 0
+Max lookbehind = 3
+May match empty string
No options
No first char
No need char
-Max lookbehind = 3
/(?>.*)(?<=(abcd)|(xyz))/I
Capturing subpattern count = 2
+Max lookbehind = 4
+May match empty string
No options
No first char
No need char
-Max lookbehind = 4
alphabetabcd
0: alphabetabcd
1: abcd
@@ -781,10 +788,10 @@ Max lookbehind = 4
/(?<=ab(?i)x(?-i)y|(?i)z|b)ZZ/I
Capturing subpattern count = 0
+Max lookbehind = 4
No options
First char = 'Z'
Need char = 'Z'
-Max lookbehind = 4
abxyZZ
0: ZZ
abXyZZ
@@ -810,10 +817,10 @@ No match
/(?<!(foo)a)bar/I
Capturing subpattern count = 1
+Max lookbehind = 4
No options
First char = 'b'
Need char = 'r'
-Max lookbehind = 4
bar
0: bar
foobbar
@@ -823,22 +830,6 @@ No match
fooabar
No match
-/This one is here because Perl 5.005_02 doesn't fail it/I
-Capturing subpattern count = 0
-No options
-First char = 'T'
-Need char = 't'
-
-/^(a)?(?(1)a|b)+$/I
-Capturing subpattern count = 1
-Options: anchored
-No first char
-No need char
- *** Failers
-No match
- a
-No match
-
/This one is here because Perl behaves differently; see also the following/I
Capturing subpattern count = 0
No options
@@ -1212,10 +1203,10 @@ No need char
/\Biss\B/I+
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 'i'
Need char = 's'
-Max lookbehind = 1
Mississippi
0: iss
0+ issippi
@@ -1233,20 +1224,20 @@ Need char = 's'
/\Biss\B/IG+
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 'i'
Need char = 's'
-Max lookbehind = 1
Mississippi
0: iss
0+ issippi
/\Biss\B/Ig+
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 'i'
Need char = 's'
-Max lookbehind = 1
Mississippi
0: iss
0+ issippi
@@ -1259,10 +1250,10 @@ No match
/(?<=[Ms])iss/Ig+
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 'i'
Need char = 's'
-Max lookbehind = 1
Mississippi
0: iss
0+ issippi
@@ -1271,10 +1262,10 @@ Max lookbehind = 1
/(?<=[Ms])iss/IG+
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 'i'
Need char = 's'
-Max lookbehind = 1
Mississippi
0: iss
0+ issippi
@@ -1392,6 +1383,7 @@ Need char = 'c'
/a*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -1410,6 +1402,7 @@ Need char = 'a'
/a{0,3}/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -1452,10 +1445,10 @@ Need char = 'r'
/...(?<=abc)/I
Capturing subpattern count = 0
+Max lookbehind = 3
No options
No first char
No need char
-Max lookbehind = 3
/abc(?!pqr)/I
Capturing subpattern count = 0
@@ -1609,6 +1602,7 @@ Need char = 'e'
/a?b?/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -1627,6 +1621,7 @@ No match
/|-/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -2640,6 +2635,7 @@ Need char = '-'
End
------------------------------------------------------------------
Capturing subpattern count = 0
+May match empty string
Options: extended
No first char
No need char
@@ -2659,7 +2655,7 @@ No need char
/[\s]/DZ
------------------------------------------------------------------
Bra
- [\x09\x0a\x0c\x0d ]
+ [\x09-\x0d ]
Ket
End
------------------------------------------------------------------
@@ -2671,7 +2667,7 @@ No need char
/[\S]/DZ
------------------------------------------------------------------
Bra
- [\x00-\x08\x0b\x0e-\x1f!-\xff] (neg)
+ [\x00-\x08\x0e-\x1f!-\xff] (neg)
Ket
End
------------------------------------------------------------------
@@ -2782,6 +2778,7 @@ Need char = '0'
End
------------------------------------------------------------------
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -2881,6 +2878,7 @@ No match
End
------------------------------------------------------------------
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -2897,20 +2895,41 @@ No options
First char = 'x'
No need char
-/x{1,3}+/DZ
+/x{1,3}+/BZO
------------------------------------------------------------------
Bra
- Once
x
- x{0,2}
+ x{0,2}+
Ket
+ End
+------------------------------------------------------------------
+
+/x{1,3}+/BZOi
+------------------------------------------------------------------
+ Bra
+ /i x
+ /i x{0,2}+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^x]{1,3}+/BZO
+------------------------------------------------------------------
+ Bra
+ [^x]
+ [^x]{0,2}+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^x]{1,3}+/BZOi
+------------------------------------------------------------------
+ Bra
+ /i [^x]
+ /i [^x]{0,2}+
Ket
End
------------------------------------------------------------------
-Capturing subpattern count = 0
-No options
-First char = 'x'
-No need char
/(x)*+/DZ
------------------------------------------------------------------
@@ -2923,12 +2942,14 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
/^(\w++|\s++)*$/I
Capturing subpattern count = 1
+May match empty string
Options: anchored
No first char
No need char
@@ -3090,7 +3111,7 @@ Need char = 'b'
[bc]+
Ket
CBra 5
- \w*
+ \w*+
Ket
Ket
Ket
@@ -3169,7 +3190,7 @@ Failed: missing terminating ] for character class at offset 10
/[\s]/IDZ
------------------------------------------------------------------
Bra
- [\x09\x0a\x0c\x0d ]
+ [\x09-\x0d ]
Ket
End
------------------------------------------------------------------
@@ -3233,10 +3254,10 @@ No match
End
------------------------------------------------------------------
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = '8'
Need char = 'X'
-Max lookbehind = 1
|\$\<\.X\+ix\[d1b\!H\#\?vV0vrK\:ZH1\=2M\>iV\;\?aPhFB\<\*vW\@QW\@sO9\}cfZA\-i\'w\%hKd6gt1UJP\,15_\#QY\$M\^Mss_U\/\]\&LK9\[5vQub\^w\[KDD\<EjmhUZ\?\.akp2dF\>qmj\;2\}YWFdYx\.Ap\]hjCPTP\(n28k\+3\;o\&WXqs\/gOXdr\$\:r\'do0\;b4c\(f_Gr\=\"\\4\)\[01T7ajQJvL\$W\~mL_sS\/4h\:x\*\[ZN\=KLs\&L5zX\/\/\>it\,o\:aU\(\;Z\>pW\&T7oP\'2K\^E\:x9\'c\[\%z\-\,64JQ5AeH_G\#KijUKghQw\^\\vea3a\?kka_G\$8\#\`\*kynsxzBLru\'\]k_\[7FrVx\}\^\=\$blx\>s\-N\%j\;D\*aZDnsw\:YKZ\%Q\.Kne9\#hP\?\+b3\(SOvL\,\^\;\&u5\@\?5C5Bhb\=m\-vEh_L15Jl\]U\)0RP6\{q\%L\^_z5E\'Dw6X\b|IDZ
------------------------------------------------------------------
@@ -3247,10 +3268,10 @@ Max lookbehind = 1
End
------------------------------------------------------------------
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = '$'
Need char = 'X'
-Max lookbehind = 1
/(.*)\d+\1/I
Capturing subpattern count = 1
@@ -3304,6 +3325,7 @@ Need char = 'b'
/(?=a).*/I
Capturing subpattern count = 0
+May match empty string
No options
First char = 'a'
No need char
@@ -3322,6 +3344,7 @@ Need char = 'z' (caseless)
/(?=a)(?=b)/I
Capturing subpattern count = 0
+May match empty string
No options
First char = 'a'
No need char
@@ -3388,6 +3411,7 @@ Need char = 'a'
/(a)*/I
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
@@ -3616,6 +3640,7 @@ No match
/(?C0)(abc(?C1))*/I
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
@@ -3649,6 +3674,7 @@ No need char
/(\d{3}(?C))*/I
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
@@ -3763,10 +3789,10 @@ Callout 2: last capture = -1
/(?<=(abc)(?C))xyz/I
Capturing subpattern count = 1
+Max lookbehind = 3
No options
First char = 'x'
Need char = 'z'
-Max lookbehind = 3
abcxyz\C+
Callout 0: last capture = 1
0: <unset>
@@ -3785,20 +3811,6 @@ Need char = 'b'
--->abbbbbccc
1 ^ ^
Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
- 1 ^ ^
-Callout data = 1
No match
/a(b+?)(c*?)(?C1)/I
@@ -3895,6 +3907,7 @@ Failed: recursive call could loop indefinitely at offset 16
/^([^()]|\((?1)*\))*$/I
Capturing subpattern count = 1
+May match empty string
Options: anchored
No first char
No need char
@@ -4174,6 +4187,7 @@ Named capturing subpatterns:
one 1
three 3
two 2
+May match empty string
Options: anchored caseless
No first char
No need char
@@ -4273,6 +4287,7 @@ Need char = 'z'
/(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)a/Is
Capturing subpattern count = 31
+May match empty string
Options: anchored dotall
No first char
No need char
@@ -4280,6 +4295,7 @@ No need char
/(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)a\31/Is
Capturing subpattern count = 31
Max back reference = 31
+May match empty string
Options: dotall
No first char
No need char
@@ -4287,6 +4303,7 @@ No need char
/(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)|(.*)a\32/Is
Capturing subpattern count = 32
Max back reference = 32
+May match empty string
Options: dotall
No first char
No need char
@@ -4363,7 +4380,7 @@ Minimum match() recursion limit = 6
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaz\M
Minimum match() limit = 32768
-Minimum match() recursion limit = 42
+Minimum match() recursion limit = 29
No match
/(aaa(?C1)bbb|ab)/I
@@ -4438,6 +4455,7 @@ Capturing subpattern count = 2
Named capturing subpatterns:
Tes 1
Test 2
+May match empty string
No options
No first char
No need char
@@ -4456,6 +4474,7 @@ Capturing subpattern count = 2
Named capturing subpatterns:
Tes 2
Test 1
+May match empty string
No options
No first char
No need char
@@ -4533,6 +4552,7 @@ Need char = ']'
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
No options
No first char
No need char
@@ -4553,6 +4573,7 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
No options
No first char
No need char
@@ -4584,6 +4605,7 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
No options
No first char
No need char
@@ -4591,9 +4613,7 @@ No need char
/[ab]{1}+/DZ
------------------------------------------------------------------
Bra
- Once
- [ab]{1,1}
- Ket
+ [ab]{1,1}+
Ket
End
------------------------------------------------------------------
@@ -5305,7 +5325,7 @@ No match
Callout 255 0 21
CBra 1
Callout 255 1 9
- [ab]{1,4}
+ [ab]{1,4}+
Callout 255 10 1
c
Callout 255 11 0
@@ -5318,7 +5338,7 @@ No match
Ket
CBra 1
Callout 255 1 9
- [ab]{1,4}
+ [ab]{1,4}+
Callout 255 10 1
c
Callout 255 11 0
@@ -5331,7 +5351,7 @@ No match
Ket
CBra 1
Callout 255 1 9
- [ab]{1,4}
+ [ab]{1,4}+
Callout 255 10 1
c
Callout 255 11 0
@@ -5344,7 +5364,7 @@ No match
Ket
CBra 1
Callout 255 1 9
- [ab]{1,4}
+ [ab]{1,4}+
Callout 255 10 1
c
Callout 255 11 0
@@ -5358,7 +5378,7 @@ No match
Braminzero
CBra 1
Callout 255 1 9
- [ab]{1,4}
+ [ab]{1,4}+
Callout 255 10 1
c
Callout 255 11 0
@@ -5411,24 +5431,27 @@ Need char = '3'
/\b.*/I
Capturing subpattern count = 0
+Max lookbehind = 1
+May match empty string
No options
No first char
No need char
-Max lookbehind = 1
ab cd\>1
0: cd
/\b.*/Is
Capturing subpattern count = 0
+Max lookbehind = 1
+May match empty string
Options: dotall
No first char
No need char
-Max lookbehind = 1
ab cd\>1
0: cd
/(?!.bcd).*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6017,6 +6040,7 @@ Matched, but too many substrings
/[^()]*(?:\((?R)\)[^()]*)*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6029,6 +6053,7 @@ No need char
/[^()]*(?:\((?>(?R))\)[^()]*)*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6039,6 +6064,7 @@ No need char
/[^()]*(?:\((?R)\))*[^()]*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6049,6 +6075,7 @@ No need char
/(?:\((?R)\))*[^()]*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6061,6 +6088,7 @@ No need char
/(?:\((?R)\))|[^()]*/I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -6110,6 +6138,17 @@ no parentheses with name "Z"
2: a1
copy substring Z failed -7
C a1 (2) A
+
+/(?|(?<a>)(?<b>)(?<a>)|(?<a>)(?<b>)(?<a>))/IJ
+Capturing subpattern count = 3
+Named capturing subpatterns:
+ a 1
+ a 3
+ b 2
+May match empty string
+Options: dupnames
+No first char
+No need char
/^(?P<A>a)(?P<A>b)/IJ
Capturing subpattern count = 2
@@ -6320,7 +6359,7 @@ Need char = 'X'
1: X
/(?:(?(2y)a|b)(X))+/I
-Failed: reference to non-existent subpattern at offset 9
+Failed: malformed number or name after (?( at offset 7
/(?:(?(ZA)a|b)(?P<ZZ>X))+/I
Failed: reference to non-existent subpattern at offset 9
@@ -6392,9 +6431,9 @@ No options
No first char
Need char = ','
Subject length lower bound = 1
-Starting byte set: \x09 \x0a \x0c \x0d \x20 ,
+Starting byte set: \x09 \x0a \x0b \x0c \x0d \x20 ,
\x0b,\x0b
- 0: ,
+ 0: \x0b,\x0b
\x0c,\x0d
0: \x0c,\x0d
@@ -6503,7 +6542,7 @@ No match
No match
/^abc/Im<bad>
-Unknown newline type at: <bad>
+Unknown modifier at: <bad>
/abc/I
@@ -6512,12 +6551,13 @@ No options
First char = 'a'
Need char = 'c'
xyz\rabc\<bad>
-Unknown newline type at: <bad>
+Unknown escape sequence at: <bad>
abc
0: abc
/.*/I<lf>
Capturing subpattern count = 0
+May match empty string
Options:
Forced newline sequence: LF
First char at start or follows newline
@@ -6559,6 +6599,7 @@ Need char = 'f'
+((?:\s|//.*\\n|/[*](?:\\n|.)*?[*]/)*)+I
Capturing subpattern count = 1
+May match empty string
No options
No first char
No need char
@@ -7482,7 +7523,7 @@ Matched, but too many substrings
/a*[^a]/BZ
------------------------------------------------------------------
Bra
- a*
+ a*+
[^a]
Ket
End
@@ -7624,7 +7665,7 @@ No match
------------------------------------------------------------------
Bra
^
- [a-z]+
+ [a-z]++
Ket
End
------------------------------------------------------------------
@@ -7665,7 +7706,7 @@ No match
^
CBra 1
Cond
- 2 Cond nref
+ 2 Cond ref
y
Ket
[()]
@@ -7725,6 +7766,7 @@ Named capturing subpatterns:
one 1
three 3
two 2
+May match empty string
Options: anchored caseless
No first char
No need char
@@ -7824,15 +7866,9 @@ Failed: reference to non-existent subpattern at offset 7
1: abcabc1Xabc2XabcX
2: abcabc1Xabc2XabcX
-/(?<A> (?'B' abc (?(R) (?(R&1)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
+/(?<A> (?'B' abc (?(R) (?(R&C)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
Failed: reference to non-existent subpattern at offset 29
-/(?<1> (?'B' abc (?(R) (?(R&1)1) (?(R&B)2) X | (?1) (?2) (?R) ))) /x
- abcabc1Xabc2XabcXabcabc
- 0: abcabc1Xabc2XabcX
- 1: abcabc1Xabc2XabcX
- 2: abcabc1Xabc2XabcX
-
/^(?(DEFINE) abc | xyz ) /x
Failed: DEFINE group contains more than one branch at offset 22
@@ -8056,7 +8092,7 @@ Failed: a numbered reference must not be zero at offset 8
/^(a)\g{3/
Failed: \g is not followed by a braced, angle-bracketed, or quoted name/number or by a plain number at offset 8
-/^(a)\g{4a}/
+/^(a)\g{aa}/
Failed: reference to non-existent subpattern at offset 9
/^a.b/<lf>
@@ -8561,7 +8597,7 @@ No match
\d
\v++
\w
- \v+
+ \v++
\S
\v++
\V
@@ -8659,27 +8695,18 @@ No match
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
- +4 ^ ^ c+
- +2 ^ ^ b?
- +4 ^ ^ c+
- +2 ^^ b?
- +4 ^^ c+
+0 ^ a+
+2 ^ ^ b?
+4 ^ ^ c+
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
- +4 ^ ^ c+
- +2 ^^ b?
- +4 ^^ c+
+0 ^ a+
+2 ^^ b?
+4 ^ ^ c+
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
+6 ^ ^ (*FAIL)
- +4 ^^ c+
No match
/a+b?(*PRUNE)c+(*FAIL)/C
@@ -8803,7 +8830,7 @@ No match
1: \x0a
/a(*CR)b/
-Failed: (*VERB) not recognized at offset 5
+Failed: (*VERB) not recognized or malformed at offset 5
/(*CR)a.b/
a\nb
@@ -9248,8 +9275,28 @@ No match
ab
No match
-/a(?!)+b/
-Failed: nothing to repeat at offset 5
+/a(?!)b/BZ
+------------------------------------------------------------------
+ Bra
+ a
+ *FAIL
+ b
+ Ket
+ End
+------------------------------------------------------------------
+
+/(?!)?a/BZ
+------------------------------------------------------------------
+ Bra
+ Brazero
+ Assert not
+ Ket
+ a
+ Ket
+ End
+------------------------------------------------------------------
+ ab
+ 0: a
/a(*FAIL)+b/
Failed: nothing to repeat at offset 8
@@ -9264,6 +9311,7 @@ Starting byte set: x y z
/(?(?=.*b)b|^)/CI
Capturing subpattern count = 0
+May match empty string
Options:
No first char
No need char
@@ -9276,6 +9324,7 @@ No need char
+7 ^ ^ b
+7 ^^ b
+7 ^ b
++11 ^ ^
+12 ^ )
+13 ^
0:
@@ -9367,7 +9416,7 @@ No match
No match
/(*NO_START_OPT)xyz/C
- abcxyz
+ abcxyz
--->abcxyz
+15 ^ x
+15 ^ x
@@ -9377,6 +9426,15 @@ No match
+17 ^ ^ z
+18 ^ ^
0: xyz
+
+/(*NO_AUTO_POSSESS)a+b/BZ
+------------------------------------------------------------------
+ Bra
+ a+
+ b
+ Ket
+ End
+------------------------------------------------------------------
/xyz/CY
abcxyz
@@ -9406,12 +9464,14 @@ No match
+3 ^ ^ (?(?=[a])[^"])
+5 ^ ^ (?=[a])
+8 ^ ^ [a]
++17 ^ ^ |
+21 ^ ^ "
+18 ^ ^ b
+19 ^ ^ )
+3 ^ ^ (?(?=[a])[^"])
+5 ^ ^ (?=[a])
+8 ^ ^ [a]
++17 ^ ^ |
+21 ^ ^ "
+22 ^ ^ $
+23 ^ ^
@@ -9719,17 +9779,17 @@ Partial match: abc12
xyzabc123pqr
0: 123
xyzabc12\P
-Partial match: abc12
+Partial match at offset 6: abc12
xyzabc12\P\P
-Partial match: abc12
+Partial match at offset 6: abc12
/\babc\b/
+++abc+++
0: abc
+++ab\P
-Partial match: +ab
+Partial match at offset 3: +ab
+++ab\P\P
-Partial match: +ab
+Partial match at offset 3: +ab
/(?&word)(?&element)(?(DEFINE)(?<element><[^m][^>]>[^<])(?<word>\w*+))/BZ
------------------------------------------------------------------
@@ -10172,7 +10232,6 @@ No set of starting bytes
Capturing subpattern count = 1
Named capturing subpatterns:
a 1
- a 1
No options
No first char
No need char
@@ -10245,7 +10304,7 @@ No match
Ket
Ket
Cond
- 4 Cond nref
+ Cond ref <D>2
X
Alt
Y
@@ -10291,7 +10350,7 @@ No match
CBra 4
d
Cond
- Cond nrecurse 1
+ Cond recurse <A>2
$
Alt
Recurse
@@ -10353,7 +10412,7 @@ Partial match: abca
xxxxabcde\P\P
Partial match: abcde
-/-- This is not in the Perl >= 5.10 test because Perl seems currently to be
+/-- This is not in the Perl-compatible test because Perl seems currently to be
broken and not behaving as specified in that it *does* bumpalong after
hitting (*COMMIT). --/
@@ -10549,34 +10608,14 @@ No match
End
------------------------------------------------------------------
-/ -- The first four of these are not in the Perl >= 5.10 test because Perl
- documents that the use of \K in assertions is "not well defined". The
- last is here because Perl gives the match as "b" rather than "ab". I
+/ -- This one is here because Perl gives the match as "b" rather than "ab". I
believe this to be a Perl bug. --/
-/(?=a\Kb)ab/
- ab
- 0: b
-
-/(?!a\Kb)ac/
- ac
- 0: ac
-
-/^abc(?<=b\Kc)d/
- abcd
- 0: cd
-
-/^abc(?<!b\Kq)d/
- abcd
- 0: abcd
-
/(?>a\Kb)z|(ab)/
ab
0: ab
1: ab
-/----------------------/
-
/(?P<L1>(?P<L2>0|)|(?P>L2)(?P>L1))/
Failed: recursive call could loop indefinitely at offset 31
@@ -10596,7 +10635,7 @@ Failed: an argument is not allowed for (*ACCEPT), (*FAIL), or (*COMMIT) at offse
ACABX
No match
-/--- These should be different, but in Perl 5.11 are not, which I think
+/--- These should be different, but in Perl they are not, which I think
is a bug in Perl. ---/
/A(*THEN)B|A(*THEN)C/K
@@ -10607,13 +10646,6 @@ No match
AC
No match
-/--- This should fail; the SKIP advances by one, but when we get to AC, the
- PRUNE kills it. Perl behaves differently. ---/
-
-/A(*PRUNE:A)A+(*SKIP:A)(B|Z) | AC/xK
- AAAC
-No match, mark = A
-
/--- Mark names can be duplicated. Perl doesn't give a mark for this one,
though PCRE does. ---/
@@ -10647,7 +10679,7 @@ No match
abcccd
No match
-/--- Perl 5.11 gets some of these wrong ---/
+/--- Perl gets some of these wrong ---/
/(?>.(*ACCEPT))*?5/
abcde
@@ -10826,21 +10858,9 @@ No match
X\x0d\x0a
No match
-/-- Perl treats this one differently, not failing the second string. I believe
- that is a bug in Perl. --/
-
-/^((abc|abcx)(*THEN)y|abcd)/
- abcd
- 0: abcd
- 1: abcd
- *** Failers
-No match
- abcxy
-No match
-
/(?<=abc)def/
abc\P\P
-Partial match: abc
+Partial match at offset 3: abc
/abc$/
abc
@@ -11087,12 +11107,14 @@ No need char
/(^ab|^)+/I
Capturing subpattern count = 1
+May match empty string
Options: anchored
No first char
No need char
/(^ab|^)++/I
Capturing subpattern count = 1
+May match empty string
Options: anchored
No first char
No need char
@@ -11111,12 +11133,14 @@ No need char
/(?:^ab|^)+/I
Capturing subpattern count = 0
+May match empty string
Options: anchored
No first char
No need char
/(?:^ab|^)++/I
Capturing subpattern count = 0
+May match empty string
Options: anchored
No first char
No need char
@@ -11135,12 +11159,14 @@ Need char = 'b'
/(.*ab|.*)+/I
Capturing subpattern count = 1
+May match empty string
No options
First char at start or follows newline
No need char
/(.*ab|.*)++/I
Capturing subpattern count = 1
+May match empty string
No options
First char at start or follows newline
No need char
@@ -11159,12 +11185,14 @@ Need char = 'b'
/(?:.*ab|.*)+/I
Capturing subpattern count = 0
+May match empty string
No options
First char at start or follows newline
No need char
/(?:.*ab|.*)++/I
Capturing subpattern count = 0
+May match empty string
No options
First char at start or follows newline
No need char
@@ -11319,7 +11347,6 @@ No match
/(a)b|ac/++SS
ac\O3
-Matched, but too many substrings
0: ac
0+
@@ -11571,7 +11598,7 @@ Matched, but too many substrings
Assert not
a
Ket
- \w+
+ \w++
Ket
End
------------------------------------------------------------------
@@ -11679,28 +11706,30 @@ No match
/\btype\b\W*?\btext\b\W*?\bjavascript\b/IS
Capturing subpattern count = 0
+Max lookbehind = 1
No options
First char = 't'
Need char = 't'
-Max lookbehind = 1
Subject length lower bound = 18
No set of starting bytes
/\btype\b\W*?\btext\b\W*?\bjavascript\b|\burl\b\W*?\bshell:|<input\b.*?\btype\b\W*?\bimage\b|\bonkeyup\b\W*?\=/IS
Capturing subpattern count = 0
+Max lookbehind = 1
No options
No first char
No need char
-Max lookbehind = 1
Subject length lower bound = 8
Starting byte set: < o t u
-/a(*SKIP)c|b(*ACCEPT)|/+SI
+/a(*SKIP)c|b(*ACCEPT)|/+S!I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
-Study returned NULL
+Subject length lower bound = -1
+No set of starting bytes
a
0:
0+
@@ -11761,75 +11790,16 @@ Minimum match() limit = 86
Minimum match() recursion limit = 45
0: abbbbbbbbbbbbbbbbbbbbba
-/-- These tests are in agreement with development Perl 5.015, which has fixed
- some things, but they don't all work with 5.012, so they aren't in the
- Perl-compatible tests. Those after the first come from Perl's own test
- files. --/
-
-/^((yes|no)(*THEN)(*F))?/
- yes
-No match
-
-/(A (.*) C? (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) C? (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) C? (*THEN) | A D) \s* (*FAIL)/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) C? (*THEN) | A D) \s* z/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) (?:C|) (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) (?:C|) (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) C{0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) C{0,6} (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) (CE){0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCEBefgBhiBqz
-No match
-
-/(A (.*) (CE){0,6} (*THEN) | A D) z/x
-AbcdCEBefgBhiBqz
-No match
-
-/(A (.*) (CE*){0,6} (*THEN) | A D) (*FAIL)/x
-AbcdCBefgBhiBqz
-No match
-
-/(A (.*) (CE*){0,6} (*THEN) | A D) z/x
-AbcdCBefgBhiBqz
-No match
-
-/-----------------------------------------------/
-
/^(?>a+)(?>(z+))\w/BZ
------------------------------------------------------------------
Bra
^
Once_NC
- a+
+ a++
Ket
Once
CBra 1
- z+
+ z++
Ket
Ket
\w
@@ -11888,14 +11858,14 @@ No match
/^(?>a+)(?>b+)(?>c+)(?>d+)(?>e+)/
\Maabbccddee
-Minimum match() limit = 12
-Minimum match() recursion limit = 3
+Minimum match() limit = 7
+Minimum match() recursion limit = 2
0: aabbccddee
/^(?>(a+))(?>(b+))(?>(c+))(?>(d+))(?>(e+))/
\Maabbccddee
-Minimum match() limit = 22
-Minimum match() recursion limit = 21
+Minimum match() limit = 17
+Minimum match() recursion limit = 16
0: aabbccddee
1: aa
2: bb
@@ -11905,8 +11875,8 @@ Minimum match() recursion limit = 21
/^(?>(a+))(?>b+)(?>(c+))(?>d+)(?>(e+))/
\Maabbccddee
-Minimum match() limit = 18
-Minimum match() recursion limit = 13
+Minimum match() limit = 13
+Minimum match() recursion limit = 10
0: aabbccddee
1: aa
2: cc
@@ -11997,7 +11967,10 @@ No match
Failed: \N is not supported in a class at offset 3
/a[B-\Nc]/
-Failed: \N is not supported in a class at offset 5
+Failed: invalid range in character class at offset 5
+
+/a[B\Nc]/
+Failed: \N is not supported in a class at offset 4
/(a)(?2){0,1999}?(b)/
@@ -12336,47 +12309,27 @@ Partial match: \x0d\x0d
\r\r\r\P\P
0: \x0d\x0d
-/-- These two are here because Perl does not match: it seems to allow the
-COMMIT to escape from the assertion. --/
-
-/(?=a(*COMMIT)b|ac)ac|ac/
- ac
- 0: ac
-
-/(?=a(*COMMIT)b|(ac)) ac | (a)c/x
- ac
- 0: ac
- 1: <unset>
- 2: a
-
"AB(C(D))(E(F))?(?(?=\2)(?=\4))"
ABCDGHI\O03
Matched, but too many substrings
0: ABCD
-/-- This one is here because Perl does not confine the *COMMIT to the
-assertion, and therefore fails the entire subroutine call. --/
-
-/((?=a(*COMMIT)b)ab|ac){0}(?:(?1)|a(c))/
- ac
- 0: ac
-
/-- These are all run as real matches in test 1; here we are just checking the
settings of the anchored and startline bits. --/
/(?>.*?a)(?<=ba)/I
Capturing subpattern count = 0
+Max lookbehind = 2
No options
No first char
Need char = 'a'
-Max lookbehind = 2
/(?:.*?a)(?<=ba)/I
Capturing subpattern count = 0
+Max lookbehind = 2
No options
First char at start or follows newline
Need char = 'a'
-Max lookbehind = 2
/.*?a(*PRUNE)b/I
Capturing subpattern count = 0
@@ -12422,17 +12375,19 @@ No need char
/(?>.*?)(?<=(abcd)|(wxyz))/I
Capturing subpattern count = 2
+Max lookbehind = 4
+May match empty string
No options
No first char
No need char
-Max lookbehind = 4
/(?>.*)(?<=(abcd)|(wxyz))/I
Capturing subpattern count = 2
+Max lookbehind = 4
+May match empty string
No options
No first char
No need char
-Max lookbehind = 4
"(?>.*)foo"I
Capturing subpattern count = 0
@@ -12468,6 +12423,7 @@ Need char = 'c'
/.?/S-I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
@@ -12475,10 +12431,1698 @@ Study returned NULL
/.?/S!I
Capturing subpattern count = 0
+May match empty string
No options
No first char
No need char
Subject length lower bound = -1
No set of starting bytes
+/(?:(a)+(?C1)bb|aa(?C2)b)/
+ aab\C+
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^ ^ b
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^^ b
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ b
+ 0: aab
+
+/(?:(a)++(?C1)bb|aa(?C2)b)/
+ aab\C+
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^ ^ b
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ b
+ 0: aab
+
+/(?:(?>(a))(?C1)bb|aa(?C2)b)/
+ aab\C+
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^^ b
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ b
+ 0: aab
+
+/(?:(?1)(?C1)x|ab(?C2))((a)){0}/
+ aab\C+
+Callout 1: last capture = -1
+ 0: <unset>
+--->aab
+ ^^ x
+Callout 1: last capture = -1
+ 0: <unset>
+--->aab
+ ^^ x
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ )
+ 0: ab
+
+/(?1)(?C1)((a)(?C2)){0}/
+ aab\C+
+Callout 2: last capture = 2
+ 0: <unset>
+ 1: <unset>
+ 2: a
+--->aab
+ ^^ )
+Callout 1: last capture = -1
+ 0: <unset>
+--->aab
+ ^^ ((a)(?C2)){0}
+ 0: a
+
+/(?:(a)+(?C1)bb|aa(?C2)b)++/
+ aab\C+
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^ ^ b
+Callout 1: last capture = 1
+ 0: <unset>
+ 1: a
+--->aab
+ ^^ b
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ b
+ 0: aab
+ aab\C+\O2
+Callout 1: last capture = 1
+ 0: <unset>
+--->aab
+ ^ ^ b
+Callout 1: last capture = 1
+ 0: <unset>
+--->aab
+ ^^ b
+Callout 2: last capture = -1
+ 0: <unset>
+--->aab
+ ^ ^ b
+ 0: aab
+
+/(ab)x|ab/
+ ab\O3
+ 0: ab
+ ab\O2
+ 0: ab
+
+/(ab)/
+ ab\O3
+Matched, but too many substrings
+ 0: ab
+ ab\O2
+Matched, but too many substrings
+ 0: ab
+
+/(?<=123)(*MARK:xx)abc/K
+ xxxx123a\P\P
+Partial match at offset 7, mark=xx: 123a
+ xxxx123a\P
+Partial match at offset 7, mark=xx: 123a
+
+/123\Kabc/
+ xxxx123a\P\P
+Partial match: 123a
+ xxxx123a\P
+Partial match: 123a
+
+/^(?(?=a)aa|bb)/C
+ bb
+--->bb
+ +0 ^ ^
+ +1 ^ (?(?=a)aa|bb)
+ +3 ^ (?=a)
+ +6 ^ a
++11 ^ b
++12 ^^ b
++13 ^ ^ )
++14 ^ ^
+ 0: bb
+
+/(?C1)^(?C2)(?(?C99)(?=(?C3)a(?C4))(?C5)a(?C6)a(?C7)|(?C8)b(?C9)b(?C10))(?C11)/
+ bb
+--->bb
+ 1 ^ ^
+ 2 ^ (?(?C99)(?=(?C3)a(?C4))(?C5)a(?C6)a(?C7)|(?C8)b(?C9)b(?C10))
+ 99 ^ (?=(?C3)a(?C4))
+ 3 ^ a
+ 8 ^ b
+ 9 ^^ b
+ 10 ^ ^ )
+ 11 ^ ^
+ 0: bb
+
+/-- Perl seems to have a bug with this one --/
+
+/aaaaa(*COMMIT)(*PRUNE)b|a+c/
+ aaaaaac
+ 0: aaaac
+
+/-- Here are some that Perl treats differently because of the way it handles
+backtracking verbs. --/
+
+ /(?!a(*COMMIT)b)ac|ad/
+ ac
+ 0: ac
+ ad
+ 0: ad
+
+/^(?!a(*THEN)b|ac)../
+ ac
+No match
+ ad
+ 0: ad
+
+/^(?=a(*THEN)b|ac)/
+ ac
+ 0:
+
+/\A.*?(?:a|b(*THEN)c)/
+ ba
+ 0: ba
+
+/\A.*?(?:a|b(*THEN)c)++/
+ ba
+ 0: ba
+
+/\A.*?(?:a|b(*THEN)c|d)/
+ ba
+ 0: ba
+
+/(?:(a(*MARK:X)a+(*SKIP:X)b)){0}(?:(?1)|aac)/
+ aac
+ 0: aac
+
+/\A.*?(a|b(*THEN)c)/
+ ba
+ 0: ba
+ 1: a
+
+/^(A(*THEN)B|A(*THEN)D)/
+ AD
+ 0: AD
+ 1: AD
+
+/(?!b(*THEN)a)bn|bnn/
+ bnn
+ 0: bn
+
+/(?(?=b(*SKIP)a)bn|bnn)/
+ bnn
+No match
+
+/(?=b(*THEN)a|)bn|bnn/
+ bnn
+ 0: bn
+
+/-------------------------/
+
+/(*LIMIT_MATCH=12bc)abc/
+Failed: (*VERB) not recognized or malformed at offset 7
+
+/(*LIMIT_MATCH=4294967290)abc/
+Failed: (*VERB) not recognized or malformed at offset 7
+
+/(*LIMIT_RECURSION=4294967280)abc/I
+Capturing subpattern count = 0
+Recursion limit = 4294967280
+No options
+First char = 'a'
+Need char = 'c'
+
+/(a+)*zz/
+ aaaaaaaaaaaaaz
+No match
+ aaaaaaaaaaaaaz\q3000
+Error -8 (match limit exceeded)
+
+/(a+)*zz/S-
+ aaaaaaaaaaaaaz\Q10
+Error -21 (recursion limit exceeded)
+
+/(*LIMIT_MATCH=3000)(a+)*zz/I
+Capturing subpattern count = 1
+Match limit = 3000
+No options
+No first char
+Need char = 'z'
+ aaaaaaaaaaaaaz
+Error -8 (match limit exceeded)
+ aaaaaaaaaaaaaz\q60000
+Error -8 (match limit exceeded)
+
+/(*LIMIT_MATCH=60000)(*LIMIT_MATCH=3000)(a+)*zz/I
+Capturing subpattern count = 1
+Match limit = 3000
+No options
+No first char
+Need char = 'z'
+ aaaaaaaaaaaaaz
+Error -8 (match limit exceeded)
+
+/(*LIMIT_MATCH=60000)(a+)*zz/I
+Capturing subpattern count = 1
+Match limit = 60000
+No options
+No first char
+Need char = 'z'
+ aaaaaaaaaaaaaz
+No match
+ aaaaaaaaaaaaaz\q3000
+Error -8 (match limit exceeded)
+
+/(*LIMIT_RECURSION=10)(a+)*zz/IS-
+Capturing subpattern count = 1
+Recursion limit = 10
+No options
+No first char
+Need char = 'z'
+Subject length lower bound = 2
+Starting byte set: a z
+ aaaaaaaaaaaaaz
+Error -21 (recursion limit exceeded)
+ aaaaaaaaaaaaaz\Q1000
+Error -21 (recursion limit exceeded)
+
+/(*LIMIT_RECURSION=10)(*LIMIT_RECURSION=1000)(a+)*zz/IS-
+Capturing subpattern count = 1
+Recursion limit = 10
+No options
+No first char
+Need char = 'z'
+Subject length lower bound = 2
+Starting byte set: a z
+ aaaaaaaaaaaaaz
+Error -21 (recursion limit exceeded)
+
+/(*LIMIT_RECURSION=1000)(a+)*zz/IS-
+Capturing subpattern count = 1
+Recursion limit = 1000
+No options
+No first char
+Need char = 'z'
+Subject length lower bound = 2
+Starting byte set: a z
+ aaaaaaaaaaaaaz
+No match
+ aaaaaaaaaaaaaz\Q10
+Error -21 (recursion limit exceeded)
+
+/-- This test causes a segfault with Perl 5.18.0 --/
+
+/^(?=(a)){0}b(?1)/
+ backgammon
+ 0: ba
+
+/(?|(?<n>f)|(?<n>b))/JI
+Capturing subpattern count = 1
+Named capturing subpatterns:
+ n 1
+Options: dupnames
+No first char
+No need char
+
+/(?<a>abc)(?<a>z)\k<a>()/JDZS
+------------------------------------------------------------------
+ Bra
+ CBra 1
+ abc
+ Ket
+ CBra 2
+ z
+ Ket
+ \k<a>2
+ CBra 3
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 3
+Max back reference = 2
+Named capturing subpatterns:
+ a 1
+ a 2
+Options: dupnames
+First char = 'a'
+Need char = 'z'
+Subject length lower bound = 5
+No set of starting bytes
+
+/a*[bcd]/BZ
+------------------------------------------------------------------
+ Bra
+ a*+
+ [b-d]
+ Ket
+ End
+------------------------------------------------------------------
+
+/[bcd]*a/BZ
+------------------------------------------------------------------
+ Bra
+ [b-d]*+
+ a
+ Ket
+ End
+------------------------------------------------------------------
+
+/-- A complete set of tests for auto-possessification of character types --/
+
+/\D+\D \D+\d \D+\S \D+\s \D+\W \D+\w \D+. \D+\C \D+\R \D+\H \D+\h \D+\V \D+\v \D+\Z \D+\z \D+$/BZx
+------------------------------------------------------------------
+ Bra
+ \D+
+ \D
+ \D++
+ \d
+ \D+
+ \S
+ \D+
+ \s
+ \D+
+ \W
+ \D+
+ \w
+ \D+
+ Any
+ \D+
+ AllAny
+ \D+
+ \R
+ \D+
+ \H
+ \D+
+ \h
+ \D+
+ \V
+ \D+
+ \v
+ \D+
+ \Z
+ \D++
+ \z
+ \D+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\d+\D \d+\d \d+\S \d+\s \d+\W \d+\w \d+. \d+\C \d+\R \d+\H \d+\h \d+\V \d+\v \d+\Z \d+\z \d+$/BZx
+------------------------------------------------------------------
+ Bra
+ \d++
+ \D
+ \d+
+ \d
+ \d+
+ \S
+ \d++
+ \s
+ \d++
+ \W
+ \d+
+ \w
+ \d+
+ Any
+ \d+
+ AllAny
+ \d++
+ \R
+ \d+
+ \H
+ \d++
+ \h
+ \d+
+ \V
+ \d++
+ \v
+ \d++
+ \Z
+ \d++
+ \z
+ \d++
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\S+\D \S+\d \S+\S \S+\s \S+\W \S+\w \S+. \S+\C \S+\R \S+\H \S+\h \S+\V \S+\v \S+\Z \S+\z \S+$/BZx
+------------------------------------------------------------------
+ Bra
+ \S+
+ \D
+ \S+
+ \d
+ \S+
+ \S
+ \S++
+ \s
+ \S+
+ \W
+ \S+
+ \w
+ \S+
+ Any
+ \S+
+ AllAny
+ \S++
+ \R
+ \S+
+ \H
+ \S++
+ \h
+ \S+
+ \V
+ \S++
+ \v
+ \S++
+ \Z
+ \S++
+ \z
+ \S++
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\s+\D \s+\d \s+\S \s+\s \s+\W \s+\w \s+. \s+\C \s+\R \s+\H \s+\h \s+\V \s+\v \s+\Z \s+\z \s+$/BZx
+------------------------------------------------------------------
+ Bra
+ \s+
+ \D
+ \s++
+ \d
+ \s++
+ \S
+ \s+
+ \s
+ \s+
+ \W
+ \s++
+ \w
+ \s+
+ Any
+ \s+
+ AllAny
+ \s+
+ \R
+ \s+
+ \H
+ \s+
+ \h
+ \s+
+ \V
+ \s+
+ \v
+ \s+
+ \Z
+ \s++
+ \z
+ \s+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\W+\D \W+\d \W+\S \W+\s \W+\W \W+\w \W+. \W+\C \W+\R \W+\H \W+\h \W+\V \W+\v \W+\Z \W+\z \W+$/BZx
+------------------------------------------------------------------
+ Bra
+ \W+
+ \D
+ \W++
+ \d
+ \W+
+ \S
+ \W+
+ \s
+ \W+
+ \W
+ \W++
+ \w
+ \W+
+ Any
+ \W+
+ AllAny
+ \W+
+ \R
+ \W+
+ \H
+ \W+
+ \h
+ \W+
+ \V
+ \W+
+ \v
+ \W+
+ \Z
+ \W++
+ \z
+ \W+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\w+\D \w+\d \w+\S \w+\s \w+\W \w+\w \w+. \w+\C \w+\R \w+\H \w+\h \w+\V \w+\v \w+\Z \w+\z \w+$/BZx
+------------------------------------------------------------------
+ Bra
+ \w+
+ \D
+ \w+
+ \d
+ \w+
+ \S
+ \w++
+ \s
+ \w++
+ \W
+ \w+
+ \w
+ \w+
+ Any
+ \w+
+ AllAny
+ \w++
+ \R
+ \w+
+ \H
+ \w++
+ \h
+ \w+
+ \V
+ \w++
+ \v
+ \w++
+ \Z
+ \w++
+ \z
+ \w++
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\C+\D \C+\d \C+\S \C+\s \C+\W \C+\w \C+. \C+\C \C+\R \C+\H \C+\h \C+\V \C+\v \C+\Z \C+\z \C+$/BZx
+------------------------------------------------------------------
+ Bra
+ AllAny+
+ \D
+ AllAny+
+ \d
+ AllAny+
+ \S
+ AllAny+
+ \s
+ AllAny+
+ \W
+ AllAny+
+ \w
+ AllAny+
+ Any
+ AllAny+
+ AllAny
+ AllAny+
+ \R
+ AllAny+
+ \H
+ AllAny+
+ \h
+ AllAny+
+ \V
+ AllAny+
+ \v
+ AllAny+
+ \Z
+ AllAny++
+ \z
+ AllAny+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\R+\D \R+\d \R+\S \R+\s \R+\W \R+\w \R+. \R+\C \R+\R \R+\H \R+\h \R+\V \R+\v \R+\Z \R+\z \R+$/BZx
+------------------------------------------------------------------
+ Bra
+ \R+
+ \D
+ \R++
+ \d
+ \R+
+ \S
+ \R++
+ \s
+ \R+
+ \W
+ \R++
+ \w
+ \R++
+ Any
+ \R+
+ AllAny
+ \R+
+ \R
+ \R+
+ \H
+ \R++
+ \h
+ \R+
+ \V
+ \R+
+ \v
+ \R+
+ \Z
+ \R++
+ \z
+ \R+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\H+\D \H+\d \H+\S \H+\s \H+\W \H+\w \H+. \H+\C \H+\R \H+\H \H+\h \H+\V \H+\v \H+\Z \H+\z \H+$/BZx
+------------------------------------------------------------------
+ Bra
+ \H+
+ \D
+ \H+
+ \d
+ \H+
+ \S
+ \H+
+ \s
+ \H+
+ \W
+ \H+
+ \w
+ \H+
+ Any
+ \H+
+ AllAny
+ \H+
+ \R
+ \H+
+ \H
+ \H++
+ \h
+ \H+
+ \V
+ \H+
+ \v
+ \H+
+ \Z
+ \H++
+ \z
+ \H+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\h+\D \h+\d \h+\S \h+\s \h+\W \h+\w \h+. \h+\C \h+\R \h+\H \h+\h \h+\V \h+\v \h+\Z \h+\z \h+$/BZx
+------------------------------------------------------------------
+ Bra
+ \h+
+ \D
+ \h++
+ \d
+ \h++
+ \S
+ \h+
+ \s
+ \h+
+ \W
+ \h++
+ \w
+ \h+
+ Any
+ \h+
+ AllAny
+ \h++
+ \R
+ \h++
+ \H
+ \h+
+ \h
+ \h+
+ \V
+ \h++
+ \v
+ \h+
+ \Z
+ \h++
+ \z
+ \h+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\V+\D \V+\d \V+\S \V+\s \V+\W \V+\w \V+. \V+\C \V+\R \V+\H \V+\h \V+\V \V+\v \V+\Z \V+\z \V+$/BZx
+------------------------------------------------------------------
+ Bra
+ \V+
+ \D
+ \V+
+ \d
+ \V+
+ \S
+ \V+
+ \s
+ \V+
+ \W
+ \V+
+ \w
+ \V+
+ Any
+ \V+
+ AllAny
+ \V++
+ \R
+ \V+
+ \H
+ \V+
+ \h
+ \V+
+ \V
+ \V++
+ \v
+ \V+
+ \Z
+ \V++
+ \z
+ \V+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\v+\D \v+\d \v+\S \v+\s \v+\W \v+\w \v+. \v+\C \v+\R \v+\H \v+\h \v+\V \v+\v \v+\Z \v+\z \v+$/BZx
+------------------------------------------------------------------
+ Bra
+ \v+
+ \D
+ \v++
+ \d
+ \v++
+ \S
+ \v+
+ \s
+ \v+
+ \W
+ \v++
+ \w
+ \v+
+ Any
+ \v+
+ AllAny
+ \v+
+ \R
+ \v+
+ \H
+ \v++
+ \h
+ \v++
+ \V
+ \v+
+ \v
+ \v+
+ \Z
+ \v++
+ \z
+ \v+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/ a+\D a+\d a+\S a+\s a+\W a+\w a+. a+\C a+\R a+\H a+\h a+\V a+\v a+\Z a+\z a+$/BZx
+------------------------------------------------------------------
+ Bra
+ a+
+ \D
+ a++
+ \d
+ a+
+ \S
+ a++
+ \s
+ a++
+ \W
+ a+
+ \w
+ a+
+ Any
+ a+
+ AllAny
+ a++
+ \R
+ a+
+ \H
+ a++
+ \h
+ a+
+ \V
+ a++
+ \v
+ a++
+ \Z
+ a++
+ \z
+ a++
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\n+\D \n+\d \n+\S \n+\s \n+\W \n+\w \n+. \n+\C \n+\R \n+\H \n+\h \n+\V \n+\v \n+\Z \n+\z \n+$/BZx
+------------------------------------------------------------------
+ Bra
+ \x0a+
+ \D
+ \x0a++
+ \d
+ \x0a++
+ \S
+ \x0a+
+ \s
+ \x0a+
+ \W
+ \x0a++
+ \w
+ \x0a+
+ Any
+ \x0a+
+ AllAny
+ \x0a+
+ \R
+ \x0a+
+ \H
+ \x0a++
+ \h
+ \x0a++
+ \V
+ \x0a+
+ \v
+ \x0a+
+ \Z
+ \x0a++
+ \z
+ \x0a+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/ .+\D .+\d .+\S .+\s .+\W .+\w .+. .+\C .+\R .+\H .+\h .+\V .+\v .+\Z .+\z .+$/BZx
+------------------------------------------------------------------
+ Bra
+ Any+
+ \D
+ Any+
+ \d
+ Any+
+ \S
+ Any+
+ \s
+ Any+
+ \W
+ Any+
+ \w
+ Any+
+ Any
+ Any+
+ AllAny
+ Any++
+ \R
+ Any+
+ \H
+ Any+
+ \h
+ Any+
+ \V
+ Any+
+ \v
+ Any+
+ \Z
+ Any++
+ \z
+ Any+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/ .+\D .+\d .+\S .+\s .+\W .+\w .+. .+\C .+\R .+\H .+\h .+\V .+\v .+\Z .+\z .+$/BZxs
+------------------------------------------------------------------
+ Bra
+ AllAny+
+ \D
+ AllAny+
+ \d
+ AllAny+
+ \S
+ AllAny+
+ \s
+ AllAny+
+ \W
+ AllAny+
+ \w
+ AllAny+
+ AllAny
+ AllAny+
+ AllAny
+ AllAny+
+ \R
+ AllAny+
+ \H
+ AllAny+
+ \h
+ AllAny+
+ \V
+ AllAny+
+ \v
+ AllAny+
+ \Z
+ AllAny++
+ \z
+ AllAny+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\D+$ \d+$ \S+$ \s+$ \W+$ \w+$ \C+$ \R+$ \H+$ \h+$ \V+$ \v+$ a+$ \n+$ .+$ .+$/BZxm
+------------------------------------------------------------------
+ Bra
+ \D+
+ /m $
+ \d++
+ /m $
+ \S++
+ /m $
+ \s+
+ /m $
+ \W+
+ /m $
+ \w++
+ /m $
+ AllAny+
+ /m $
+ \R+
+ /m $
+ \H+
+ /m $
+ \h+
+ /m $
+ \V+
+ /m $
+ \v+
+ /m $
+ a+
+ /m $
+ \x0a+
+ /m $
+ Any+
+ /m $
+ Any+
+ /m $
+ Ket
+ End
+------------------------------------------------------------------
+
+/(?=a+)a(a+)++a/BZ
+------------------------------------------------------------------
+ Bra
+ Assert
+ a++
+ Ket
+ a
+ CBraPos 1
+ a++
+ KetRpos
+ a
+ Ket
+ End
+------------------------------------------------------------------
+
+/a+(bb|cc)a+(?:bb|cc)a+(?>bb|cc)a+(?:bb|cc)+a+(aa)a+(?:bb|aa)/BZ
+------------------------------------------------------------------
+ Bra
+ a++
+ CBra 1
+ bb
+ Alt
+ cc
+ Ket
+ a++
+ Bra
+ bb
+ Alt
+ cc
+ Ket
+ a++
+ Once_NC
+ bb
+ Alt
+ cc
+ Ket
+ a++
+ Bra
+ bb
+ Alt
+ cc
+ KetRmax
+ a+
+ CBra 2
+ aa
+ Ket
+ a+
+ Bra
+ bb
+ Alt
+ aa
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+
+/a+(bb|cc)?#a+(?:bb|cc)??#a+(?:bb|cc)?+#a+(?:bb|cc)*#a+(bb|cc)?a#a+(?:aa)?/BZ
+------------------------------------------------------------------
+ Bra
+ a++
+ Brazero
+ CBra 1
+ bb
+ Alt
+ cc
+ Ket
+ #
+ a++
+ Braminzero
+ Bra
+ bb
+ Alt
+ cc
+ Ket
+ #
+ a++
+ Once
+ Brazero
+ Bra
+ bb
+ Alt
+ cc
+ Ket
+ Ket
+ #
+ a++
+ Brazero
+ Bra
+ bb
+ Alt
+ cc
+ KetRmax
+ #
+ a+
+ Brazero
+ CBra 2
+ bb
+ Alt
+ cc
+ Ket
+ a#
+ a+
+ Brazero
+ Bra
+ aa
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+
+/a+(?:bb)?a#a+(?:|||)#a+(?:|b)a#a+(?:|||)?a/BZ
+------------------------------------------------------------------
+ Bra
+ a+
+ Brazero
+ Bra
+ bb
+ Ket
+ a#
+ a++
+ Bra
+ Alt
+ Alt
+ Alt
+ Ket
+ #
+ a+
+ Bra
+ Alt
+ b
+ Ket
+ a#
+ a+
+ Brazero
+ Bra
+ Alt
+ Alt
+ Alt
+ Ket
+ a
+ Ket
+ End
+------------------------------------------------------------------
+
+/[ab]*/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]*+
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aaaa
+
+/[ab]*?/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]*?
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0:
+
+/[ab]?/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]?+
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: a
+
+/[ab]??/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]??
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0:
+
+/[ab]+/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]++
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aaaa
+
+/[ab]+?/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]+?
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: a
+
+/[ab]{2,3}/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]{2,3}+
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aaa
+
+/[ab]{2,3}?/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]{2,3}?
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aa
+
+/[ab]{2,}/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]{2,}+
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aaaa
+
+/[ab]{2,}?/BZ
+------------------------------------------------------------------
+ Bra
+ [ab]{2,}?
+ Ket
+ End
+------------------------------------------------------------------
+ aaaa
+ 0: aa
+
+/\d+\s{0,5}=\s*\S?=\w{0,4}\W*/BZ
+------------------------------------------------------------------
+ Bra
+ \d++
+ \s{0,5}+
+ =
+ \s*+
+ \S?
+ =
+ \w{0,4}+
+ \W*+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-d]{5,12}[e-z0-9]*#[^a-z]+[b-y]*a[2-7]?[^0-9a-z]+/BZ
+------------------------------------------------------------------
+ Bra
+ [a-d]{5,12}+
+ [0-9e-z]*+
+ #
+ [\x00-`{-\xff] (neg)++
+ [b-y]*+
+ a
+ [2-7]?+
+ [\x00-/:-`{-\xff] (neg)++
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-z]*\s#[ \t]?\S#[a-c]*\S#[C-G]+?\d#[4-8]*\D#[4-9,]*\D#[!$]{0,5}\w#[M-Xf-l]+\W#[a-c,]?\W/BZ
+------------------------------------------------------------------
+ Bra
+ [a-z]*+
+ \s
+ #
+ [\x09 ]?+
+ \S
+ #
+ [a-c]*
+ \S
+ #
+ [C-G]++
+ \d
+ #
+ [4-8]*+
+ \D
+ #
+ [,4-9]*
+ \D
+ #
+ [!$]{0,5}+
+ \w
+ #
+ [M-Xf-l]++
+ \W
+ #
+ [,a-c]?
+ \W
+ Ket
+ End
+------------------------------------------------------------------
+
+/a+(aa|bb)*c#a*(bb|cc)*a#a?(bb|cc)*d#[a-f]*(g|hh)*f/BZ
+------------------------------------------------------------------
+ Bra
+ a+
+ Brazero
+ CBra 1
+ aa
+ Alt
+ bb
+ KetRmax
+ c#
+ a*
+ Brazero
+ CBra 2
+ bb
+ Alt
+ cc
+ KetRmax
+ a#
+ a?+
+ Brazero
+ CBra 3
+ bb
+ Alt
+ cc
+ KetRmax
+ d#
+ [a-f]*
+ Brazero
+ CBra 4
+ g
+ Alt
+ hh
+ KetRmax
+ f
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-f]*(g|hh|i)*i#[a-x]{4,}(y{0,6})*y#[a-k]+(ll|mm)+n/BZ
+------------------------------------------------------------------
+ Bra
+ [a-f]*+
+ Brazero
+ CBra 1
+ g
+ Alt
+ hh
+ Alt
+ i
+ KetRmax
+ i#
+ [a-x]{4,}
+ Brazero
+ SCBra 2
+ y{0,6}
+ KetRmax
+ y#
+ [a-k]++
+ CBra 3
+ ll
+ Alt
+ mm
+ KetRmax
+ n
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-f]*(?>gg|hh)+#[a-f]*(?>gg|hh)?#[a-f]*(?>gg|hh)*a#[a-f]*(?>gg|hh)*h/BZ
+------------------------------------------------------------------
+ Bra
+ [a-f]*+
+ Once_NC
+ gg
+ Alt
+ hh
+ KetRmax
+ #
+ [a-f]*+
+ Brazero
+ Once_NC
+ gg
+ Alt
+ hh
+ Ket
+ #
+ [a-f]*
+ Brazero
+ Once_NC
+ gg
+ Alt
+ hh
+ KetRmax
+ a#
+ [a-f]*+
+ Brazero
+ Once_NC
+ gg
+ Alt
+ hh
+ KetRmax
+ h
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-c]*d/DZS
+------------------------------------------------------------------
+ Bra
+ [a-c]*+
+ d
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+Need char = 'd'
+Subject length lower bound = 1
+Starting byte set: a b c d
+
+/[a-c]+d/DZS
+------------------------------------------------------------------
+ Bra
+ [a-c]++
+ d
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+Need char = 'd'
+Subject length lower bound = 2
+Starting byte set: a b c
+
+/[a-c]?d/DZS
+------------------------------------------------------------------
+ Bra
+ [a-c]?+
+ d
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+Need char = 'd'
+Subject length lower bound = 1
+Starting byte set: a b c d
+
+/[a-c]{4,6}d/DZS
+------------------------------------------------------------------
+ Bra
+ [a-c]{4,6}+
+ d
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+Need char = 'd'
+Subject length lower bound = 5
+Starting byte set: a b c
+
+/[a-c]{0,6}d/DZS
+------------------------------------------------------------------
+ Bra
+ [a-c]{0,6}+
+ d
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+Need char = 'd'
+Subject length lower bound = 1
+Starting byte set: a b c d
+
+/-- End of special auto-possessive tests --/
+
+/^A\o{1239}B/
+Failed: non-octal character in \o{} (closing brace missing?) at offset 8
+
+/^A\oB/
+Failed: missing opening brace after \o at offset 3
+
+/^A\x{zz}B/
+Failed: non-hex character in \x{} (closing brace missing?) at offset 5
+
+/^A\x{12Z/
+Failed: non-hex character in \x{} (closing brace missing?) at offset 7
+
+/^A\x{/
+Failed: non-hex character in \x{} (closing brace missing?) at offset 5
+
+/[ab]++/BZO
+------------------------------------------------------------------
+ Bra
+ [ab]++
+ Ket
+ End
+------------------------------------------------------------------
+
+/[^ab]*+/BZO
+------------------------------------------------------------------
+ Bra
+ [\x00-`c-\xff] (neg)*+
+ Ket
+ End
+------------------------------------------------------------------
+
+/a{4}+/BZO
+------------------------------------------------------------------
+ Bra
+ a{4}
+ Ket
+ End
+------------------------------------------------------------------
+
+/a{4}+/BZOi
+------------------------------------------------------------------
+ Bra
+ /i a{4}
+ Ket
+ End
+------------------------------------------------------------------
+
+/[a-[:digit:]]+/
+Failed: invalid range in character class at offset 3
+
+/[A-[:digit:]]+/
+Failed: invalid range in character class at offset 3
+
+/[a-[.xxx.]]+/
+Failed: invalid range in character class at offset 3
+
+/[a-[=xxx=]]+/
+Failed: invalid range in character class at offset 3
+
+/[a-[!xxx!]]+/
+Failed: range out of order in character class at offset 3
+
+/[A-[!xxx!]]+/
+ A]]]
+ 0: A]]]
+
+/[a-\d]+/
+Failed: invalid range in character class at offset 4
+
+/(?<0abc>xx)/
+Failed: group name must start with a non-digit at offset 3
+
+/(?&1abc)xx(?<1abc>y)/
+Failed: group name must start with a non-digit at offset 3
+
+/(?<ab-cd>xx)/
+Failed: syntax error in subpattern name (missing terminator) at offset 5
+
+/(?'0abc'xx)/
+Failed: group name must start with a non-digit at offset 3
+
+/(?P<0abc>xx)/
+Failed: group name must start with a non-digit at offset 4
+
+/\k<5ghj>/
+Failed: group name must start with a non-digit at offset 3
+
+/\k'5ghj'/
+Failed: group name must start with a non-digit at offset 3
+
+/\k{2fgh}/
+Failed: group name must start with a non-digit at offset 3
+
+/(?P=8yuki)/
+Failed: group name must start with a non-digit at offset 4
+
+/\g{4df}/
+Failed: group name must start with a non-digit at offset 3
+
+/(?&1abc)xx(?<1abc>y)/
+Failed: group name must start with a non-digit at offset 3
+
+/(?P>1abc)xx(?<1abc>y)/
+Failed: group name must start with a non-digit at offset 4
+
+/\g'3gh'/
+Failed: \g is not followed by a braced, angle-bracketed, or quoted name/number or by a plain number at offset 7
+
+/\g<5fg>/
+Failed: \g is not followed by a braced, angle-bracketed, or quoted name/number or by a plain number at offset 7
+
+/(?(<4gh>)abc)/
+Failed: group name must start with a non-digit at offset 4
+
+/(?('4gh')abc)/
+Failed: group name must start with a non-digit at offset 4
+
+/(?(4gh)abc)/
+Failed: malformed number or name after (?( at offset 4
+
+/(?(R&6yh)abc)/
+Failed: group name must start with a non-digit at offset 5
+
+/-- Test the ugly "start or end of word" compatibility syntax --/
+
+/[[:<:]]red[[:>:]]/BZ
+------------------------------------------------------------------
+ Bra
+ \b
+ Assert
+ \w
+ Ket
+ red
+ \b
+ AssertB
+ Reverse
+ \w
+ Ket
+ Ket
+ End
+------------------------------------------------------------------
+ little red riding hood
+ 0: red
+ a /red/ thing
+ 0: red
+ red is a colour
+ 0: red
+ put it all on red
+ 0: red
+ ** Failers
+No match
+ no reduction
+No match
+ Alfred Winifred
+No match
+
+/[a[:<:]] should give error/
+Failed: unknown POSIX class name at offset 4
+
/-- End of testinput2 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput20 b/ext/pcre/pcrelib/testdata/testoutput20
new file mode 100644
index 0000000000..c1b20ee804
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput20
@@ -0,0 +1,24 @@
+/-- These DFA tests are for the handling of characters greater than 255 in
+ 16- or 32-bit, non-UTF mode. --/
+
+/^\x{ffff}+/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}?/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}*/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/^\x{ffff}{3}/i
+ \x{ffff}\x{ffff}\x{ffff}
+ 0: \x{ffff}\x{ffff}\x{ffff}
+
+/^\x{ffff}{0,3}/i
+ \x{ffff}
+ 0: \x{ffff}
+
+/-- End of testinput20 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput21-16 b/ext/pcre/pcrelib/testdata/testoutput21-16
new file mode 100644
index 0000000000..0e21350f89
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput21-16
@@ -0,0 +1,100 @@
+/-- Tests for reloading pre-compiled patterns. The first one gives an error
+right away, and can be any old pattern compiled in 8-bit mode ("abc" is
+typical). The others require the link size to be 2. */x
+
+<!testsaved8
+Compiled pattern loaded from testsaved8
+No study data
+Error -28 from pcre16_fullinfo(0)
+Running in 16-bit mode but pattern was compiled in 8-bit mode
+
+%-- Generated from:
+ /^[aL](?P<name>(?:[AaLl]+)[^xX-]*?)(?P<other>[\x{150}-\x{250}\x{300}]|
+ [^\x{800}aAs-uS-U\x{d800}-\x{dfff}])++[^#\b\x{500}\x{1000}]{3,5}$
+ /x
+
+ In 16-bit mode with options: S>testdata/saved16LE-1
+ FS>testdata/saved16BE-1
+ In 32-bit mode with options: S>testdata/saved32LE-1
+ FS>testdata/saved32BE-1
+--%x
+
+<!testsaved16LE-1
+Compiled pattern loaded from testsaved16LE-1
+Study data loaded from testsaved16LE-1
+------------------------------------------------------------------
+ 0 134 Bra
+ 2 ^
+ 3 [La]
+ 20 43 CBra 1
+ 23 20 Bra
+ 25 [ALal]+
+ 43 20 Ket
+ 45 [\x00-,.-WY-wy-\xff] (neg)*?
+ 63 43 Ket
+ 65 12 CBraPos 2
+ 68 [\x{150}-\x{250}\x{300}]
+ 77 27 Alt
+ 79 [^AS-Uas-u\x{800}\x{d800}-\x{dfff}]
+104 39 KetRpos
+106 [^\x08#\x{500}\x{1000}]{3,5}
+133 $
+134 134 Ket
+136 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ name 1
+ other 2
+Options: anchored extended
+No first char
+No need char
+Subject length lower bound = 6
+No set of starting bytes
+
+<!testsaved16BE-1
+Compiled pattern loaded from testsaved16BE-1
+Study data loaded from testsaved16BE-1
+------------------------------------------------------------------
+ 0 134 Bra
+ 2 ^
+ 3 [La]
+ 20 43 CBra 1
+ 23 20 Bra
+ 25 [ALal]+
+ 43 20 Ket
+ 45 [\x00-,.-WY-wy-\xff] (neg)*?
+ 63 43 Ket
+ 65 12 CBraPos 2
+ 68 [\x{150}-\x{250}\x{300}]
+ 77 27 Alt
+ 79 [^AS-Uas-u\x{800}\x{d800}-\x{dfff}]
+104 39 KetRpos
+106 [^\x08#\x{500}\x{1000}]{3,5}
+133 $
+134 134 Ket
+136 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ name 1
+ other 2
+Options: anchored extended
+No first char
+No need char
+Subject length lower bound = 6
+No set of starting bytes
+
+<!testsaved32LE-1
+Compiled pattern loaded from testsaved32LE-1
+Study data loaded from testsaved32LE-1
+Error -28 from pcre16_fullinfo(0)
+Running in 16-bit mode but pattern was compiled in 32-bit mode
+
+<!testsaved32BE-1
+Compiled pattern loaded from testsaved32BE-1
+Study data loaded from testsaved32BE-1
+Error -28 from pcre16_fullinfo(0)
+Running in 16-bit mode but pattern was compiled in 32-bit mode
+
+/-- End of testinput21 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput21-32 b/ext/pcre/pcrelib/testdata/testoutput21-32
new file mode 100644
index 0000000000..183487aca1
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput21-32
@@ -0,0 +1,100 @@
+/-- Tests for reloading pre-compiled patterns. The first one gives an error
+right away, and can be any old pattern compiled in 8-bit mode ("abc" is
+typical). The others require the link size to be 2. */x
+
+<!testsaved8
+Compiled pattern loaded from testsaved8
+No study data
+Error -28 from pcre32_fullinfo(0)
+Running in 32-bit mode but pattern was compiled in 8-bit mode
+
+%-- Generated from:
+ /^[aL](?P<name>(?:[AaLl]+)[^xX-]*?)(?P<other>[\x{150}-\x{250}\x{300}]|
+ [^\x{800}aAs-uS-U\x{d800}-\x{dfff}])++[^#\b\x{500}\x{1000}]{3,5}$
+ /x
+
+ In 16-bit mode with options: S>testdata/saved16LE-1
+ FS>testdata/saved16BE-1
+ In 32-bit mode with options: S>testdata/saved32LE-1
+ FS>testdata/saved32BE-1
+--%x
+
+<!testsaved16LE-1
+Compiled pattern loaded from testsaved16LE-1
+Study data loaded from testsaved16LE-1
+Error -28 from pcre32_fullinfo(0)
+Running in 32-bit mode but pattern was compiled in 16-bit mode
+
+<!testsaved16BE-1
+Compiled pattern loaded from testsaved16BE-1
+Study data loaded from testsaved16BE-1
+Error -28 from pcre32_fullinfo(0)
+Running in 32-bit mode but pattern was compiled in 16-bit mode
+
+<!testsaved32LE-1
+Compiled pattern loaded from testsaved32LE-1
+Study data loaded from testsaved32LE-1
+------------------------------------------------------------------
+ 0 94 Bra
+ 2 ^
+ 3 [La]
+ 12 27 CBra 1
+ 15 12 Bra
+ 17 [ALal]+
+ 27 12 Ket
+ 29 [\x00-,.-WY-wy-\xff] (neg)*?
+ 39 27 Ket
+ 41 12 CBraPos 2
+ 44 [\x{150}-\x{250}\x{300}]
+ 53 19 Alt
+ 55 [^AS-Uas-u\x{800}\x{d800}-\x{dfff}]
+ 72 31 KetRpos
+ 74 [^\x08#\x{500}\x{1000}]{3,5}
+ 93 $
+ 94 94 Ket
+ 96 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ name 1
+ other 2
+Options: anchored extended
+No first char
+No need char
+Subject length lower bound = 6
+No set of starting bytes
+
+<!testsaved32BE-1
+Compiled pattern loaded from testsaved32BE-1
+Study data loaded from testsaved32BE-1
+------------------------------------------------------------------
+ 0 94 Bra
+ 2 ^
+ 3 [La]
+ 12 27 CBra 1
+ 15 12 Bra
+ 17 [ALal]+
+ 27 12 Ket
+ 29 [\x00-,.-WY-wy-\xff] (neg)*?
+ 39 27 Ket
+ 41 12 CBraPos 2
+ 44 [\x{150}-\x{250}\x{300}]
+ 53 19 Alt
+ 55 [^AS-Uas-u\x{800}\x{d800}-\x{dfff}]
+ 72 31 KetRpos
+ 74 [^\x08#\x{500}\x{1000}]{3,5}
+ 93 $
+ 94 94 Ket
+ 96 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ name 1
+ other 2
+Options: anchored extended
+No first char
+No need char
+Subject length lower bound = 6
+No set of starting bytes
+
+/-- End of testinput21 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput22-16 b/ext/pcre/pcrelib/testdata/testoutput22-16
new file mode 100644
index 0000000000..f896b13e18
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput22-16
@@ -0,0 +1,81 @@
+/-- Tests for reloading pre-compile patterns with UTF-16 or UTF-32 support. */
+
+%-- Generated from:
+ /(?P<cbra1>[aZ\x{400}-\x{10ffff}]{4,}
+ [\x{f123}\x{10039}\x{20000}-\x{21234}]?|
+ [A-Cx-z\x{100000}-\x{1000a7}\x{101234}])
+ (?<cb2>[^az])/x
+
+ In 16-bit mode with options: S8>testdata/saved16LE-2
+ FS8>testdata/saved16BE-2
+ In 32-bit mode with options: S8>testdata/saved32LE-2
+ FS8>testdata/saved32BE-2
+--%8x
+
+<!testsaved16LE-2
+Compiled pattern loaded from testsaved16LE-2
+Study data loaded from testsaved16LE-2
+------------------------------------------------------------------
+ 0 101 Bra
+ 2 45 CBra 1
+ 5 [Za\x{400}-\x{10ffff}]{4,}
+ 32 [\x{f123}\x{10039}\x{20000}-\x{21234}]?
+ 47 30 Alt
+ 49 [A-Cx-z\x{100000}-\x{1000a7}\x{101234}]
+ 77 75 Ket
+ 79 20 CBra 2
+ 82 [\x00-`b-y{-\xff] (neg)
+ 99 20 Ket
+101 101 Ket
+103 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ cb2 2
+ cbra1 1
+Options: extended utf
+No first char
+No need char
+Subject length lower bound = 2
+No set of starting bytes
+
+<!testsaved16BE-2
+Compiled pattern loaded from testsaved16BE-2
+Study data loaded from testsaved16BE-2
+------------------------------------------------------------------
+ 0 101 Bra
+ 2 45 CBra 1
+ 5 [Za\x{400}-\x{10ffff}]{4,}
+ 32 [\x{f123}\x{10039}\x{20000}-\x{21234}]?
+ 47 30 Alt
+ 49 [A-Cx-z\x{100000}-\x{1000a7}\x{101234}]
+ 77 75 Ket
+ 79 20 CBra 2
+ 82 [\x00-`b-y{-\xff] (neg)
+ 99 20 Ket
+101 101 Ket
+103 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ cb2 2
+ cbra1 1
+Options: extended utf
+No first char
+No need char
+Subject length lower bound = 2
+No set of starting bytes
+
+<!testsaved32LE-2
+Compiled pattern loaded from testsaved32LE-2
+Study data loaded from testsaved32LE-2
+Error -28 from pcre16_fullinfo(0)
+Running in 16-bit mode but pattern was compiled in 32-bit mode
+
+<!testsaved32BE-2
+Compiled pattern loaded from testsaved32BE-2
+Study data loaded from testsaved32BE-2
+Error -28 from pcre16_fullinfo(0)
+Running in 16-bit mode but pattern was compiled in 32-bit mode
+
+/-- End of testinput22 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput22-32 b/ext/pcre/pcrelib/testdata/testoutput22-32
new file mode 100644
index 0000000000..783926b821
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput22-32
@@ -0,0 +1,81 @@
+/-- Tests for reloading pre-compile patterns with UTF-16 or UTF-32 support. */
+
+%-- Generated from:
+ /(?P<cbra1>[aZ\x{400}-\x{10ffff}]{4,}
+ [\x{f123}\x{10039}\x{20000}-\x{21234}]?|
+ [A-Cx-z\x{100000}-\x{1000a7}\x{101234}])
+ (?<cb2>[^az])/x
+
+ In 16-bit mode with options: S8>testdata/saved16LE-2
+ FS8>testdata/saved16BE-2
+ In 32-bit mode with options: S8>testdata/saved32LE-2
+ FS8>testdata/saved32BE-2
+--%8x
+
+<!testsaved16LE-2
+Compiled pattern loaded from testsaved16LE-2
+Study data loaded from testsaved16LE-2
+Error -28 from pcre32_fullinfo(0)
+Running in 32-bit mode but pattern was compiled in 16-bit mode
+
+<!testsaved16BE-2
+Compiled pattern loaded from testsaved16BE-2
+Study data loaded from testsaved16BE-2
+Error -28 from pcre32_fullinfo(0)
+Running in 32-bit mode but pattern was compiled in 16-bit mode
+
+<!testsaved32LE-2
+Compiled pattern loaded from testsaved32LE-2
+Study data loaded from testsaved32LE-2
+------------------------------------------------------------------
+ 0 70 Bra
+ 2 33 CBra 1
+ 5 [Za\x{400}-\x{10ffff}]{4,}
+ 23 [\x{f123}\x{10039}\x{20000}-\x{21234}]?
+ 35 19 Alt
+ 37 [A-Cx-z\x{100000}-\x{1000a7}\x{101234}]
+ 54 52 Ket
+ 56 12 CBra 2
+ 59 [\x00-`b-y{-\xff] (neg)
+ 68 12 Ket
+ 70 70 Ket
+ 72 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ cb2 2
+ cbra1 1
+Options: extended utf
+No first char
+No need char
+Subject length lower bound = 2
+No set of starting bytes
+
+<!testsaved32BE-2
+Compiled pattern loaded from testsaved32BE-2
+Study data loaded from testsaved32BE-2
+------------------------------------------------------------------
+ 0 70 Bra
+ 2 33 CBra 1
+ 5 [Za\x{400}-\x{10ffff}]{4,}
+ 23 [\x{f123}\x{10039}\x{20000}-\x{21234}]?
+ 35 19 Alt
+ 37 [A-Cx-z\x{100000}-\x{1000a7}\x{101234}]
+ 54 52 Ket
+ 56 12 CBra 2
+ 59 [\x00-`b-y{-\xff] (neg)
+ 68 12 Ket
+ 70 70 Ket
+ 72 End
+------------------------------------------------------------------
+Capturing subpattern count = 2
+Named capturing subpatterns:
+ cb2 2
+ cbra1 1
+Options: extended utf
+No first char
+No need char
+Subject length lower bound = 2
+No set of starting bytes
+
+/-- End of testinput22 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput23 b/ext/pcre/pcrelib/testdata/testoutput23
new file mode 100644
index 0000000000..6f5384c34e
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput23
@@ -0,0 +1,46 @@
+/-- Tests for the 16-bit library only */
+
+< forbid 8W
+
+/-- Check maximum non-UTF character size --/
+
+/\x{ffff}/
+ A\x{ffff}B
+ 0: \x{ffff}
+
+/\x{10000}/
+Failed: character value in \x{} or \o{} is too large at offset 8
+
+/\o{20000}/
+
+/-- Check character ranges --/
+
+/[\H]/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0a-\x1f!-\x9f\x{a1}-\x{167f}\x{1681}-\x{180d}\x{180f}-\x{1fff}\x{200b}-\x{202e}\x{2030}-\x{205e}\x{2060}-\x{2fff}\x{3001}-\x{ffff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/[\V]/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x00-\x09\x0e-\x84\x{86}-\x{2027}\x{202a}-\x{ffff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/-- End of testinput23 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput24 b/ext/pcre/pcrelib/testdata/testoutput24
new file mode 100644
index 0000000000..0714a0fe15
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput24
@@ -0,0 +1,13 @@
+/-- Tests for the 16-bit library with UTF-16 support only */
+
+< forbid W
+
+/bad/8
+ \x{d800}
+Error -10 (bad UTF-16 string) offset=0 reason=1
+
+/short/8
+ \P\P\x{d800}
+Error -25 (short UTF-16 string) offset=0 reason=1
+
+/-- End of testinput24 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput25 b/ext/pcre/pcrelib/testdata/testoutput25
new file mode 100644
index 0000000000..7ad3378368
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput25
@@ -0,0 +1,93 @@
+/-- Tests for the 32-bit library only */
+
+< forbid 8w
+
+/-- Check maximum character size --/
+
+/\x{110000}/
+
+/\x{7fffffff}/
+
+/\x{80000000}/
+
+/\x{ffffffff}/
+
+/\x{100000000}/
+Failed: character value in \x{} or \o{} is too large at offset 12
+
+/\o{17777777777}/
+
+/\o{20000000000}/
+
+/\o{37777777777}/
+
+/\o{40000000000}/
+Failed: character value in \x{} or \o{} is too large at offset 14
+
+/\x{7fffffff}\x{7fffffff}/I
+Capturing subpattern count = 0
+No options
+First char = \x{7fffffff}
+Need char = \x{7fffffff}
+
+/\x{80000000}\x{80000000}/I
+Capturing subpattern count = 0
+No options
+First char = \x{80000000}
+Need char = \x{80000000}
+
+/\x{ffffffff}\x{ffffffff}/I
+Capturing subpattern count = 0
+No options
+First char = \x{ffffffff}
+Need char = \x{ffffffff}
+
+/-- Non-UTF characters --/
+
+/\C{2,3}/
+ \x{400000}\x{400001}\x{400002}\x{400003}
+ 0: \x{400000}\x{400001}\x{400002}
+
+/\x{400000}\x{800000}/iDZ
+------------------------------------------------------------------
+ Bra
+ /i \x{400000}\x{800000}
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+Options: caseless
+First char = \x{400000}
+Need char = \x{800000}
+
+/-- Check character ranges --/
+
+/[\H]/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x00-\x08\x0a-\x1f!-\x9f\x{a1}-\x{167f}\x{1681}-\x{180d}\x{180f}-\x{1fff}\x{200b}-\x{202e}\x{2030}-\x{205e}\x{2060}-\x{2fff}\x{3001}-\x{ffffffff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/[\V]/BZSI
+------------------------------------------------------------------
+ Bra
+ [\x00-\x09\x0e-\x84\x{86}-\x{2027}\x{202a}-\x{ffffffff}]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+No set of starting bytes
+
+/-- End of testinput25 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput26 b/ext/pcre/pcrelib/testdata/testoutput26
new file mode 100644
index 0000000000..28f8d42a5e
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutput26
@@ -0,0 +1,17 @@
+/-- Tests for the 32-bit library with UTF-32 support only */
+
+< forbid W
+
+/-- Non-UTF characters --/
+
+/\x{110000}/8
+Failed: character value in \x{} or \o{} is too large at offset 9
+
+/\o{4200000}/8
+Failed: character value in \x{} or \o{} is too large at offset 10
+
+/\C/8
+ \x{110000}
+Error -10 (bad UTF-32 string) offset=0 reason=3
+
+/-- End of testinput26 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput3 b/ext/pcre/pcrelib/testdata/testoutput3
index 7b0a3e926e..12ffc9911b 100644
--- a/ext/pcre/pcrelib/testdata/testoutput3
+++ b/ext/pcre/pcrelib/testdata/testoutput3
@@ -1,6 +1,8 @@
/-- This set of tests checks local-specific features, using the fr_FR locale.
It is not Perl-compatible. There is different version called wintestinput3
f or use on Windows, where the locale is called "french". --/
+
+< forbid 8W
/^[\w]+/
*** Failers
diff --git a/ext/pcre/pcrelib/testdata/testoutput4 b/ext/pcre/pcrelib/testdata/testoutput4
index 2082721c56..0dbec4ecca 100644
--- a/ext/pcre/pcrelib/testdata/testoutput4
+++ b/ext/pcre/pcrelib/testdata/testoutput4
@@ -1,6 +1,8 @@
/-- This set of tests is for UTF support, excluding Unicode properties. It is
compatible with all versions of Perl >= 5.10 and both the 8-bit and 16-bit
PCRE libraries. --/
+
+< forbid 9?=ABCDEFfGILMNPTUWXZ<
/a.b/8
acb
@@ -1091,4 +1093,174 @@ MK: a\x{1234}b
0: a
MK: a\x{a3}b
+/-- Noncharacters --/
+
+/./8
+ \x{fffe}
+ 0: \x{fffe}
+ \x{ffff}
+ 0: \x{ffff}
+ \x{1fffe}
+ 0: \x{1fffe}
+ \x{1ffff}
+ 0: \x{1ffff}
+ \x{2fffe}
+ 0: \x{2fffe}
+ \x{2ffff}
+ 0: \x{2ffff}
+ \x{3fffe}
+ 0: \x{3fffe}
+ \x{3ffff}
+ 0: \x{3ffff}
+ \x{4fffe}
+ 0: \x{4fffe}
+ \x{4ffff}
+ 0: \x{4ffff}
+ \x{5fffe}
+ 0: \x{5fffe}
+ \x{5ffff}
+ 0: \x{5ffff}
+ \x{6fffe}
+ 0: \x{6fffe}
+ \x{6ffff}
+ 0: \x{6ffff}
+ \x{7fffe}
+ 0: \x{7fffe}
+ \x{7ffff}
+ 0: \x{7ffff}
+ \x{8fffe}
+ 0: \x{8fffe}
+ \x{8ffff}
+ 0: \x{8ffff}
+ \x{9fffe}
+ 0: \x{9fffe}
+ \x{9ffff}
+ 0: \x{9ffff}
+ \x{afffe}
+ 0: \x{afffe}
+ \x{affff}
+ 0: \x{affff}
+ \x{bfffe}
+ 0: \x{bfffe}
+ \x{bffff}
+ 0: \x{bffff}
+ \x{cfffe}
+ 0: \x{cfffe}
+ \x{cffff}
+ 0: \x{cffff}
+ \x{dfffe}
+ 0: \x{dfffe}
+ \x{dffff}
+ 0: \x{dffff}
+ \x{efffe}
+ 0: \x{efffe}
+ \x{effff}
+ 0: \x{effff}
+ \x{ffffe}
+ 0: \x{ffffe}
+ \x{fffff}
+ 0: \x{fffff}
+ \x{10fffe}
+ 0: \x{10fffe}
+ \x{10ffff}
+ 0: \x{10ffff}
+ \x{fdd0}
+ 0: \x{fdd0}
+ \x{fdd1}
+ 0: \x{fdd1}
+ \x{fdd2}
+ 0: \x{fdd2}
+ \x{fdd3}
+ 0: \x{fdd3}
+ \x{fdd4}
+ 0: \x{fdd4}
+ \x{fdd5}
+ 0: \x{fdd5}
+ \x{fdd6}
+ 0: \x{fdd6}
+ \x{fdd7}
+ 0: \x{fdd7}
+ \x{fdd8}
+ 0: \x{fdd8}
+ \x{fdd9}
+ 0: \x{fdd9}
+ \x{fdda}
+ 0: \x{fdda}
+ \x{fddb}
+ 0: \x{fddb}
+ \x{fddc}
+ 0: \x{fddc}
+ \x{fddd}
+ 0: \x{fddd}
+ \x{fdde}
+ 0: \x{fdde}
+ \x{fddf}
+ 0: \x{fddf}
+ \x{fde0}
+ 0: \x{fde0}
+ \x{fde1}
+ 0: \x{fde1}
+ \x{fde2}
+ 0: \x{fde2}
+ \x{fde3}
+ 0: \x{fde3}
+ \x{fde4}
+ 0: \x{fde4}
+ \x{fde5}
+ 0: \x{fde5}
+ \x{fde6}
+ 0: \x{fde6}
+ \x{fde7}
+ 0: \x{fde7}
+ \x{fde8}
+ 0: \x{fde8}
+ \x{fde9}
+ 0: \x{fde9}
+ \x{fdea}
+ 0: \x{fdea}
+ \x{fdeb}
+ 0: \x{fdeb}
+ \x{fdec}
+ 0: \x{fdec}
+ \x{fded}
+ 0: \x{fded}
+ \x{fdee}
+ 0: \x{fdee}
+ \x{fdef}
+ 0: \x{fdef}
+
+/^\d*\w{4}/8
+ 1234
+ 0: 1234
+ 123
+No match
+
+/^[^b]*\w{4}/8
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/^[^b]*\w{4}/8i
+ aaaa
+ 0: aaaa
+ aaa
+No match
+
+/^\x{100}*.{4}/8
+ \x{100}\x{100}\x{100}\x{100}
+ 0: \x{100}\x{100}\x{100}\x{100}
+ \x{100}\x{100}\x{100}
+No match
+
+/^\x{100}*.{4}/8i
+ \x{100}\x{100}\x{100}\x{100}
+ 0: \x{100}\x{100}\x{100}\x{100}
+ \x{100}\x{100}\x{100}
+No match
+
+/^a+[a\x{200}]/8
+ aa
+ 0: aa
+
/-- End of testinput4 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput5 b/ext/pcre/pcrelib/testdata/testoutput5
index 0e840540c4..3fa581052e 100644
--- a/ext/pcre/pcrelib/testdata/testoutput5
+++ b/ext/pcre/pcrelib/testdata/testoutput5
@@ -1,26 +1,47 @@
/-- This set of tests checks the API, internals, and non-Perl stuff for UTF
support, excluding Unicode properties. However, tests that give different
results in 8-bit and 16-bit modes are excluded (see tests 16 and 17). --/
+
+< forbid W
/\x{110000}/8DZ
-Failed: character value in \x{...} sequence is too large at offset 9
+Failed: character value in \x{} or \o{} is too large at offset 9
+
+/\o{4200000}/8DZ
+Failed: character value in \x{} or \o{} is too large at offset 10
/\x{ffffffff}/8
-Failed: character value in \x{...} sequence is too large at offset 11
+Failed: character value in \x{} or \o{} is too large at offset 11
+
+/\o{37777777777}/8
+Failed: character value in \x{} or \o{} is too large at offset 14
/\x{100000000}/8
-Failed: character value in \x{...} sequence is too large at offset 12
+Failed: character value in \x{} or \o{} is too large at offset 12
+
+/\o{77777777777}/8
+Failed: character value in \x{} or \o{} is too large at offset 14
/\x{d800}/8
Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
+/\o{154000}/8
+Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 9
+
/\x{dfff}/8
Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
+/\o{157777}/8
+Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 9
+
/\x{d7ff}/8
+/\o{153777}/8
+
/\x{e000}/8
+/\o{170000}/8
+
/^\x{100}a\x{1234}/8
\x{100}a\x{1234}bcd
0: \x{100}a\x{1234}
@@ -146,11 +167,12 @@ No match
/\x{100}*/8DZ
------------------------------------------------------------------
Bra
- \x{100}*
+ \x{100}*+
Ket
End
------------------------------------------------------------------
Capturing subpattern count = 0
+May match empty string
Options: utf
No first char
No need char
@@ -159,7 +181,7 @@ No need char
------------------------------------------------------------------
Bra
a
- \x{100}*
+ \x{100}*+
Ket
End
------------------------------------------------------------------
@@ -172,7 +194,7 @@ No need char
------------------------------------------------------------------
Bra
ab
- \x{100}*
+ \x{100}*+
Ket
End
------------------------------------------------------------------
@@ -373,6 +395,7 @@ Need char = 'z'
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
Options: utf
No first char
No need char
@@ -404,6 +427,7 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
Options: utf
No first char
No need char
@@ -424,6 +448,7 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
Options: utf
No first char
No need char
@@ -455,6 +480,7 @@ No need char
End
------------------------------------------------------------------
Capturing subpattern count = 2
+May match empty string
Options: utf
No first char
No need char
@@ -768,7 +794,7 @@ No match
/[\h]{3,}/8BZ
------------------------------------------------------------------
Bra
- [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]{3,}
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}]{3,}+
Ket
End
------------------------------------------------------------------
@@ -1572,7 +1598,7 @@ Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
/[\h\x{e000}]+/8BZ
------------------------------------------------------------------
Bra
- [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}\x{e000}]+
+ [\x09 \xa0\x{1680}\x{180e}\x{2000}-\x{200a}\x{202f}\x{205f}\x{3000}\x{e000}]++
Ket
End
------------------------------------------------------------------
@@ -1594,7 +1620,7 @@ Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
/[\H\x{d7ff}]+/8BZ
------------------------------------------------------------------
Bra
- [\x00-\x08\x0a-\x1f!-\x9f\x{a1}-\x{167f}\x{1681}-\x{180d}\x{180f}-\x{1fff}\x{200b}-\x{202e}\x{2030}-\x{205e}\x{2060}-\x{2fff}\x{3001}-\x{10ffff}\x{d7ff}]+
+ [\x00-\x08\x0a-\x1f!-\x9f\x{a1}-\x{167f}\x{1681}-\x{180d}\x{180f}-\x{1fff}\x{200b}-\x{202e}\x{2030}-\x{205e}\x{2060}-\x{2fff}\x{3001}-\x{10ffff}\x{d7ff}]++
Ket
End
------------------------------------------------------------------
@@ -1616,7 +1642,7 @@ Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
/[\v\x{e000}]+/8BZ
------------------------------------------------------------------
Bra
- [\x0a-\x0d\x85\x{2028}-\x{2029}\x{e000}]+
+ [\x0a-\x0d\x85\x{2028}-\x{2029}\x{e000}]++
Ket
End
------------------------------------------------------------------
@@ -1634,7 +1660,7 @@ Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 7
/[\V\x{d7ff}]+/8BZ
------------------------------------------------------------------
Bra
- [\x00-\x09\x0e-\x84\x{86}-\x{2027}\x{202a}-\x{10ffff}\x{d7ff}]+
+ [\x00-\x09\x0e-\x84\x{86}-\x{2027}\x{202a}-\x{10ffff}\x{d7ff}]++
Ket
End
------------------------------------------------------------------
@@ -1808,20 +1834,18 @@ Partial match: \x{0d}\x{0d}
/i [^\x{8000}]*
/i [^\x{7fff}]{2}
/i [^\x{7fff}]{0,7}?
- Once
/i [^\x{fffff}]{5}
- /i [^\x{fffff}]?
- Ket
+ /i [^\x{fffff}]?+
Ket
End
------------------------------------------------------------------
/(?<=\x{1234}\x{1234})\bxy/I8
Capturing subpattern count = 0
+Max lookbehind = 2
Options: utf
First char = 'x'
Need char = 'y'
-Max lookbehind = 2
/(?<!^)ETA/8
ETA
@@ -1846,4 +1870,16 @@ No match
/\ud800/<JS>8
Failed: disallowed Unicode code point (>= 0xd800 && <= 0xdfff) at offset 5
+/^a+[a\x{200}]/8BZ
+------------------------------------------------------------------
+ Bra
+ ^
+ a+
+ [a\x{200}]
+ Ket
+ End
+------------------------------------------------------------------
+ aa
+ 0: aa
+
/-- End of testinput5 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput6 b/ext/pcre/pcrelib/testdata/testoutput6
index 0182746168..6c42fce1a5 100644
--- a/ext/pcre/pcrelib/testdata/testoutput6
+++ b/ext/pcre/pcrelib/testdata/testoutput6
@@ -1,5 +1,7 @@
/-- This set of tests is for Unicode property support. It is compatible with
Perl >= 5.15. --/
+
+< forbid 9?=ABCDEFfGILMNPTUXZ<
/^\pC\pL\pM\pN\pP\pS\pZ</8
\x7f\x{c0}\x{30f}\x{660}\x{66c}\x{f01}\x{1680}<
@@ -543,16 +545,6 @@ No match
abc
No match
-/\p{Lu}/8i
- A
- 0: A
- aZ
- 0: Z
- ** Failers
- 0: F
- abc
-No match
-
/\p{Ll}/8
a
0: a
@@ -727,6 +719,8 @@ No match
0: \x{6e9}
\x{060b}
0: \x{60b}
+ \x{061c}
+ 0: \x{61c}
** Failers
No match
X\x{06e9}
@@ -1310,7 +1304,7 @@ No match
/^>\s+/8W
>\x{20}\x{a0}\x{1680}\x{2028}\x{2029}\x{202f}\x{9}\x{b}
- 0: > \x{a0}\x{1680}\x{2028}\x{2029}\x{202f}\x{09}
+ 0: > \x{a0}\x{1680}\x{2028}\x{2029}\x{202f}\x{09}\x{0b}
/^>\pZ+/8W
>\x{20}\x{a0}\x{1680}\x{2028}\x{2029}\x{202f}\x{9}\x{b}
@@ -1338,15 +1332,15 @@ No match
/^[[:graph:]]*/8W
A\x{a1}\x{a0}
- 0: A
+ 0: A\x{a1}
/^[[:print:]]*/8W
A z\x{a0}\x{a1}
- 0: A z
+ 0: A z\x{a0}\x{a1}
/^[[:punct:]]*/8W
.+\x{a1}\x{a0}
- 0: .+
+ 0: .+\x{a1}
/\p{Zs}*?\R/
** Failers
@@ -1548,6 +1542,19 @@ No match
0: \x{1111}\x{ae4c}\x{1111}\x{ae4c}\x{1111}\x{ae4c}\x{1111}\x{ae4c}X
0+
+/\X*Z/8Y
+ A\x{300}
+No match
+
+/\X*(.)/8Y
+ A\x{1111}\x{ae4c}\x{1169}
+ 0: A\x{1111}
+ 1: \x{1111}
+
+/\X?abc/8Y
+\xff\x7f\x00\x00\x03\x00\x41\xcc\x80\x41\x{300}\x61\x62\x63\x00\>06\?
+ 0: A\x{300}abc
+
/-- --/
/\x{1e9e}+/8i
@@ -2134,4 +2141,308 @@ No match
\x{0053}\x{0073}\x{017f}
0: Ss\x{17f}
+/^\p{Any}*\d{4}/8
+ 1234
+ 0: 1234
+ 123
+No match
+
+/^\X*\w{4}/8
+ 1234
+ 0: 1234
+ 123
+No match
+
+/^A\s+Z/8W
+ A\x{2005}Z
+ 0: A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+ 0: A\x{85}\x{180e}\x{2005}Z
+
+/^A[\s]+Z/8W
+ A\x{2005}Z
+ 0: A\x{2005}Z
+ A\x{85}\x{180e}\x{2005}Z
+ 0: A\x{85}\x{180e}\x{2005}Z
+
+/^[[:graph:]]+$/8W
+ Letter:ABC
+ 0: Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ 0: Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ 0: Number:9\x{660}
+ Punctuation:\x{66a},;
+ 0: Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ 0: Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ 0: Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ 0: \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ 0: \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ 0: \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ 0: \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ 0: \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ 0: \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ 0: \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ 0: \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ 0: \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ 0: \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ ** Failers
+No match
+ \x{09}
+No match
+ \x{0a}
+No match
+ \x{1D}
+No match
+ \x{20}
+No match
+ \x{85}
+No match
+ \x{a0}
+No match
+ \x{61c}
+No match
+ \x{1680}
+No match
+ \x{180e}
+No match
+ \x{2028}
+No match
+ \x{2029}
+No match
+ \x{202f}
+No match
+ \x{2065}
+No match
+ \x{2066}
+No match
+ \x{2067}
+No match
+ \x{2068}
+No match
+ \x{2069}
+No match
+ \x{3000}
+No match
+ \x{e0002}
+No match
+ \x{e001f}
+No match
+ \x{e0080}
+No match
+
+/^[[:print:]]+$/8W
+ Space: \x{a0}
+ 0: Space: \x{a0}
+ \x{1680}\x{2000}\x{2001}\x{2002}\x{2003}\x{2004}\x{2005}
+ 0: \x{1680}\x{2000}\x{2001}\x{2002}\x{2003}\x{2004}\x{2005}
+ \x{2006}\x{2007}\x{2008}\x{2009}\x{200a}
+ 0: \x{2006}\x{2007}\x{2008}\x{2009}\x{200a}
+ \x{202f}\x{205f}
+ 0: \x{202f}\x{205f}
+ \x{3000}
+ 0: \x{3000}
+ Letter:ABC
+ 0: Letter:ABC
+ Mark:\x{300}\x{1d172}\x{1d17b}
+ 0: Mark:\x{300}\x{1d172}\x{1d17b}
+ Number:9\x{660}
+ 0: Number:9\x{660}
+ Punctuation:\x{66a},;
+ 0: Punctuation:\x{66a},;
+ Symbol:\x{6de}<>\x{fffc}
+ 0: Symbol:\x{6de}<>\x{fffc}
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ 0: Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+ \x{180e}
+ 0: \x{180e}
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ 0: \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ 0: \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+ \x{202f}
+ 0: \x{202f}
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ 0: \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ 0: \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+ \x{feff}
+ 0: \x{feff}
+ \x{fff9}\x{fffa}\x{fffb}
+ 0: \x{fff9}\x{fffa}\x{fffb}
+ \x{110bd}
+ 0: \x{110bd}
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ 0: \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+ \x{e0001}
+ 0: \x{e0001}
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ 0: \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+ ** Failers
+ 0: ** Failers
+ \x{09}
+No match
+ \x{1D}
+No match
+ \x{85}
+No match
+ \x{61c}
+No match
+ \x{2028}
+No match
+ \x{2029}
+No match
+ \x{2065}
+No match
+ \x{2066}
+No match
+ \x{2067}
+No match
+ \x{2068}
+No match
+ \x{2069}
+No match
+ \x{e0002}
+No match
+ \x{e001f}
+No match
+ \x{e0080}
+No match
+
+/^[[:punct:]]+$/8W
+ \$+<=>^`|~
+ 0: $+<=>^`|~
+ !\"#%&'()*,-./:;?@[\\]_{}
+ 0: !"#%&'()*,-./:;?@[\]_{}
+ \x{a1}\x{a7}
+ 0: \x{a1}\x{a7}
+ \x{37e}
+ 0: \x{37e}
+ ** Failers
+No match
+ abcde
+No match
+
+/^[[:^graph:]]+$/8W
+ \x{09}\x{0a}\x{1D}\x{20}\x{85}\x{a0}\x{61c}\x{1680}\x{180e}
+ 0: \x{09}\x{0a}\x{1d} \x{85}\x{a0}\x{61c}\x{1680}\x{180e}
+ \x{2028}\x{2029}\x{202f}\x{2065}\x{2066}\x{2067}\x{2068}\x{2069}
+ 0: \x{2028}\x{2029}\x{202f}\x{2065}\x{2066}\x{2067}\x{2068}\x{2069}
+ \x{3000}\x{e0002}\x{e001f}\x{e0080}
+ 0: \x{3000}\x{e0002}\x{e001f}\x{e0080}
+ ** Failers
+No match
+ Letter:ABC
+No match
+ Mark:\x{300}\x{1d172}\x{1d17b}
+No match
+ Number:9\x{660}
+No match
+ Punctuation:\x{66a},;
+No match
+ Symbol:\x{6de}<>\x{fffc}
+No match
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+No match
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+No match
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+No match
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+No match
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+No match
+ \x{feff}
+No match
+ \x{fff9}\x{fffa}\x{fffb}
+No match
+ \x{110bd}
+No match
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+No match
+ \x{e0001}
+No match
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+No match
+
+/^[[:^print:]]+$/8W
+ \x{09}\x{1D}\x{85}\x{61c}\x{2028}\x{2029}\x{2065}\x{2066}\x{2067}
+ 0: \x{09}\x{1d}\x{85}\x{61c}\x{2028}\x{2029}\x{2065}\x{2066}\x{2067}
+ \x{2068}\x{2069}\x{e0002}\x{e001f}\x{e0080}
+ 0: \x{2068}\x{2069}\x{e0002}\x{e001f}\x{e0080}
+ ** Failers
+No match
+ Space: \x{a0}
+No match
+ \x{1680}\x{2000}\x{2001}\x{2002}\x{2003}\x{2004}\x{2005}
+No match
+ \x{2006}\x{2007}\x{2008}\x{2009}\x{200a}
+No match
+ \x{202f}\x{205f}
+No match
+ \x{3000}
+No match
+ Letter:ABC
+No match
+ Mark:\x{300}\x{1d172}\x{1d17b}
+No match
+ Number:9\x{660}
+No match
+ Punctuation:\x{66a},;
+No match
+ Symbol:\x{6de}<>\x{fffc}
+No match
+ Cf-property:\x{ad}\x{600}\x{601}\x{602}\x{603}\x{604}\x{6dd}\x{70f}
+No match
+ \x{180e}
+No match
+ \x{200b}\x{200c}\x{200d}\x{200e}\x{200f}
+No match
+ \x{202a}\x{202b}\x{202c}\x{202d}\x{202e}
+No match
+ \x{202f}
+No match
+ \x{2060}\x{2061}\x{2062}\x{2063}\x{2064}
+No match
+ \x{206a}\x{206b}\x{206c}\x{206d}\x{206e}\x{206f}
+No match
+ \x{feff}
+No match
+ \x{fff9}\x{fffa}\x{fffb}
+No match
+ \x{110bd}
+No match
+ \x{1d173}\x{1d174}\x{1d175}\x{1d176}\x{1d177}\x{1d178}\x{1d179}\x{1d17a}
+No match
+ \x{e0001}
+No match
+ \x{e0020}\x{e0030}\x{e0040}\x{e0050}\x{e0060}\x{e0070}\x{e007f}
+No match
+
+/^[[:^punct:]]+$/8W
+ abcde
+ 0: abcde
+ ** Failers
+No match
+ \$+<=>^`|~
+No match
+ !\"#%&'()*,-./:;?@[\\]_{}
+No match
+ \x{a1}\x{a7}
+No match
+ \x{37e}
+No match
+
/-- End of testinput6 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput7 b/ext/pcre/pcrelib/testdata/testoutput7
index 4f8b7b9bf3..45ac72fd8d 100644
--- a/ext/pcre/pcrelib/testdata/testoutput7
+++ b/ext/pcre/pcrelib/testdata/testoutput7
@@ -78,7 +78,7 @@ No need char
/[\p{Nd}+-]+/8DZ
------------------------------------------------------------------
Bra
- [+\-\p{Nd}]+
+ [+\-\p{Nd}]++
Ket
End
------------------------------------------------------------------
@@ -270,6 +270,20 @@ No need char
End
------------------------------------------------------------------
+/^\p{Cf}/8
+ \x{180e}
+ 0: \x{180e}
+ \x{061c}
+ 0: \x{61c}
+ \x{2066}
+ 0: \x{2066}
+ \x{2067}
+ 0: \x{2067}
+ \x{2068}
+ 0: \x{2068}
+ \x{2069}
+ 0: \x{2069}
+
/^\p{Cs}/8
\?\x{dfff}
0: \x{dfff}
@@ -278,6 +292,22 @@ No match
\x{09f}
No match
+/^\p{Mn}/8
+ \x{1a1b}
+ 0: \x{1a1b}
+
+/^\p{Pe}/8
+ \x{2309}
+ 0: \x{2309}
+ \x{230b}
+ 0: \x{230b}
+
+/^\p{Ps}/8
+ \x{2308}
+ 0: \x{2308}
+ \x{230a}
+ 0: \x{230a}
+
/^\p{Sc}+/8
$\x{a2}\x{a3}\x{a4}\x{a5}\x{a6}
0: $\x{a2}\x{a3}\x{a4}\x{a5}
@@ -297,8 +327,6 @@ No match
0: \x{a0}
\x{1680}
0: \x{1680}
- \x{180e}
- 0: \x{180e}
\x{2000}
0: \x{2000}
\x{2001}
@@ -310,8 +338,9 @@ No match
\x{200d}
No match
-/-- These four are here rather than in test 6 because Perl has problems with
- the negative versions of the properties. --/
+/-- These are here rather than in test 6 because Perl has problems with
+ the negative versions of the properties and behaves has changed how
+ it behaves for caseless matching. --/
/\p{^Lu}/8i
1234
@@ -351,6 +380,16 @@ No match
\x{1d00}
No match
+/\p{Lu}/8i
+ A
+ 0: A
+ aZ
+ 0: Z
+ ** Failers
+ 0: F
+ abc
+No match
+
/[\x{c0}\x{391}]/8i
\x{c0}
0: \x{c0}
@@ -501,7 +540,7 @@ No match
/^>\p{Xsp}+/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
/^>\p{Xsp}+?/8
>\x{1680}\x{2028}\x{0b}
@@ -509,11 +548,11 @@ No match
/^>\p{Xsp}*/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
/^>\p{Xsp}{2,9}/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
/^>\p{Xsp}{2,9}?/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
@@ -525,7 +564,7 @@ No match
/^>[\p{Xsp}]+/8
> \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
- 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}
+ 0: > \x{09}\x{0a}\x{0c}\x{0d}\x{a0}\x{1680}\x{2028}\x{0b}
/^>\p{Xps}/8
>\x{1680}\x{2028}\x{0b}
@@ -820,7 +859,7 @@ No match
/[[:graph:]]/WBZ
------------------------------------------------------------------
Bra
- [!-~]
+ [[:graph:]]
Ket
End
------------------------------------------------------------------
@@ -828,7 +867,7 @@ No match
/[[:print:]]/WBZ
------------------------------------------------------------------
Bra
- [ -~]
+ [[:print:]]
Ket
End
------------------------------------------------------------------
@@ -836,7 +875,7 @@ No match
/[[:punct:]]/WBZ
------------------------------------------------------------------
Bra
- [!-/:-@[-`{-~]
+ [[:punct:]]
Ket
End
------------------------------------------------------------------
@@ -910,7 +949,7 @@ No match
/[[:^alpha:][:^cntrl:]]+/8WBZ
------------------------------------------------------------------
Bra
- [ -~\x80-\xff\P{L}]+
+ [ -~\x80-\xff\P{L}]++
Ket
End
------------------------------------------------------------------
@@ -922,7 +961,7 @@ No match
/[[:^cntrl:][:^alpha:]]+/8WBZ
------------------------------------------------------------------
Bra
- [ -~\x80-\xff\P{L}]+
+ [ -~\x80-\xff\P{L}]++
Ket
End
------------------------------------------------------------------
@@ -934,7 +973,7 @@ No match
/[[:alpha:]]+/8WBZ
------------------------------------------------------------------
Bra
- [\p{L}]+
+ [\p{L}]++
Ket
End
------------------------------------------------------------------
@@ -944,7 +983,7 @@ No match
/[[:^alpha:]\S]+/8WBZ
------------------------------------------------------------------
Bra
- [\P{L}\P{Xsp}]+
+ [\P{L}\P{Xsp}]++
Ket
End
------------------------------------------------------------------
@@ -956,7 +995,7 @@ No match
/[^\d]+/8WBZ
------------------------------------------------------------------
Bra
- [^\p{Nd}]+
+ [^\p{Nd}]++
Ket
End
------------------------------------------------------------------
@@ -1070,8 +1109,8 @@ No match
prop Nd
B+
prop N *+
- B+
- prop Nd *
+ B++
+ prop Nd *+
Ket
End
------------------------------------------------------------------
@@ -1347,7 +1386,7 @@ Need char = 'B' (caseless)
/[\x{3a3}]+/8iBZ
------------------------------------------------------------------
Bra
- clist 03a3 03c2 03c3 +
+ clist 03a3 03c2 03c3 ++
Ket
End
------------------------------------------------------------------
@@ -1355,7 +1394,7 @@ Need char = 'B' (caseless)
/[^\x{3a3}]+/8iBZ
------------------------------------------------------------------
Bra
- not clist 03a3 03c2 03c3 +
+ not clist 03a3 03c2 03c3 ++
Ket
End
------------------------------------------------------------------
@@ -1469,5 +1508,759 @@ No match
/is{2}t/8i
iskt
No match
+
+/-- This property is a PCRE special --/
+
+/^\p{Xuc}/8
+ $abc
+ 0: $
+ @abc
+ 0: @
+ `abc
+ 0: `
+ \x{1234}abc
+ 0: \x{1234}
+ ** Failers
+No match
+ abc
+No match
+
+/^\p{Xuc}+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}+?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}+?\*/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}*
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}++/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}{3,5}/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\p{Xuc}{3,5}?/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^[\p{Xuc}]/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^[\p{Xuc}]+/8
+ $@`\x{a0}\x{1234}\x{e000}**
+ 0: $@`\x{a0}\x{1234}\x{e000}
+ ** Failers
+No match
+ \x{9f}
+No match
+
+/^\P{Xuc}/8
+ abc
+ 0: a
+ ** Failers
+ 0: *
+ $abc
+No match
+ @abc
+No match
+ `abc
+No match
+ \x{1234}abc
+No match
+
+/^[\P{Xuc}]/8
+ abc
+ 0: a
+ ** Failers
+ 0: *
+ $abc
+No match
+ @abc
+No match
+ `abc
+No match
+ \x{1234}abc
+No match
+
+/-- Some auto-possessification tests --/
+
+/\pN+\z/BZ
+------------------------------------------------------------------
+ Bra
+ prop N ++
+ \z
+ Ket
+ End
+------------------------------------------------------------------
+
+/\PN+\z/BZ
+------------------------------------------------------------------
+ Bra
+ notprop N ++
+ \z
+ Ket
+ End
+------------------------------------------------------------------
+
+/\pN+/BZ
+------------------------------------------------------------------
+ Bra
+ prop N ++
+ Ket
+ End
+------------------------------------------------------------------
+
+/\PN+/BZ
+------------------------------------------------------------------
+ Bra
+ notprop N ++
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Any}+\p{Any} \p{Any}+\P{Any} \p{Any}+\p{L&} \p{Any}+\p{L} \p{Any}+\p{Lu} \p{Any}+\p{Han} \p{Any}+\p{Xan} \p{Any}+\p{Xsp} \p{Any}+\p{Xps} \p{Xwd}+\p{Any} \p{Any}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Any +
+ prop Any
+ prop Any +
+ notprop Any
+ prop Any +
+ prop L&
+ prop Any +
+ prop L
+ prop Any +
+ prop Lu
+ prop Any +
+ prop Han
+ prop Any +
+ prop Xan
+ prop Any +
+ prop Xsp
+ prop Any +
+ prop Xps
+ prop Xwd +
+ prop Any
+ prop Any +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{L&}+\p{Any} \p{L&}+\p{L&} \P{L&}+\p{L&} \p{L&}+\p{L} \p{L&}+\p{Lu} \p{L&}+\p{Han} \p{L&}+\p{Xan} \p{L&}+\P{Xan} \p{L&}+\p{Xsp} \p{L&}+\p{Xps} \p{Xwd}+\p{L&} \p{L&}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop L& +
+ prop Any
+ prop L& +
+ prop L&
+ notprop L& ++
+ prop L&
+ prop L& +
+ prop L
+ prop L& +
+ prop Lu
+ prop L& +
+ prop Han
+ prop L& +
+ prop Xan
+ prop L& ++
+ notprop Xan
+ prop L& ++
+ prop Xsp
+ prop L& ++
+ prop Xps
+ prop Xwd +
+ prop L&
+ prop L& +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{N}+\p{Any} \p{N}+\p{L&} \p{N}+\p{L} \p{N}+\P{L} \p{N}+\P{N} \p{N}+\p{Lu} \p{N}+\p{Han} \p{N}+\p{Xan} \p{N}+\p{Xsp} \p{N}+\p{Xps} \p{Xwd}+\p{N} \p{N}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop N +
+ prop Any
+ prop N +
+ prop L&
+ prop N ++
+ prop L
+ prop N +
+ notprop L
+ prop N ++
+ notprop N
+ prop N ++
+ prop Lu
+ prop N +
+ prop Han
+ prop N +
+ prop Xan
+ prop N ++
+ prop Xsp
+ prop N ++
+ prop Xps
+ prop Xwd +
+ prop N
+ prop N +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Lu}+\p{Any} \p{Lu}+\p{L&} \p{Lu}+\p{L} \p{Lu}+\p{Lu} \P{Lu}+\p{Lu} \p{Lu}+\p{Nd} \p{Lu}+\P{Nd} \p{Lu}+\p{Han} \p{Lu}+\p{Xan} \p{Lu}+\p{Xsp} \p{Lu}+\p{Xps} \p{Xwd}+\p{Lu} \p{Lu}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Lu +
+ prop Any
+ prop Lu +
+ prop L&
+ prop Lu +
+ prop L
+ prop Lu +
+ prop Lu
+ notprop Lu ++
+ prop Lu
+ prop Lu ++
+ prop Nd
+ prop Lu +
+ notprop Nd
+ prop Lu +
+ prop Han
+ prop Lu +
+ prop Xan
+ prop Lu ++
+ prop Xsp
+ prop Lu ++
+ prop Xps
+ prop Xwd +
+ prop Lu
+ prop Lu +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Han}+\p{Lu} \p{Han}+\p{L&} \p{Han}+\p{L} \p{Han}+\p{Lu} \p{Han}+\p{Arabic} \p{Arabic}+\p{Arabic} \p{Han}+\p{Xan} \p{Han}+\p{Xsp} \p{Han}+\p{Xps} \p{Xwd}+\p{Han} \p{Han}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Han +
+ prop Lu
+ prop Han +
+ prop L&
+ prop Han +
+ prop L
+ prop Han +
+ prop Lu
+ prop Han ++
+ prop Arabic
+ prop Arabic +
+ prop Arabic
+ prop Han +
+ prop Xan
+ prop Han +
+ prop Xsp
+ prop Han +
+ prop Xps
+ prop Xwd +
+ prop Han
+ prop Han +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xan}+\p{Any} \p{Xan}+\p{L&} \P{Xan}+\p{L&} \p{Xan}+\p{L} \p{Xan}+\p{Lu} \p{Xan}+\p{Han} \p{Xan}+\p{Xan} \p{Xan}+\P{Xan} \p{Xan}+\p{Xsp} \p{Xan}+\p{Xps} \p{Xwd}+\p{Xan} \p{Xan}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xan +
+ prop Any
+ prop Xan +
+ prop L&
+ notprop Xan ++
+ prop L&
+ prop Xan +
+ prop L
+ prop Xan +
+ prop Lu
+ prop Xan +
+ prop Han
+ prop Xan +
+ prop Xan
+ prop Xan ++
+ notprop Xan
+ prop Xan ++
+ prop Xsp
+ prop Xan ++
+ prop Xps
+ prop Xwd +
+ prop Xan
+ prop Xan +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xsp}+\p{Any} \p{Xsp}+\p{L&} \p{Xsp}+\p{L} \p{Xsp}+\p{Lu} \p{Xsp}+\p{Han} \p{Xsp}+\p{Xan} \p{Xsp}+\p{Xsp} \P{Xsp}+\p{Xsp} \p{Xsp}+\p{Xps} \p{Xwd}+\p{Xsp} \p{Xsp}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xsp +
+ prop Any
+ prop Xsp ++
+ prop L&
+ prop Xsp ++
+ prop L
+ prop Xsp ++
+ prop Lu
+ prop Xsp +
+ prop Han
+ prop Xsp ++
+ prop Xan
+ prop Xsp +
+ prop Xsp
+ notprop Xsp ++
+ prop Xsp
+ prop Xsp +
+ prop Xps
+ prop Xwd ++
+ prop Xsp
+ prop Xsp +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xwd}+\p{Any} \p{Xwd}+\p{L&} \p{Xwd}+\p{L} \p{Xwd}+\p{Lu} \p{Xwd}+\p{Han} \p{Xwd}+\p{Xan} \p{Xwd}+\p{Xsp} \p{Xwd}+\p{Xps} \p{Xwd}+\p{Xwd} \p{Xwd}+\P{Xwd} \p{Xwd}+\p{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xwd +
+ prop Any
+ prop Xwd +
+ prop L&
+ prop Xwd +
+ prop L
+ prop Xwd +
+ prop Lu
+ prop Xwd +
+ prop Han
+ prop Xwd +
+ prop Xan
+ prop Xwd ++
+ prop Xsp
+ prop Xwd ++
+ prop Xps
+ prop Xwd +
+ prop Xwd
+ prop Xwd ++
+ notprop Xwd
+ prop Xwd +
+ prop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xuc}+\p{Any} \p{Xuc}+\p{L&} \p{Xuc}+\p{L} \p{Xuc}+\p{Lu} \p{Xuc}+\p{Han} \p{Xuc}+\p{Xan} \p{Xuc}+\p{Xsp} \p{Xuc}+\p{Xps} \p{Xwd}+\p{Xuc} \p{Xuc}+\p{Xuc} \p{Xuc}+\P{Xuc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xuc +
+ prop Any
+ prop Xuc +
+ prop L&
+ prop Xuc +
+ prop L
+ prop Xuc +
+ prop Lu
+ prop Xuc +
+ prop Han
+ prop Xuc +
+ prop Xan
+ prop Xuc +
+ prop Xsp
+ prop Xuc +
+ prop Xps
+ prop Xwd +
+ prop Xuc
+ prop Xuc +
+ prop Xuc
+ prop Xuc ++
+ notprop Xuc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{N}+\p{Ll} \p{N}+\p{Nd} \p{N}+\P{Nd}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop N ++
+ prop Ll
+ prop N +
+ prop Nd
+ prop N +
+ notprop Nd
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xan}+\p{L} \p{Xan}+\p{N} \p{Xan}+\p{C} \p{Xan}+\P{L} \P{Xan}+\p{N} \p{Xan}+\P{C}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xan +
+ prop L
+ prop Xan +
+ prop N
+ prop Xan ++
+ prop C
+ prop Xan +
+ notprop L
+ notprop Xan ++
+ prop N
+ prop Xan +
+ notprop C
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{L}+\p{Xan} \p{N}+\p{Xan} \p{C}+\p{Xan} \P{L}+\p{Xan} \p{N}+\p{Xan} \P{C}+\p{Xan} \p{L}+\P{Xan}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop L +
+ prop Xan
+ prop N +
+ prop Xan
+ prop C ++
+ prop Xan
+ notprop L +
+ prop Xan
+ prop N +
+ prop Xan
+ notprop C +
+ prop Xan
+ prop L ++
+ notprop Xan
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xan}+\p{Lu} \p{Xan}+\p{Nd} \p{Xan}+\p{Cc} \p{Xan}+\P{Ll} \P{Xan}+\p{No} \p{Xan}+\P{Cf}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xan +
+ prop Lu
+ prop Xan +
+ prop Nd
+ prop Xan ++
+ prop Cc
+ prop Xan +
+ notprop Ll
+ notprop Xan ++
+ prop No
+ prop Xan +
+ notprop Cf
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Lu}+\p{Xan} \p{Nd}+\p{Xan} \p{Cs}+\p{Xan} \P{Lt}+\p{Xan} \p{Nl}+\p{Xan} \P{Cc}+\p{Xan} \p{Lt}+\P{Xan}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Lu +
+ prop Xan
+ prop Nd +
+ prop Xan
+ prop Cs ++
+ prop Xan
+ notprop Lt +
+ prop Xan
+ prop Nl +
+ prop Xan
+ notprop Cc +
+ prop Xan
+ prop Lt ++
+ notprop Xan
+ Ket
+ End
+------------------------------------------------------------------
+
+/\w+\p{P} \w+\p{Po} \w+\s \p{Xan}+\s \s+\p{Xan} \s+\w/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xwd +
+ prop P
+ prop Xwd +
+ prop Po
+ prop Xwd ++
+ prop Xsp
+ prop Xan ++
+ prop Xsp
+ prop Xsp ++
+ prop Xan
+ prop Xsp ++
+ prop Xwd
+ Ket
+ End
+------------------------------------------------------------------
+
+/\w+\P{P} \W+\p{Po} \w+\S \P{Xan}+\s \s+\P{Xan} \s+\W/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xwd +
+ notprop P
+ notprop Xwd +
+ prop Po
+ prop Xwd +
+ notprop Xsp
+ notprop Xan +
+ prop Xsp
+ prop Xsp +
+ notprop Xan
+ prop Xsp +
+ notprop Xwd
+ Ket
+ End
+------------------------------------------------------------------
+
+/\w+\p{Po} \w+\p{Pc} \W+\p{Po} \W+\p{Pc} \w+\P{Po} \w+\P{Pc}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xwd +
+ prop Po
+ prop Xwd ++
+ prop Pc
+ notprop Xwd +
+ prop Po
+ notprop Xwd +
+ prop Pc
+ prop Xwd +
+ notprop Po
+ prop Xwd +
+ notprop Pc
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Nl}+\p{Xan} \P{Nl}+\p{Xan} \p{Nl}+\P{Xan} \P{Nl}+\P{Xan}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Nl +
+ prop Xan
+ notprop Nl +
+ prop Xan
+ prop Nl ++
+ notprop Xan
+ notprop Nl +
+ notprop Xan
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xan}+\p{Nl} \P{Xan}+\p{Nl} \p{Xan}+\P{Nl} \P{Xan}+\P{Nl}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xan +
+ prop Nl
+ notprop Xan ++
+ prop Nl
+ prop Xan +
+ notprop Nl
+ notprop Xan +
+ notprop Nl
+ Ket
+ End
+------------------------------------------------------------------
+
+/\p{Xan}+\p{Nd} \P{Xan}+\p{Nd} \p{Xan}+\P{Nd} \P{Xan}+\P{Nd}/BWZx
+------------------------------------------------------------------
+ Bra
+ prop Xan +
+ prop Nd
+ notprop Xan ++
+ prop Nd
+ prop Xan +
+ notprop Nd
+ notprop Xan +
+ notprop Nd
+ Ket
+ End
+------------------------------------------------------------------
+
+/-- End auto-possessification tests --/
+
+/\w+/8CWBZ
+------------------------------------------------------------------
+ Bra
+ Callout 255 0 3
+ prop Xwd ++
+ Callout 255 3 0
+ Ket
+ End
+------------------------------------------------------------------
+ abcd
+--->abcd
+ +0 ^ \w+
+ +3 ^ ^
+ 0: abcd
+
+/[\p{N}]?+/BZO
+------------------------------------------------------------------
+ Bra
+ [\p{N}]?+
+ Ket
+ End
+------------------------------------------------------------------
+
+/[\p{L}ab]{2,3}+/BZO
+------------------------------------------------------------------
+ Bra
+ [ab\p{L}]{2,3}+
+ Ket
+ End
+------------------------------------------------------------------
+
+/\D+\X \d+\X \S+\X \s+\X \W+\X \w+\X \C+\X \R+\X \H+\X \h+\X \V+\X \v+\X a+\X \n+\X .+\X/BZx
+------------------------------------------------------------------
+ Bra
+ \D+
+ extuni
+ \d+
+ extuni
+ \S+
+ extuni
+ \s+
+ extuni
+ \W+
+ extuni
+ \w+
+ extuni
+ AllAny+
+ extuni
+ \R+
+ extuni
+ \H+
+ extuni
+ \h+
+ extuni
+ \V+
+ extuni
+ \v+
+ extuni
+ a+
+ extuni
+ \x0a+
+ extuni
+ Any+
+ extuni
+ Ket
+ End
+------------------------------------------------------------------
+
+/.+\X/BZxs
+------------------------------------------------------------------
+ Bra
+ AllAny+
+ extuni
+ Ket
+ End
+------------------------------------------------------------------
+
+/\X+$/BZxm
+------------------------------------------------------------------
+ Bra
+ extuni+
+ /m $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\X+\D \X+\d \X+\S \X+\s \X+\W \X+\w \X+. \X+\C \X+\R \X+\H \X+\h \X+\V \X+\v \X+\X \X+\Z \X+\z \X+$/BZx
+------------------------------------------------------------------
+ Bra
+ extuni+
+ \D
+ extuni+
+ \d
+ extuni+
+ \S
+ extuni+
+ \s
+ extuni+
+ \W
+ extuni+
+ \w
+ extuni+
+ Any
+ extuni+
+ AllAny
+ extuni+
+ \R
+ extuni+
+ \H
+ extuni+
+ \h
+ extuni+
+ \V
+ extuni+
+ \v
+ extuni+
+ extuni
+ extuni+
+ \Z
+ extuni++
+ \z
+ extuni+
+ $
+ Ket
+ End
+------------------------------------------------------------------
+
+/\d+\s{0,5}=\s*\S?=\w{0,4}\W*/8WBZ
+------------------------------------------------------------------
+ Bra
+ prop Nd ++
+ prop Xsp {0,5}+
+ =
+ prop Xsp *+
+ notprop Xsp ?
+ =
+ prop Xwd {0,4}+
+ notprop Xwd *+
+ Ket
+ End
+------------------------------------------------------------------
/-- End of testinput7 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput8 b/ext/pcre/pcrelib/testdata/testoutput8
index 73e0eae87b..bb68d3e645 100644
--- a/ext/pcre/pcrelib/testdata/testoutput8
+++ b/ext/pcre/pcrelib/testdata/testoutput8
@@ -1,5 +1,8 @@
-/-- This set of tests check the DFA matching functionality of pcre_dfa_exec().
- The -dfa flag must be used with pcretest when running it. --/
+/-- This set of tests check the DFA matching functionality of pcre_dfa_exec(),
+ excluding UTF and Unicode property support. The -dfa flag must be used with
+ pcretest when running it. --/
+
+< forbid 8W
/abc/
abc
@@ -25,7 +28,7 @@ No match
ab
No match
-/a*/
+/a*/O
a
0: a
1:
@@ -49,7 +52,7 @@ No match
16: a
17:
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -341,7 +344,7 @@ No match
axyzq
No match
-/[^a]+/
+/[^a]+/O
bac
0: b
bcdefax
@@ -359,7 +362,7 @@ No match
aaaaa
No match
-/[^a]*/
+/[^a]*/O
bac
0: b
1:
@@ -380,7 +383,7 @@ No match
aaaaa
0:
-/[^a]{3,5}/
+/[^a]{3,5}/O
xyz
0: xyz
awxyza
@@ -408,29 +411,18 @@ No match
/\d*/
1234b567
0: 1234
- 1: 123
- 2: 12
- 3: 1
- 4:
xyz
0:
/\D*/
a1234b567
0: a
- 1:
xyz
0: xyz
- 1: xy
- 2: x
- 3:
/\d+/
ab1234c56
0: 1234
- 1: 123
- 2: 12
- 3: 1
*** Failers
No match
xyz
@@ -439,19 +431,8 @@ No match
/\D+/
ab123c56
0: ab
- 1: a
*** Failers
0: *** Failers
- 1: *** Failer
- 2: *** Faile
- 3: *** Fail
- 4: *** Fai
- 5: *** Fa
- 6: *** F
- 7: ***
- 8: ***
- 9: **
-10: *
789
No match
@@ -478,9 +459,6 @@ No match
/a+/
aaaa
0: aaaa
- 1: aaa
- 2: aa
- 3: a
/^.*xyz/
xyz
@@ -886,9 +864,6 @@ No match
0:
aaabcd
0: aaa
- 1: aa
- 2: a
- 3:
xyz
0: xyz
1:
@@ -985,7 +960,7 @@ Partial match: abc
xyzfo\P
No match
foob\P\>2
-Partial match: foob
+Partial match at offset 3: foob
foobar...\R\P\>4
0: ar
xyzfo\P
@@ -1577,18 +1552,6 @@ No match
/^[.^$|()*+?{,}]+/
.^\$(*+)|{?,?}
0: .^$(*+)|{?,?}
- 1: .^$(*+)|{?,?
- 2: .^$(*+)|{?,
- 3: .^$(*+)|{?
- 4: .^$(*+)|{
- 5: .^$(*+)|
- 6: .^$(*+)
- 7: .^$(*+
- 8: .^$(*
- 9: .^$(
-10: .^$
-11: .^
-12: .
/^a*\w/
z
@@ -1744,38 +1707,16 @@ No match
/foo(?!bar)(.*)/
foobar is foolish see?
0: foolish see?
- 1: foolish see
- 2: foolish se
- 3: foolish s
- 4: foolish
- 5: foolish
- 6: foolis
- 7: fooli
- 8: fool
- 9: foo
/(?:(?!foo)...|^.{0,2})bar(.*)/
foobar crowbar etc
0: rowbar etc
- 1: rowbar et
- 2: rowbar e
- 3: rowbar
- 4: rowbar
barrel
0: barrel
- 1: barre
- 2: barr
- 3: bar
2barrel
0: 2barrel
- 1: 2barre
- 2: 2barr
- 3: 2bar
A barrel
0: A barrel
- 1: A barre
- 2: A barr
- 3: A bar
/^(\D*)(?=\d)(?!123)/
abc456
@@ -1820,7 +1761,7 @@ No match
the abc
No match
-/^[ab]{1,3}(ab*|b)/
+/^[ab]{1,3}(ab*|b)/O
aabbbbb
0: aabbbbb
1: aabbbb
@@ -1829,7 +1770,7 @@ No match
4: aab
5: aa
-/^[ab]{1,3}?(ab*|b)/
+/^[ab]{1,3}?(ab*|b)/O
aabbbbb
0: aabbbbb
1: aabbbb
@@ -1838,7 +1779,7 @@ No match
4: aab
5: aa
-/^[ab]{1,3}?(ab*?|b)/
+/^[ab]{1,3}?(ab*?|b)/O
aabbbbb
0: aabbbbb
1: aabbbb
@@ -1847,7 +1788,7 @@ No match
4: aab
5: aa
-/^[ab]{1,3}(ab*?|b)/
+/^[ab]{1,3}(ab*?|b)/O
aabbbbb
0: aabbbbb
1: aabbbb
@@ -2705,10 +2646,6 @@ No match
/\0*/
\0\0\0\0
0: \x00\x00\x00\x00
- 1: \x00\x00\x00
- 2: \x00\x00
- 3: \x00
- 4:
/A\x0{2,3}Z/
The A\x0\x0Z
@@ -2760,56 +2697,14 @@ No match
/([^.]*)\.([^:]*):[T ]+(.*)/
track1.title:TBlah blah blah
0: track1.title:TBlah blah blah
- 1: track1.title:TBlah blah bla
- 2: track1.title:TBlah blah bl
- 3: track1.title:TBlah blah b
- 4: track1.title:TBlah blah
- 5: track1.title:TBlah blah
- 6: track1.title:TBlah bla
- 7: track1.title:TBlah bl
- 8: track1.title:TBlah b
- 9: track1.title:TBlah
-10: track1.title:TBlah
-11: track1.title:TBla
-12: track1.title:TBl
-13: track1.title:TB
-14: track1.title:T
/([^.]*)\.([^:]*):[T ]+(.*)/i
track1.title:TBlah blah blah
0: track1.title:TBlah blah blah
- 1: track1.title:TBlah blah bla
- 2: track1.title:TBlah blah bl
- 3: track1.title:TBlah blah b
- 4: track1.title:TBlah blah
- 5: track1.title:TBlah blah
- 6: track1.title:TBlah bla
- 7: track1.title:TBlah bl
- 8: track1.title:TBlah b
- 9: track1.title:TBlah
-10: track1.title:TBlah
-11: track1.title:TBla
-12: track1.title:TBl
-13: track1.title:TB
-14: track1.title:T
/([^.]*)\.([^:]*):[t ]+(.*)/i
track1.title:TBlah blah blah
0: track1.title:TBlah blah blah
- 1: track1.title:TBlah blah bla
- 2: track1.title:TBlah blah bl
- 3: track1.title:TBlah blah b
- 4: track1.title:TBlah blah
- 5: track1.title:TBlah blah
- 6: track1.title:TBlah bla
- 7: track1.title:TBlah bl
- 8: track1.title:TBlah b
- 9: track1.title:TBlah
-10: track1.title:TBlah
-11: track1.title:TBla
-12: track1.title:TBl
-13: track1.title:TB
-14: track1.title:T
/^[W-c]+$/
WXY_^abc
@@ -2882,13 +2777,10 @@ No match
0: b
c::b
0: ::
- 1: :
/[-az]+/
az-
0: az-
- 1: az
- 2: a
*** Failers
0: a
b
@@ -2897,8 +2789,6 @@ No match
/[az-]+/
za-
0: za-
- 1: za
- 2: z
*** Failers
0: a
b
@@ -2907,8 +2797,6 @@ No match
/[a\-z]+/
a-z
0: a-z
- 1: a-
- 2: a
*** Failers
0: a
b
@@ -2917,20 +2805,10 @@ No match
/[a-z]+/
abcdxyz
0: abcdxyz
- 1: abcdxy
- 2: abcdx
- 3: abcd
- 4: abc
- 5: ab
- 6: a
/[\d-]+/
12-34
0: 12-34
- 1: 12-3
- 2: 12-
- 3: 12
- 4: 1
*** Failers
No match
aaa
@@ -2939,11 +2817,6 @@ No match
/[\d-z]+/
12-34z
0: 12-34z
- 1: 12-34
- 2: 12-3
- 3: 12-
- 4: 12
- 5: 1
*** Failers
No match
aaa
@@ -3027,18 +2900,22 @@ No match
abc\100\60
0: abc@0
-/abc\81/
- abc\081
- 0: abc\x0081
- abc\0\x38\x31
- 0: abc\x0081
-
-/abc\91/
- abc\091
- 0: abc\x0091
- abc\0\x39\x31
- 0: abc\x0091
-
+/^A\8B\9C$/
+ A8B9C
+ 0: A8B9C
+ *** Failers
+No match
+ A\08B\09C
+No match
+
+/^[A\8B\9C]+$/
+ A8B9C
+ 0: A8B9C
+ *** Failers
+No match
+ A8B9C\x00
+No match
+
/(a)(b)(c)(d)(e)(f)(g)(h)(i)(j)(k)\12\123/
abcdefghijk\12S
0: abcdefghijk\x0aS
@@ -3077,16 +2954,13 @@ No match
1: baNOTccc
2: baNOTcc
3: baNOTc
- 4: baNOT
baNOTcccd
0: baNOTccc
1: baNOTcc
2: baNOTc
- 3: baNOT
baNOTccd
0: baNOTcc
1: baNOTc
- 2: baNOT
bacccd
0: baccc
*** Failers
@@ -3096,7 +2970,6 @@ No match
3: *** Fail
4: *** Fai
5: *** Fa
- 6: *** F
anything
No match
b\bc
@@ -3115,23 +2988,14 @@ No match
/[^a]+/
AAAaAbc
0: AAA
- 1: AA
- 2: A
/[^a]+/i
AAAaAbc
0: bc
- 1: b
/[^a]+/
bbb\nccc
0: bbb\x0accc
- 1: bbb\x0acc
- 2: bbb\x0ac
- 3: bbb\x0a
- 4: bbb
- 5: bb
- 6: b
/[^k]$/
abc
@@ -3208,20 +3072,8 @@ No match
/(\.\d\d[1-9]?)\d+/
1.230003938
0: .230003938
- 1: .23000393
- 2: .2300039
- 3: .230003
- 4: .23000
- 5: .2300
- 6: .230
1.875000282
0: .875000282
- 1: .87500028
- 2: .8750002
- 3: .875000
- 4: .87500
- 5: .8750
- 6: .875
1.235
0: .235
@@ -3243,10 +3095,6 @@ No match
/\b(foo)\s+(\w+)/i
Food is on the foo table
0: foo table
- 1: foo tabl
- 2: foo tab
- 3: foo ta
- 4: foo t
/foo(.*)bar/
The food is under the bar in the barn.
@@ -3258,9 +3106,9 @@ No match
0: food is under the bar in the bar
1: food is under the bar
-/(.*)(\d*)/
+/(.*)(\d*)/O
I have 2 numbers: 53147
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: I have 2 numbers: 53147
1: I have 2 numbers: 5314
2: I have 2 numbers: 531
@@ -3287,15 +3135,11 @@ Matched, but too many subsidiary matches
/(.*)(\d+)/
I have 2 numbers: 53147
0: I have 2 numbers: 53147
- 1: I have 2 numbers: 5314
- 2: I have 2 numbers: 531
- 3: I have 2 numbers: 53
- 4: I have 2 numbers: 5
- 5: I have 2
+ 1: I have 2
-/(.*?)(\d*)/
+/(.*?)(\d*)/O
I have 2 numbers: 53147
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: I have 2 numbers: 53147
1: I have 2 numbers: 5314
2: I have 2 numbers: 531
@@ -3322,11 +3166,7 @@ Matched, but too many subsidiary matches
/(.*?)(\d+)/
I have 2 numbers: 53147
0: I have 2 numbers: 53147
- 1: I have 2 numbers: 5314
- 2: I have 2 numbers: 531
- 3: I have 2 numbers: 53
- 4: I have 2 numbers: 5
- 5: I have 2
+ 1: I have 2
/(.*)(\d+)$/
I have 2 numbers: 53147
@@ -3738,13 +3578,8 @@ No match
0: a
ab
0: ab
- 1: a
abbbb
0: abbbb
- 1: abbb
- 2: abb
- 3: ab
- 4: a
*** Failers
0: a
bbbbb
@@ -3930,19 +3765,8 @@ No match
/(?>(\.\d\d[1-9]?))\d+/
1.230003938
0: .230003938
- 1: .23000393
- 2: .2300039
- 3: .230003
- 4: .23000
- 5: .2300
- 6: .230
1.875000282
0: .875000282
- 1: .87500028
- 2: .8750002
- 3: .875000
- 4: .87500
- 5: .8750
*** Failers
No match
1.235
@@ -4561,7 +4385,6 @@ No match
/.{3,4}/
abbbbc
0: abbb
- 1: abb
/ab{0,}bc/
abbbbc
@@ -4929,9 +4752,6 @@ No match
/[^ab]*/
cde
0: cde
- 1: cd
- 2: c
- 3:
/abc/
*** Failers
@@ -4966,7 +4786,6 @@ No match
/ab*/
xabyabbbz
0: ab
- 1: a
xayabbbz
0: a
@@ -4995,8 +4814,7 @@ No match
/a([bc]*)c*/
abc
0: abc
- 1: ab
- 2: a
+ 1: a
/a([bc]*)(c*d)/
abcd
@@ -5033,10 +4851,6 @@ No match
/[a-zA-Z_][a-zA-Z0-9_]*/
alpha
0: alpha
- 1: alph
- 2: alp
- 3: al
- 4: a
/^a(bc+|b[eh])g|.h$/
abh
@@ -5079,8 +4893,6 @@ No match
/(.*)c(.*)/
abcde
0: abcde
- 1: abcd
- 2: abc
/\((.*), (.*)\)/
(a, b)
@@ -5395,9 +5207,6 @@ No match
/[^ab]*/i
CDE
0: CDE
- 1: CD
- 2: C
- 3:
/abc/i
@@ -5427,7 +5236,6 @@ No match
/ab*/i
XABYABBBZ
0: AB
- 1: A
XAYABBBZ
0: A
@@ -5458,8 +5266,7 @@ No match
/a([bc]*)c*/i
ABC
0: ABC
- 1: AB
- 2: A
+ 1: A
/a([bc]*)(c*d)/i
ABCD
@@ -5490,10 +5297,6 @@ No match
/[a-zA-Z_][a-zA-Z0-9_]*/i
ALPHA
0: ALPHA
- 1: ALPH
- 2: ALP
- 3: AL
- 4: A
/^a(bc+|b[eh])g|.h$/i
ABH
@@ -5546,8 +5349,6 @@ No match
/(.*)c(.*)/i
ABCDE
0: ABCDE
- 1: ABCD
- 2: ABC
/\((.*), (.*)\)/i
(A, B)
@@ -6052,17 +5853,14 @@ No match
/([[:]+)/
a:[b]:
0: :[
- 1: :
/([[=]+)/
a=[b]=
0: =[
- 1: =
/([[.]+)/
a.[b].
0: .[
- 1: .
/((?>a+)b)/
aaab
@@ -6196,26 +5994,12 @@ No match
/a*/g
abbab
0: a
- 1:
0:
0:
0: a
- 1:
0:
0:
-/^[a-\d]/
- abcde
- 0: a
- -things
- 0: -
- 0digit
- 0: 0
- *** Failers
-No match
- bcdef
-No match
-
/^[\d-a]/
abcde
0: a
@@ -6231,36 +6015,22 @@ No match
/[[:space:]]+/
> \x09\x0a\x0c\x0d\x0b<
0: \x09\x0a\x0c\x0d\x0b
- 1: \x09\x0a\x0c\x0d
- 2: \x09\x0a\x0c
- 3: \x09\x0a
- 4: \x09
- 5:
/[[:blank:]]+/
> \x09\x0a\x0c\x0d\x0b<
0: \x09
- 1:
/[\s]+/
> \x09\x0a\x0c\x0d\x0b<
- 0: \x09\x0a\x0c\x0d
- 1: \x09\x0a\x0c
- 2: \x09\x0a
- 3: \x09
- 4:
+ 0: \x09\x0a\x0c\x0d\x0b
/\s+/
> \x09\x0a\x0c\x0d\x0b<
- 0: \x09\x0a\x0c\x0d
- 1: \x09\x0a\x0c
- 2: \x09\x0a
- 3: \x09
- 4:
+ 0: \x09\x0a\x0c\x0d\x0b
/a b/x
ab
-No match
+ 0: ab
/(?!\A)x/m
a\nxb\n
@@ -6563,8 +6333,6 @@ Partial match: 123
/Content-Type\x3A[^\r\n]{6,}/
Content-Type:xxxxxyyy
0: Content-Type:xxxxxyyy
- 1: Content-Type:xxxxxyy
- 2: Content-Type:xxxxxy
/Content-Type\x3A[^\r\n]{6,}z/
Content-Type:xxxxxyyyz
@@ -6661,66 +6429,22 @@ No match
/.*/<lf>
abc\ndef
0: abc
- 1: ab
- 2: a
- 3:
abc\rdef
0: abc\x0ddef
- 1: abc\x0dde
- 2: abc\x0dd
- 3: abc\x0d
- 4: abc
- 5: ab
- 6: a
- 7:
abc\r\ndef
0: abc\x0d
- 1: abc
- 2: ab
- 3: a
- 4:
\<cr>abc\ndef
0: abc\x0adef
- 1: abc\x0ade
- 2: abc\x0ad
- 3: abc\x0a
- 4: abc
- 5: ab
- 6: a
- 7:
\<cr>abc\rdef
0: abc
- 1: ab
- 2: a
- 3:
\<cr>abc\r\ndef
0: abc
- 1: ab
- 2: a
- 3:
\<crlf>abc\ndef
0: abc\x0adef
- 1: abc\x0ade
- 2: abc\x0ad
- 3: abc\x0a
- 4: abc
- 5: ab
- 6: a
- 7:
\<crlf>abc\rdef
0: abc\x0ddef
- 1: abc\x0dde
- 2: abc\x0dd
- 3: abc\x0d
- 4: abc
- 5: ab
- 6: a
- 7:
\<crlf>abc\r\ndef
0: abc
- 1: ab
- 2: a
- 3:
/\w+(.)(.)?def/s
abc\ndef
@@ -7033,10 +6757,8 @@ No match
/\H*\h+\V?\v{3,4}/
\x09\x20\xa0X\x0a\x0b\x0c\x0d\x0a
0: \x09 \xa0X\x0a\x0b\x0c\x0d
- 1: \x09 \xa0X\x0a\x0b\x0c
\x09\x20\xa0\x0a\x0b\x0c\x0d\x0a
0: \x09 \xa0\x0a\x0b\x0c\x0d
- 1: \x09 \xa0\x0a\x0b\x0c
\x09\x20\xa0\x0a\x0b\x0c
0: \x09 \xa0\x0a\x0b\x0c
** Failers
@@ -7047,7 +6769,6 @@ No match
/\H{3,4}/
XY ABCDE
0: ABCD
- 1: ABC
XY PQR ST
0: PQR
@@ -7466,17 +7187,17 @@ Error -16 (item unsupported for DFA matching)
xyzabc123pqr
0: 123
xyzabc12\P
-Partial match: abc12
+Partial match at offset 6: abc12
xyzabc12\P\P
-Partial match: abc12
+Partial match at offset 6: abc12
/\babc\b/
+++abc+++
0: abc
+++ab\P
-Partial match: +ab
+Partial match at offset 3: +ab
+++ab\P\P
-Partial match: +ab
+Partial match at offset 3: +ab
/(?=C)/g+
ABCDECBA
@@ -7531,15 +7252,11 @@ No match
xxxxabcd\P
0: abcd
0+
- 1: abc
xxxxabcd\P\P
Partial match: abcd
dddxxx\R
0: ddd
0+ xxx
- 1: dd
- 2: d
- 3:
xxxxabcd\P\P
Partial match: abcd
xxx\R
@@ -7549,27 +7266,22 @@ Partial match: abcd
/abcd*/i
xxxxabcd\P
0: abcd
- 1: abc
xxxxabcd\P\P
Partial match: abcd
XXXXABCD\P
0: ABCD
- 1: ABC
XXXXABCD\P\P
Partial match: ABCD
/abc\d*/
xxxxabc1\P
0: abc1
- 1: abc
xxxxabc1\P\P
Partial match: abc1
/abc[de]*/
xxxxabcde\P
0: abcde
- 1: abcd
- 2: abc
xxxxabcde\P\P
Partial match: abcde
@@ -7625,7 +7337,7 @@ Error -16 (item unsupported for DFA matching)
/(?<=abc)def/
abc\P\P
-Partial match: abc
+Partial match at offset 3: abc
/abc$/
abc
@@ -7684,11 +7396,8 @@ Partial match: abc
/.+/
abc\>0
0: abc
- 1: ab
- 2: a
abc\>1
0: bc
- 1: b
abc\>2
0: c
abc\>3
@@ -7811,10 +7520,6 @@ No match
/^(?!a){0}\w+/
aaaaa
0: aaaaa
- 1: aaaa
- 2: aaa
- 3: aa
- 4: a
/(?<=(abc))?xyz/
abcxyz
@@ -7846,9 +7551,9 @@ Error -17 (backreference condition or recursion test not supported for DFA match
aaaabcde
Error -26 (nested recursion at the same subject position)
-/(a+)/
+/(a+)/O
\O6aaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaa
1: aaa
2: aa
@@ -7971,7 +7676,6 @@ Partial match: \x0d
Partial match: \x0d\x0d
\r\r\r\P
0: \x0d\x0d\x0d
- 1: \x0d\x0d
\r\r\r\P\P
Partial match: \x0d\x0d\x0d
@@ -8016,4 +7720,61 @@ Error -30 (invalid data in workspace for DFA restart)
0: xx\xa0xxxxxabcd
1: xx\xa0xxxxxabc
+/abcd/
+ abcd\O0
+Matched, but offsets vector is too small to show all matches
+
+/-- These tests show up auto-possessification --/
+
+/[ab]*/
+ aaaa
+ 0: aaaa
+
+/[ab]*?/
+ aaaa
+ 0: aaaa
+ 1: aaa
+ 2: aa
+ 3: a
+ 4:
+
+/[ab]?/
+ aaaa
+ 0: a
+
+/[ab]??/
+ aaaa
+ 0: a
+ 1:
+
+/[ab]+/
+ aaaa
+ 0: aaaa
+
+/[ab]+?/
+ aaaa
+ 0: aaaa
+ 1: aaa
+ 2: aa
+ 3: a
+
+/[ab]{2,3}/
+ aaaa
+ 0: aaa
+
+/[ab]{2,3}?/
+ aaaa
+ 0: aaa
+ 1: aa
+
+/[ab]{2,}/
+ aaaa
+ 0: aaaa
+
+/[ab]{2,}?/
+ aaaa
+ 0: aaaa
+ 1: aaa
+ 2: aa
+
/-- End of testinput8 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutput9 b/ext/pcre/pcrelib/testdata/testoutput9
index 95cd618dc2..efbbf18010 100644
--- a/ext/pcre/pcrelib/testdata/testoutput9
+++ b/ext/pcre/pcrelib/testdata/testoutput9
@@ -1,6 +1,8 @@
/-- This set of tests checks UTF-8 support with the DFA matching functionality
- of pcre_dfa_exec(). The -dfa flag must be used with pcretest when running
- it. --/
+ of pcre_dfa_exec(), excluding Unicode property support. The -dfa flag must
+ be used with pcretest when running it. --/
+
+< forbid W
/\x{100}ab/8
\x{100}ab
@@ -313,13 +315,9 @@ No match
/[^a]+/8g
bcd
0: bcd
- 1: bc
- 2: b
\x{100}aY\x{256}Z
0: \x{100}
0: Y\x{256}Z
- 1: Y\x{256}
- 2: Y
/^[^a]{2}/8
\x{100}bc
@@ -328,8 +326,6 @@ No match
/^[^a]{2,}/8
\x{100}bcAa
0: \x{100}bcA
- 1: \x{100}bc
- 2: \x{100}b
/^[^a]{2,}?/8
\x{100}bca
@@ -339,13 +335,9 @@ No match
/[^a]+/8ig
bcd
0: bcd
- 1: bc
- 2: b
\x{100}aY\x{256}Z
0: \x{100}
0: Y\x{256}Z
- 1: Y\x{256}
- 2: Y
/^[^a]{2}/8i
\x{100}bc
@@ -354,7 +346,6 @@ No match
/^[^a]{2,}/8i
\x{100}bcAa
0: \x{100}bc
- 1: \x{100}b
/^[^a]{2,}?/8i
\x{100}bca
@@ -370,28 +361,18 @@ No match
0:
\x{100}\x{100}
0: \x{100}
- 1:
/\x{100}{0,3}/8
\x{100}\x{100}
0: \x{100}\x{100}
- 1: \x{100}
- 2:
\x{100}\x{100}\x{100}\x{100}
0: \x{100}\x{100}\x{100}
- 1: \x{100}\x{100}
- 2: \x{100}
- 3:
/\x{100}*/8
abce
0:
\x{100}\x{100}\x{100}\x{100}
0: \x{100}\x{100}\x{100}\x{100}
- 1: \x{100}\x{100}\x{100}
- 2: \x{100}\x{100}
- 3: \x{100}
- 4:
/\x{100}{1,1}/8
abcd\x{100}\x{100}\x{100}\x{100}
@@ -400,15 +381,10 @@ No match
/\x{100}{1,3}/8
abcd\x{100}\x{100}\x{100}\x{100}
0: \x{100}\x{100}\x{100}
- 1: \x{100}\x{100}
- 2: \x{100}
/\x{100}+/8
abcd\x{100}\x{100}\x{100}\x{100}
0: \x{100}\x{100}\x{100}\x{100}
- 1: \x{100}\x{100}\x{100}
- 2: \x{100}\x{100}
- 3: \x{100}
/\x{100}{3}/8
abcd\x{100}\x{100}\x{100}XX
@@ -417,10 +393,8 @@ No match
/\x{100}{3,5}/8
abcd\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}XX
0: \x{100}\x{100}\x{100}\x{100}\x{100}
- 1: \x{100}\x{100}\x{100}\x{100}
- 2: \x{100}\x{100}\x{100}
-/\x{100}{3,}/8
+/\x{100}{3,}/8O
abcd\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}XX
0: \x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
1: \x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
@@ -432,9 +406,9 @@ No match
Xyyya\x{100}\x{100}bXzzz
0: X
-/\D*/8
+/\D*/8O
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
1: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
2: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -458,9 +432,9 @@ Matched, but too many subsidiary matches
20: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
21: aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
-/\D*/8
+/\D*/8O
\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
-Matched, but too many subsidiary matches
+Matched, but offsets vector is too small to show all matches
0: \x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
1: \x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
2: \x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}\x{100}
@@ -507,33 +481,18 @@ Matched, but too many subsidiary matches
/\D+/8
12abcd34
0: abcd
- 1: abc
- 2: ab
- 3: a
*** Failers
0: *** Failers
- 1: *** Failer
- 2: *** Faile
- 3: *** Fail
- 4: *** Fai
- 5: *** Fa
- 6: *** F
- 7: ***
- 8: ***
- 9: **
-10: *
1234
No match
/\D{2,3}/8
12abcd34
0: abc
- 1: ab
12ab34
0: ab
*** Failers
0: ***
- 1: **
1234
No match
12a34
@@ -556,7 +515,6 @@ No match
/\d+/8
12abcd34
0: 12
- 1: 1
*** Failers
No match
@@ -565,7 +523,6 @@ No match
0: 12
1234abcd
0: 123
- 1: 12
*** Failers
No match
1.4
@@ -585,30 +542,18 @@ No match
/\S+/8
12abcd34
0: 12abcd34
- 1: 12abcd3
- 2: 12abcd
- 3: 12abc
- 4: 12ab
- 5: 12a
- 6: 12
- 7: 1
*** Failers
0: ***
- 1: **
- 2: *
\ \
No match
/\S{2,3}/8
12abcd34
0: 12a
- 1: 12
1234abcd
0: 123
- 1: 12
*** Failers
0: ***
- 1: **
\ \
No match
@@ -654,15 +599,8 @@ No match
/\w+/8
12 34
0: 12
- 1: 1
*** Failers
0: Failers
- 1: Failer
- 2: Faile
- 3: Fail
- 4: Fai
- 5: Fa
- 6: F
+++=*!
No match
@@ -671,10 +609,8 @@ No match
0: ab
abcd ce
0: abc
- 1: ab
*** Failers
0: Fai
- 1: Fa
a.b.c
No match
@@ -693,26 +629,18 @@ No match
/\W+/8
12====34
0: ====
- 1: ===
- 2: ==
- 3: =
*** Failers
0: ***
- 1: ***
- 2: **
- 3: *
abcd
No match
/\W{2,3}/8
ab====cd
0: ===
- 1: ==
ab==cd
0: ==
*** Failers
0: ***
- 1: **
a.b.c
No match
@@ -825,8 +753,6 @@ No match
0: \x{200}
ab\x{200}\x{100}\x{200}\x{100}cd
0: \x{200}\x{100}\x{200}
- 1: \x{200}\x{100}
- 2: \x{200}
*** Failers
No match
@@ -849,8 +775,6 @@ No match
0: \x{200}
ab\x{200}\x{100}\x{200}\x{100}cd
0: \x{200}\x{100}\x{200}
- 1: \x{200}\x{100}
- 2: \x{200}
*** Failers
No match
@@ -1126,21 +1050,21 @@ No match
a\r
No match
-/\h+\V?\v{3,4}/8
+/\h+\V?\v{3,4}/8O
\x09\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
0: \x{09} \x{a0}X\x{0a}\x{0b}\x{0c}\x{0d}
1: \x{09} \x{a0}X\x{0a}\x{0b}\x{0c}
-/\V?\v{3,4}/8
+/\V?\v{3,4}/8O
\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
0: X\x{0a}\x{0b}\x{0c}\x{0d}
1: X\x{0a}\x{0b}\x{0c}
-/\h+\V?\v{3,4}/8
+/\h+\V?\v{3,4}/8O
>\x09\x20\x{a0}X\x0a\x0a\x0a<
0: \x{09} \x{a0}X\x{0a}\x{0a}\x{0a}
-/\V?\v{3,4}/8
+/\V?\v{3,4}/8O
>\x09\x20\x{a0}X\x0a\x0a\x0a<
0: X\x{0a}\x{0a}\x{0a}
@@ -1154,7 +1078,7 @@ No match
\x{a0} X\x0a
No match
-/\H*\h+\V?\v{3,4}/8
+/\H*\h+\V?\v{3,4}/8O
\x09\x20\x{a0}X\x0a\x0b\x0c\x0d\x0a
0: \x{09} \x{a0}X\x{0a}\x{0b}\x{0c}\x{0d}
1: \x{09} \x{a0}X\x{0a}\x{0b}\x{0c}
@@ -1178,7 +1102,7 @@ No match
\x{2009} X\x0a
No match
-/\H*\h+\V?\v{3,4}/8
+/\H*\h+\V?\v{3,4}/8O
\x{1680}\x{180e}\x{2007}X\x{2028}\x{2029}\x0c\x0d\x0a
0: \x{1680}\x{180e}\x{2007}X\x{2028}\x{2029}\x{0c}\x{0d}
1: \x{1680}\x{180e}\x{2007}X\x{2028}\x{2029}\x{0c}
@@ -1279,34 +1203,28 @@ No match
/abcd*/8
xxxxabcd\P
0: abcd
- 1: abc
xxxxabcd\P\P
Partial match: abcd
/abcd*/i8
xxxxabcd\P
0: abcd
- 1: abc
xxxxabcd\P\P
Partial match: abcd
XXXXABCD\P
0: ABCD
- 1: ABC
XXXXABCD\P\P
Partial match: ABCD
/abc\d*/8
xxxxabc1\P
0: abc1
- 1: abc
xxxxabc1\P\P
Partial match: abc1
/abc[de]*/8
xxxxabcde\P
0: abcde
- 1: abcd
- 2: abc
xxxxabcde\P\P
Partial match: abcde
@@ -1340,7 +1258,6 @@ Partial match: \x{0d}
Partial match: \x{0d}\x{0d}
\r\r\r\P
0: \x{0d}\x{0d}\x{0d}
- 1: \x{0d}\x{0d}
\r\r\r\P\P
Partial match: \x{0d}\x{0d}\x{0d}
@@ -1366,6 +1283,5 @@ Partial match: \x{0d}\x{0d}\x{0d}
/[^\x{100}]+/8
\x{100}\x{101}X
0: \x{101}X
- 1: \x{101}
/-- End of testinput9 --/
diff --git a/ext/pcre/pcrelib/testdata/testoutputEBC b/ext/pcre/pcrelib/testdata/testoutputEBC
new file mode 100644
index 0000000000..abbfdc43fc
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/testoutputEBC
@@ -0,0 +1,182 @@
+/-- This is a specialized test for checking, when PCRE is compiled with the
+EBCDIC option but in an ASCII environment, that newline and white space
+functionality is working. It catches cases where explicit values such as 0x0a
+have been used instead of names like CHAR_LF. Needless to say, it is not a
+genuine EBCDIC test! In patterns, alphabetic characters that follow a backslash
+must be in EBCDIC code. In data, newlines and other spacing characters must be
+in EBCDIC, but can be specified as escapes. --/
+
+/-- Test default newline and variations --/
+
+/^A/m
+ ABC
+ 0: A
+ 12\x15ABC
+ 0: A
+
+/^A/m<any>
+ 12\x15ABC
+ 0: A
+ 12\x0dABC
+ 0: A
+ 12\x0d\x15ABC
+ 0: A
+ 12\x25ABC
+ 0: A
+
+/^A/m<anycrlf>
+ 12\x15ABC
+ 0: A
+ 12\x0dABC
+ 0: A
+ 12\x0d\x15ABC
+ 0: A
+ ** Fail
+No match
+ 12\x25ABC
+No match
+
+/-- Test \h --/
+
+/^A\ˆ/
+ A B
+ 0: A\x20
+
+/-- Test \H --/
+
+/^A\È/
+ AB
+ 0: AB
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \R --/
+
+/^A\Ù/
+ A\x15B
+ 0: A\x15
+ A\x0dB
+ 0: A\x0d
+ A\x25B
+ 0: A\x25
+ A\x0bB
+ 0: A\x0b
+ A\x0cB
+ 0: A\x0c
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \v --/
+
+/^A\¥/
+ A\x15B
+ 0: A\x15
+ A\x0dB
+ 0: A\x0d
+ A\x25B
+ 0: A\x25
+ A\x0bB
+ 0: A\x0b
+ A\x0cB
+ 0: A\x0c
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \V --/
+
+/^A\å/
+ A B
+ 0: A\x20
+ ** Fail
+No match
+ A\x15B
+No match
+ A\x0dB
+No match
+ A\x25B
+No match
+ A\x0bB
+No match
+ A\x0cB
+No match
+
+/-- For repeated items, use an atomic group so that the output is the same
+for DFA matching (otherwise it may show multiple matches). --/
+
+/-- Test \h+ --/
+
+/^A(?>\ˆ+)/
+ A B
+ 0: A\x20
+
+/-- Test \H+ --/
+
+/^A(?>\È+)/
+ AB
+ 0: AB
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \R+ --/
+
+/^A(?>\Ù+)/
+ A\x15B
+ 0: A\x15
+ A\x0dB
+ 0: A\x0d
+ A\x25B
+ 0: A\x25
+ A\x0bB
+ 0: A\x0b
+ A\x0cB
+ 0: A\x0c
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \v+ --/
+
+/^A(?>\¥+)/
+ A\x15B
+ 0: A\x15
+ A\x0dB
+ 0: A\x0d
+ A\x25B
+ 0: A\x25
+ A\x0bB
+ 0: A\x0b
+ A\x0cB
+ 0: A\x0c
+ ** Fail
+No match
+ A B
+No match
+
+/-- Test \V+ --/
+
+/^A(?>\å+)/
+ A B
+ 0: A\x20B
+ ** Fail
+No match
+ A\x15B
+No match
+ A\x0dB
+No match
+ A\x25B
+No match
+ A\x0bB
+No match
+ A\x0cB
+No match
+
+/-- End --/
diff --git a/ext/pcre/pcrelib/testdata/wintestinput3 b/ext/pcre/pcrelib/testdata/wintestinput3
new file mode 100644
index 0000000000..04e76a6dc8
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/wintestinput3
@@ -0,0 +1,91 @@
+/^[\w]+/
+ *** Failers
+ École
+
+/^[\w]+/Lfrench
+ École
+
+/^[\w]+/
+ *** Failers
+ École
+
+/^[\W]+/
+ École
+
+/^[\W]+/Lfrench
+ *** Failers
+ École
+
+/[\b]/
+ \b
+ *** Failers
+ a
+
+/[\b]/Lfrench
+ \b
+ *** Failers
+ a
+
+/^\w+/
+ *** Failers
+ École
+
+/^\w+/Lfrench
+ École
+
+/(.+)\b(.+)/
+ École
+
+/(.+)\b(.+)/Lfrench
+ *** Failers
+ École
+
+/École/i
+ École
+ *** Failers
+ école
+
+/École/iLfrench
+ École
+ école
+
+/\w/IS
+
+/\w/ISLfrench
+
+/^[\xc8-\xc9]/iLfrench
+ École
+ école
+
+/^[\xc8-\xc9]/Lfrench
+ École
+ *** Failers
+ école
+
+/\W+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/[\W]+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/[^[:alpha:]]+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/\w+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/[\w]+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/[[:alpha:]]+/Lfrench
+ >>>\xaa<<<
+ >>>\xba<<<
+
+/[[:alpha:]][[:lower:]][[:upper:]]/DZLfrench
+
+/ End of testinput3 /
diff --git a/ext/pcre/pcrelib/testdata/wintestoutput3 b/ext/pcre/pcrelib/testdata/wintestoutput3
new file mode 100644
index 0000000000..0088007067
--- /dev/null
+++ b/ext/pcre/pcrelib/testdata/wintestoutput3
@@ -0,0 +1,166 @@
+/^[\w]+/
+ *** Failers
+No match
+ École
+No match
+
+/^[\w]+/Lfrench
+ École
+ 0: École
+
+/^[\w]+/
+ *** Failers
+No match
+ École
+No match
+
+/^[\W]+/
+ École
+ 0: \xc9
+
+/^[\W]+/Lfrench
+ *** Failers
+ 0: ***
+ École
+No match
+
+/[\b]/
+ \b
+ 0: \x08
+ *** Failers
+No match
+ a
+No match
+
+/[\b]/Lfrench
+ \b
+ 0: \x08
+ *** Failers
+No match
+ a
+No match
+
+/^\w+/
+ *** Failers
+No match
+ École
+No match
+
+/^\w+/Lfrench
+ École
+ 0: École
+
+/(.+)\b(.+)/
+ École
+ 0: \xc9cole
+ 1: \xc9
+ 2: cole
+
+/(.+)\b(.+)/Lfrench
+ *** Failers
+ 0: *** Failers
+ 1: ***
+ 2: Failers
+ École
+No match
+
+/École/i
+ École
+ 0: \xc9cole
+ *** Failers
+No match
+ école
+No match
+
+/École/iLfrench
+ École
+ 0: École
+ école
+ 0: école
+
+/\w/IS
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: 0 1 2 3 4 5 6 7 8 9 A B C D E F G H I J K L M N O P
+ Q R S T U V W X Y Z _ a b c d e f g h i j k l m n o p q r s t u v w x y z
+
+/\w/ISLfrench
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+Subject length lower bound = 1
+Starting byte set: 0 1 2 3 4 5 6 7 8 9 A B C D E F G H I J K L M N O P
+ Q R S T U V W X Y Z _ a b c d e f g h i j k l m n o p q r s t u v w x y z
+ ƒ Š Œ Ž š œ ž Ÿ ª ² ³ µ ¹ º À Á Â Ã Ä Å Æ Ç È É Ê Ë Ì Í Î Ï Ð Ñ Ò Ó Ô Õ Ö
+ Ø Ù Ú Û Ü Ý Þ ß à á â ã ä å æ ç è é ê ë ì í î ï ð ñ ò ó ô õ ö ø ù ú û ü ý
+ þ ÿ
+
+/^[\xc8-\xc9]/iLfrench
+ École
+ 0: É
+ école
+ 0: é
+
+/^[\xc8-\xc9]/Lfrench
+ École
+ 0: É
+ *** Failers
+No match
+ école
+No match
+
+/\W+/Lfrench
+ >>>\xaa<<<
+ 0: >>>
+ >>>\xba<<<
+ 0: >>>
+
+/[\W]+/Lfrench
+ >>>\xaa<<<
+ 0: >>>
+ >>>\xba<<<
+ 0: >>>
+
+/[^[:alpha:]]+/Lfrench
+ >>>\xaa<<<
+ 0: >>>
+ >>>\xba<<<
+ 0: >>>
+
+/\w+/Lfrench
+ >>>\xaa<<<
+ 0: ª
+ >>>\xba<<<
+ 0: º
+
+/[\w]+/Lfrench
+ >>>\xaa<<<
+ 0: ª
+ >>>\xba<<<
+ 0: º
+
+/[[:alpha:]]+/Lfrench
+ >>>\xaa<<<
+ 0: ª
+ >>>\xba<<<
+ 0: º
+
+/[[:alpha:]][[:lower:]][[:upper:]]/DZLfrench
+------------------------------------------------------------------
+ Bra
+ [A-Za-z\x83\x8a\x8c\x8e\x9a\x9c\x9e\x9f\xaa\xb5\xba\xc0-\xd6\xd8-\xf6\xf8-\xff]
+ [a-z\x83\x9a\x9c\x9e\xaa\xb5\xba\xdf-\xf6\xf8-\xff]
+ [A-Z\x8a\x8c\x8e\x9f\xc0-\xd6\xd8-\xde]
+ Ket
+ End
+------------------------------------------------------------------
+Capturing subpattern count = 0
+No options
+No first char
+No need char
+
+/ End of testinput3 /
diff --git a/ext/pcre/pcrelib/ucp.h b/ext/pcre/pcrelib/ucp.h
index 21039106e5..d8b34bfcc5 100644
--- a/ext/pcre/pcrelib/ucp.h
+++ b/ext/pcre/pcrelib/ucp.h
@@ -11,7 +11,10 @@ should always be at the end of each enum, for backwards compatibility.
IMPORTANT: Note also that the specific numeric values of the enums have to be
the same as the values that are generated by the maint/MultiStage2.py script,
-where the equivalent property descriptive names are listed in vectors. */
+where the equivalent property descriptive names are listed in vectors.
+
+ALSO: The specific values of the first two enums are assumed for the table
+called catposstab in pcre_compile.c. */
/* These are the general character categories. */
diff --git a/ext/pcre/php_pcre.c b/ext/pcre/php_pcre.c
index 7d34d9feb1..196ada0266 100644
--- a/ext/pcre/php_pcre.c
+++ b/ext/pcre/php_pcre.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcre/php_pcre.h b/ext/pcre/php_pcre.h
index db14ce38fc..4b261871e2 100644
--- a/ext/pcre/php_pcre.h
+++ b/ext/pcre/php_pcre.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pcre/tests/bug37911.phpt b/ext/pcre/tests/bug37911.phpt
index f7881191b7..2b7481a464 100644
--- a/ext/pcre/tests/bug37911.phpt
+++ b/ext/pcre/tests/bug37911.phpt
@@ -37,5 +37,5 @@ array(3) {
string(4) "blub"
}
-Warning: preg_replace_callback(): Numeric named subpatterns are not allowed in %sbug37911.php on line 14
+Warning: preg_replace_callback(): Compilation failed: group name must start with a non-digit at offset %d in %sbug37911.php on line %d
NULL
diff --git a/ext/pcre/tests/grep2.phpt b/ext/pcre/tests/grep2.phpt
index 0cf8d4aebc..1a8476c396 100644
--- a/ext/pcre/tests/grep2.phpt
+++ b/ext/pcre/tests/grep2.phpt
@@ -40,6 +40,12 @@ array(1) {
string(1) "1"
}
bool(true)
-array(0) {
+array(3) {
+ [5]=>
+ string(1) "a"
+ ["xyz"]=>
+ string(2) "q6"
+ [6]=>
+ string(3) "h20"
}
-bool(true)
+bool(false)
diff --git a/ext/pcre/tests/match_flags3.phpt b/ext/pcre/tests/match_flags3.phpt
index f22205e3d8..84deb0b80c 100644
--- a/ext/pcre/tests/match_flags3.phpt
+++ b/ext/pcre/tests/match_flags3.phpt
@@ -42,5 +42,5 @@ array(1) {
}
}
-Warning: preg_match(): Numeric named subpatterns are not allowed in %smatch_flags3.php on line 14
+Warning: preg_match(): Compilation failed: group name must start with a non-digit at offset %d in %smatch_flags3.php on line %d
bool(false)
diff --git a/ext/pdo/pdo.c b/ext/pdo/pdo.c
index 452c27b591..f3c9b65766 100644
--- a/ext/pdo/pdo.c
+++ b/ext/pdo/pdo.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/pdo_dbh.c b/ext/pdo/pdo_dbh.c
index d5860b1a1e..4f5a391704 100644
--- a/ext/pdo/pdo_dbh.c
+++ b/ext/pdo/pdo_dbh.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -196,7 +196,7 @@ static char *dsn_from_uri(char *uri, char *buf, size_t buflen TSRMLS_DC) /* {{{
}
/* }}} */
-/* {{{ proto void PDO::__construct(string dsn, string username, string passwd [, array options])
+/* {{{ proto void PDO::__construct(string dsn[, string username[, string passwd [, array options]]])
*/
static PHP_METHOD(PDO, dbh_constructor)
{
@@ -460,7 +460,7 @@ static void pdo_stmt_construct(pdo_stmt_t *stmt, zval *object, zend_class_entry
if (dbstmt_ce->constructor) {
zend_fcall_info fci;
zend_fcall_info_cache fcc;
- zval *retval;
+ zval *retval = NULL;
fci.size = sizeof(zend_fcall_info);
fci.function_table = &dbstmt_ce->function_table;
@@ -495,7 +495,7 @@ static void pdo_stmt_construct(pdo_stmt_t *stmt, zval *object, zend_class_entry
zval_dtor(object);
ZVAL_NULL(object);
object = NULL; /* marks failure */
- } else {
+ } else if (retval) {
zval_ptr_dtor(&retval);
}
@@ -1226,7 +1226,7 @@ static PHP_METHOD(PDO, getAvailableDrivers)
/* }}} */
/* {{{ arginfo */
-ZEND_BEGIN_ARG_INFO_EX(arginfo_pdo___construct, 0, 0, 3)
+ZEND_BEGIN_ARG_INFO_EX(arginfo_pdo___construct, 0, 0, 1)
ZEND_ARG_INFO(0, dsn)
ZEND_ARG_INFO(0, username)
ZEND_ARG_INFO(0, passwd)
diff --git a/ext/pdo/pdo_sql_parser.c b/ext/pdo/pdo_sql_parser.c
index aea362fdb2..341e664bbe 100644
--- a/ext/pdo/pdo_sql_parser.c
+++ b/ext/pdo/pdo_sql_parser.c
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -586,7 +586,9 @@ safe:
}
plc->freeq = 1;
} else {
- switch (Z_TYPE_P(param->parameter)) {
+ zval tmp_param = *param->parameter;
+ zval_copy_ctor(&tmp_param);
+ switch (Z_TYPE(tmp_param)) {
case IS_NULL:
plc->quoted = "NULL";
plc->qlen = sizeof("NULL")-1;
@@ -594,20 +596,20 @@ safe:
break;
case IS_BOOL:
- convert_to_long(param->parameter);
-
+ convert_to_long(&tmp_param);
+ /* fall through */
case IS_LONG:
case IS_DOUBLE:
- convert_to_string(param->parameter);
- plc->qlen = Z_STRLEN_P(param->parameter);
- plc->quoted = Z_STRVAL_P(param->parameter);
- plc->freeq = 0;
+ convert_to_string(&tmp_param);
+ plc->qlen = Z_STRLEN(tmp_param);
+ plc->quoted = estrdup(Z_STRVAL(tmp_param));
+ plc->freeq = 1;
break;
default:
- convert_to_string(param->parameter);
- if (!stmt->dbh->methods->quoter(stmt->dbh, Z_STRVAL_P(param->parameter),
- Z_STRLEN_P(param->parameter), &plc->quoted, &plc->qlen,
+ convert_to_string(&tmp_param);
+ if (!stmt->dbh->methods->quoter(stmt->dbh, Z_STRVAL(tmp_param),
+ Z_STRLEN(tmp_param), &plc->quoted, &plc->qlen,
param->param_type TSRMLS_CC)) {
/* bork */
ret = -1;
@@ -616,6 +618,7 @@ safe:
}
plc->freeq = 1;
}
+ zval_dtor(&tmp_param);
}
} else {
plc->quoted = Z_STRVAL_P(param->parameter);
diff --git a/ext/pdo/pdo_sql_parser.re b/ext/pdo/pdo_sql_parser.re
index 1936a37340..fa8ef187fa 100644
--- a/ext/pdo/pdo_sql_parser.re
+++ b/ext/pdo/pdo_sql_parser.re
@@ -228,7 +228,9 @@ safe:
}
plc->freeq = 1;
} else {
- switch (Z_TYPE_P(param->parameter)) {
+ zval tmp_param = *param->parameter;
+ zval_copy_ctor(&tmp_param);
+ switch (Z_TYPE(tmp_param)) {
case IS_NULL:
plc->quoted = "NULL";
plc->qlen = sizeof("NULL")-1;
@@ -236,20 +238,20 @@ safe:
break;
case IS_BOOL:
- convert_to_long(param->parameter);
-
+ convert_to_long(&tmp_param);
+ /* fall through */
case IS_LONG:
case IS_DOUBLE:
- convert_to_string(param->parameter);
- plc->qlen = Z_STRLEN_P(param->parameter);
- plc->quoted = Z_STRVAL_P(param->parameter);
- plc->freeq = 0;
+ convert_to_string(&tmp_param);
+ plc->qlen = Z_STRLEN(tmp_param);
+ plc->quoted = estrdup(Z_STRVAL(tmp_param));
+ plc->freeq = 1;
break;
default:
- convert_to_string(param->parameter);
- if (!stmt->dbh->methods->quoter(stmt->dbh, Z_STRVAL_P(param->parameter),
- Z_STRLEN_P(param->parameter), &plc->quoted, &plc->qlen,
+ convert_to_string(&tmp_param);
+ if (!stmt->dbh->methods->quoter(stmt->dbh, Z_STRVAL(tmp_param),
+ Z_STRLEN(tmp_param), &plc->quoted, &plc->qlen,
param->param_type TSRMLS_CC)) {
/* bork */
ret = -1;
@@ -258,6 +260,7 @@ safe:
}
plc->freeq = 1;
}
+ zval_dtor(&tmp_param);
}
} else {
plc->quoted = Z_STRVAL_P(param->parameter);
diff --git a/ext/pdo/pdo_sqlstate.c b/ext/pdo/pdo_sqlstate.c
index 7c92c1c0f3..533a35c404 100644
--- a/ext/pdo/pdo_sqlstate.c
+++ b/ext/pdo/pdo_sqlstate.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/pdo_stmt.c b/ext/pdo/pdo_stmt.c
index 04e71823b9..2735aede41 100644
--- a/ext/pdo/pdo_stmt.c
+++ b/ext/pdo/pdo_stmt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/php_pdo.h b/ext/pdo/php_pdo.h
index f8a8ce377e..0b8bf6dfa9 100644
--- a/ext/pdo/php_pdo.h
+++ b/ext/pdo/php_pdo.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/php_pdo_driver.h b/ext/pdo/php_pdo_driver.h
index ede2d6fb76..56a69cac30 100644
--- a/ext/pdo/php_pdo_driver.h
+++ b/ext/pdo/php_pdo_driver.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/php_pdo_int.h b/ext/pdo/php_pdo_int.h
index 91d0bf0412..2740fc8e63 100644
--- a/ext/pdo/php_pdo_int.h
+++ b/ext/pdo/php_pdo_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo/tests/bug65946.phpt b/ext/pdo/tests/bug65946.phpt
new file mode 100644
index 0000000000..1c4bd8d6c4
--- /dev/null
+++ b/ext/pdo/tests/bug65946.phpt
@@ -0,0 +1,32 @@
+--TEST--
+Bug #65946 (pdo_sql_parser.c permanently converts values bound to strings)
+--SKIPIF--
+<?php
+if (!extension_loaded('pdo')) die('skip');
+$dir = getenv('REDIR_TEST_DIR');
+if (false == $dir) die('skip no driver');
+require_once $dir . 'pdo_test.inc';
+PDOTest::skip();
+?>
+--FILE--
+<?php
+if (getenv('REDIR_TEST_DIR') === false) putenv('REDIR_TEST_DIR='.dirname(__FILE__) . '/../../pdo/tests/');
+require_once getenv('REDIR_TEST_DIR') . 'pdo_test.inc';
+$db = PDOTest::factory();
+$db->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);
+$db->exec('CREATE TABLE test(id int)');
+$db->exec('INSERT INTO test VALUES(1)');
+$stmt = $db->prepare('SELECT * FROM test LIMIT :limit');
+$stmt->bindValue('limit', 1, PDO::PARAM_INT);
+if(!($res = $stmt->execute())) var_dump($stmt->errorInfo());
+if(!($res = $stmt->execute())) var_dump($stmt->errorInfo());
+var_dump($stmt->fetchAll(PDO::FETCH_ASSOC));
+?>
+--EXPECTF--
+array(1) {
+ [0]=>
+ array(1) {
+ ["id"]=>
+ string(1) "1"
+ }
+}
diff --git a/ext/pdo_dblib/dblib_driver.c b/ext/pdo_dblib/dblib_driver.c
index daf5494d58..0fa68900b0 100644
--- a/ext/pdo_dblib/dblib_driver.c
+++ b/ext/pdo_dblib/dblib_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_dblib/dblib_stmt.c b/ext/pdo_dblib/dblib_stmt.c
index 51cebc48b0..18e9e679cc 100644
--- a/ext/pdo_dblib/dblib_stmt.c
+++ b/ext/pdo_dblib/dblib_stmt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_dblib/pdo_dblib.c b/ext/pdo_dblib/pdo_dblib.c
index bc5d364ed3..2801ece8f1 100644
--- a/ext/pdo_dblib/pdo_dblib.c
+++ b/ext/pdo_dblib/pdo_dblib.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_dblib/php_pdo_dblib.h b/ext/pdo_dblib/php_pdo_dblib.h
index 3396f208e5..f7de387b96 100644
--- a/ext/pdo_dblib/php_pdo_dblib.h
+++ b/ext/pdo_dblib/php_pdo_dblib.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_dblib/php_pdo_dblib_int.h b/ext/pdo_dblib/php_pdo_dblib_int.h
index 2bdb83c326..df15b229e0 100644
--- a/ext/pdo_dblib/php_pdo_dblib_int.h
+++ b/ext/pdo_dblib/php_pdo_dblib_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_firebird/firebird_driver.c b/ext/pdo_firebird/firebird_driver.c
index bda6d23fa4..aa5e795594 100644
--- a/ext/pdo_firebird/firebird_driver.c
+++ b/ext/pdo_firebird/firebird_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_firebird/firebird_statement.c b/ext/pdo_firebird/firebird_statement.c
index 2b57cd8ba6..efb232bff6 100644
--- a/ext/pdo_firebird/firebird_statement.c
+++ b/ext/pdo_firebird/firebird_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_firebird/pdo_firebird.c b/ext/pdo_firebird/pdo_firebird.c
index 1f14b55421..c512004b2c 100644
--- a/ext/pdo_firebird/pdo_firebird.c
+++ b/ext/pdo_firebird/pdo_firebird.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_firebird/php_pdo_firebird.h b/ext/pdo_firebird/php_pdo_firebird.h
index cbece41d9f..3816497c2a 100644
--- a/ext/pdo_firebird/php_pdo_firebird.h
+++ b/ext/pdo_firebird/php_pdo_firebird.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_firebird/php_pdo_firebird_int.h b/ext/pdo_firebird/php_pdo_firebird_int.h
index 9632edc810..b186eeb474 100644
--- a/ext/pdo_firebird/php_pdo_firebird_int.h
+++ b/ext/pdo_firebird/php_pdo_firebird_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_mysql/mysql_driver.c b/ext/pdo_mysql/mysql_driver.c
index cd86503dd7..825fe2647f 100644
--- a/ext/pdo_mysql/mysql_driver.c
+++ b/ext/pdo_mysql/mysql_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_mysql/mysql_statement.c b/ext/pdo_mysql/mysql_statement.c
index 369c389462..95501c22c7 100644
--- a/ext/pdo_mysql/mysql_statement.c
+++ b/ext/pdo_mysql/mysql_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_mysql/pdo_mysql.c b/ext/pdo_mysql/pdo_mysql.c
index 78c4ceefe9..6f4e9d5265 100644
--- a/ext/pdo_mysql/pdo_mysql.c
+++ b/ext/pdo_mysql/pdo_mysql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -64,7 +64,12 @@ static MYSQLND * pdo_mysql_convert_zv_to_mysqlnd(zval * zv TSRMLS_DC)
if (Z_TYPE_P(zv) == IS_OBJECT && instanceof_function(Z_OBJCE_P(zv), php_pdo_get_dbh_ce() TSRMLS_CC)) {
pdo_dbh_t * dbh = zend_object_store_get_object(zv TSRMLS_CC);
- if (!dbh || dbh->driver != &pdo_mysql_driver) {
+ if (!dbh) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Failed to retrieve handle from object store");
+ return NULL;
+ }
+
+ if (dbh->driver != &pdo_mysql_driver) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Provided PDO instance is not using MySQL but %s", dbh->driver->driver_name);
return NULL;
}
diff --git a/ext/pdo_mysql/php_pdo_mysql.h b/ext/pdo_mysql/php_pdo_mysql.h
index e4493b569a..e4d37c88ab 100644
--- a/ext/pdo_mysql/php_pdo_mysql.h
+++ b/ext/pdo_mysql/php_pdo_mysql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_mysql/php_pdo_mysql_int.h b/ext/pdo_mysql/php_pdo_mysql_int.h
index 24f7aa2182..26263222b9 100644
--- a/ext/pdo_mysql/php_pdo_mysql_int.h
+++ b/ext/pdo_mysql/php_pdo_mysql_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_mysql/tests/bug66141.phpt b/ext/pdo_mysql/tests/bug66141.phpt
new file mode 100644
index 0000000000..3a28509314
--- /dev/null
+++ b/ext/pdo_mysql/tests/bug66141.phpt
@@ -0,0 +1,38 @@
+--TEST--
+Bug #66141 (mysqlnd quote function is wrong with NO_BACKSLASH_ESCAPES after failed query)
+--SKIPIF--
+<?php
+require_once(dirname(__FILE__) . DIRECTORY_SEPARATOR . 'skipif.inc');
+require_once(dirname(__FILE__) . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc');
+MySQLPDOTest::skip();
+?>
+--FILE--
+<?php
+include __DIR__ . DIRECTORY_SEPARATOR . 'mysql_pdo_test.inc';
+$db = MySQLPDOTest::factory();
+
+$input = 'Something\', 1 as one, 2 as two FROM dual; -- f';
+
+$quotedInput0 = $db->quote($input);
+
+$db->query('set session sql_mode="NO_BACKSLASH_ESCAPES"');
+
+// injection text from some user input
+
+$quotedInput1 = $db->quote($input);
+
+$db->query('something that throws an exception');
+
+$quotedInput2 = $db->quote($input);
+
+var_dump($quotedInput0);
+var_dump($quotedInput1);
+var_dump($quotedInput2);
+?>
+done
+--EXPECTF--
+Warning: PDO::query(): SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'something that throws an exception' at line %d in %s on line %d
+string(50) "'Something\', 1 as one, 2 as two FROM dual; -- f'"
+string(50) "'Something'', 1 as one, 2 as two FROM dual; -- f'"
+string(50) "'Something'', 1 as one, 2 as two FROM dual; -- f'"
+done \ No newline at end of file
diff --git a/ext/pdo_oci/oci_driver.c b/ext/pdo_oci/oci_driver.c
index fcdefa94b3..8f56c674d1 100644
--- a/ext/pdo_oci/oci_driver.c
+++ b/ext/pdo_oci/oci_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_oci/oci_statement.c b/ext/pdo_oci/oci_statement.c
index 6a74efa7ba..4e341c08be 100644
--- a/ext/pdo_oci/oci_statement.c
+++ b/ext/pdo_oci/oci_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_oci/pdo_oci.c b/ext/pdo_oci/pdo_oci.c
index 69577148f6..8eabb7e7c5 100644
--- a/ext/pdo_oci/pdo_oci.c
+++ b/ext/pdo_oci/pdo_oci.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_oci/php_pdo_oci.h b/ext/pdo_oci/php_pdo_oci.h
index d0b1b3d015..3299dfe269 100644
--- a/ext/pdo_oci/php_pdo_oci.h
+++ b/ext/pdo_oci/php_pdo_oci.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_oci/php_pdo_oci_int.h b/ext/pdo_oci/php_pdo_oci_int.h
index af5618b61a..4979aadb13 100644
--- a/ext/pdo_oci/php_pdo_oci_int.h
+++ b/ext/pdo_oci/php_pdo_oci_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_odbc/odbc_driver.c b/ext/pdo_odbc/odbc_driver.c
index f7f3ef34ed..339db5698a 100644
--- a/ext/pdo_odbc/odbc_driver.c
+++ b/ext/pdo_odbc/odbc_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_odbc/odbc_stmt.c b/ext/pdo_odbc/odbc_stmt.c
index 0e3fd3cbb9..8b0ccf34e6 100644
--- a/ext/pdo_odbc/odbc_stmt.c
+++ b/ext/pdo_odbc/odbc_stmt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -472,7 +472,7 @@ static int odbc_stmt_param_hook(pdo_stmt_t *stmt, struct pdo_bound_param_data *p
if (P->outbuf) {
unsigned long ulen;
char *srcbuf;
- unsigned long srclen;
+ unsigned long srclen = 0;
switch (P->len) {
case SQL_NULL_DATA:
@@ -551,7 +551,8 @@ static int odbc_stmt_describe(pdo_stmt_t *stmt, int colno TSRMLS_DC)
struct pdo_column_data *col = &stmt->columns[colno];
RETCODE rc;
SWORD colnamelen;
- SDWORD colsize, displaysize;
+ SDWORD colsize;
+ SQLLEN displaysize;
rc = SQLDescribeCol(S->stmt, colno+1, S->cols[colno].colname,
sizeof(S->cols[colno].colname)-1, &colnamelen,
diff --git a/ext/pdo_odbc/pdo_odbc.c b/ext/pdo_odbc/pdo_odbc.c
index f481c07f26..1fe17c1c30 100644
--- a/ext/pdo_odbc/pdo_odbc.c
+++ b/ext/pdo_odbc/pdo_odbc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_odbc/php_pdo_odbc.h b/ext/pdo_odbc/php_pdo_odbc.h
index ee80e7517b..cd01ae45e5 100644
--- a/ext/pdo_odbc/php_pdo_odbc.h
+++ b/ext/pdo_odbc/php_pdo_odbc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_odbc/php_pdo_odbc_int.h b/ext/pdo_odbc/php_pdo_odbc_int.h
index 8594120ef0..87b2f9100d 100644
--- a/ext/pdo_odbc/php_pdo_odbc_int.h
+++ b/ext/pdo_odbc/php_pdo_odbc_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.0 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_pgsql/pdo_pgsql.c b/ext/pdo_pgsql/pdo_pgsql.c
index 7c37a603f8..8e4cc97fb5 100644
--- a/ext/pdo_pgsql/pdo_pgsql.c
+++ b/ext/pdo_pgsql/pdo_pgsql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_pgsql/pgsql_driver.c b/ext/pdo_pgsql/pgsql_driver.c
index 50136430a0..3be9359216 100644
--- a/ext/pdo_pgsql/pgsql_driver.c
+++ b/ext/pdo_pgsql/pgsql_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1039,6 +1039,7 @@ static int pdo_pgsql_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_
pdo_pgsql_db_handle *H;
int ret = 0;
char *conn_str, *p, *e;
+ char *tmp_pass;
long connect_timeout = 30;
H = pecalloc(1, sizeof(pdo_pgsql_db_handle), dbh->is_persistent);
@@ -1060,18 +1061,44 @@ static int pdo_pgsql_handle_factory(pdo_dbh_t *dbh, zval *driver_options TSRMLS_
connect_timeout = pdo_attr_lval(driver_options, PDO_ATTR_TIMEOUT, 30 TSRMLS_CC);
}
+ if (dbh->password) {
+ if (dbh->password[0] != '\'' && dbh->password[strlen(dbh->password) - 1] != '\'') {
+ char *pwd = dbh->password;
+ int pos = 1;
+
+ tmp_pass = safe_emalloc(2, strlen(dbh->password), 3);
+ tmp_pass[0] = '\'';
+
+ while (*pwd != '\0') {
+ if (*pwd == '\\' || *pwd == '\'') {
+ tmp_pass[pos++] = '\\';
+ }
+
+ tmp_pass[pos++] = *pwd++;
+ }
+
+ tmp_pass[pos++] = '\'';
+ tmp_pass[pos] = '\0';
+ } else {
+ tmp_pass = dbh->password;
+ }
+ }
+
/* support both full connection string & connection string + login and/or password */
if (dbh->username && dbh->password) {
- spprintf(&conn_str, 0, "%s user=%s password=%s connect_timeout=%ld", dbh->data_source, dbh->username, dbh->password, connect_timeout);
+ spprintf(&conn_str, 0, "%s user=%s password=%s connect_timeout=%ld", dbh->data_source, dbh->username, tmp_pass, connect_timeout);
} else if (dbh->username) {
spprintf(&conn_str, 0, "%s user=%s connect_timeout=%ld", dbh->data_source, dbh->username, connect_timeout);
} else if (dbh->password) {
- spprintf(&conn_str, 0, "%s password=%s connect_timeout=%ld", dbh->data_source, dbh->password, connect_timeout);
+ spprintf(&conn_str, 0, "%s password=%s connect_timeout=%ld", dbh->data_source, tmp_pass, connect_timeout);
} else {
spprintf(&conn_str, 0, "%s connect_timeout=%ld", (char *) dbh->data_source, connect_timeout);
}
H->server = PQconnectdb(conn_str);
+ if (dbh->password && tmp_pass != dbh->password) {
+ efree(tmp_pass);
+ }
efree(conn_str);
diff --git a/ext/pdo_pgsql/pgsql_statement.c b/ext/pdo_pgsql/pgsql_statement.c
index 792ad27078..ea5a67633e 100644
--- a/ext/pdo_pgsql/pgsql_statement.c
+++ b/ext/pdo_pgsql/pgsql_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_pgsql/php_pdo_pgsql.h b/ext/pdo_pgsql/php_pdo_pgsql.h
index b7ea2628e7..9c01d9886c 100644
--- a/ext/pdo_pgsql/php_pdo_pgsql.h
+++ b/ext/pdo_pgsql/php_pdo_pgsql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_pgsql/php_pdo_pgsql_int.h b/ext/pdo_pgsql/php_pdo_pgsql_int.h
index 02a6717760..6ca4794c8c 100644
--- a/ext/pdo_pgsql/php_pdo_pgsql_int.h
+++ b/ext/pdo_pgsql/php_pdo_pgsql_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_pgsql/tests/bug62479.phpt b/ext/pdo_pgsql/tests/bug62479.phpt
new file mode 100644
index 0000000000..a12bb8d1ff
--- /dev/null
+++ b/ext/pdo_pgsql/tests/bug62479.phpt
@@ -0,0 +1,56 @@
+--TEST--
+PDO PgSQL Bug #62479 (PDO-psql cannot connect if password contains spaces)
+--SKIPIF--
+<?php
+if (!extension_loaded('pdo') || !extension_loaded('pdo_pgsql')) die('skip not loaded');
+require dirname(__FILE__) . '/config.inc';
+require dirname(__FILE__) . '/../../../ext/pdo/tests/pdo_test.inc';
+PDOTest::skip();
+if (!isset($conf['ENV']['PDOTEST_DSN'])) die('no dsn found in env');
+$db = PDOTest::test_factory(dirname(__FILE__) . '/common.phpt');
+$rand = rand(5, 5);
+
+// Assume that if we can't create a user, this test needs to be skipped
+$testQuery = "CREATE USER pdo_$rand WITH PASSWORD 'testpass'";
+$db->query($testQuery);
+$testQuery = "DROP USER pdo_$rand";
+$db->query($testQuery);
+?>
+--FILE--
+<?php
+require dirname(__FILE__) . '/../../../ext/pdo/tests/pdo_test.inc';
+$pdo = PDOTest::test_factory(dirname(__FILE__) . '/common.phpt');
+$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, true);
+$rand = rand(5, 400);
+$user = "pdo_$rand";
+$template = "CREATE USER $user WITH PASSWORD '%s'";
+$dropUser = "DROP USER $user";
+$testQuery = 'SELECT 1 as verification';
+
+// Create temp user with space in password
+$sql = sprintf($template, 'my password');
+$pdo->query($sql);
+$testConn = new PDO($conf['ENV']['PDOTEST_DSN'], $user, "my password");
+$result = $testConn->query($testQuery)->fetch();
+$check = $result[0];
+var_dump($check);
+
+// Remove the user
+$pdo->query($dropUser);
+
+// Create a user with a space and single quote
+$sql = sprintf($template, "my pass''word");
+$pdo->query($sql);
+
+$testConn = new PDO($conf['ENV']['PDOTEST_DSN'], $user, "my pass'word");
+$result = $testConn->query($testQuery)->fetch();
+$check = $result[0];
+var_dump($check);
+
+// Remove the user
+$pdo->query($dropUser);
+?>
+--EXPECT--
+int(1)
+int(1)
+
diff --git a/ext/pdo_sqlite/pdo_sqlite.c b/ext/pdo_sqlite/pdo_sqlite.c
index cc9b03e62d..33cffee821 100644
--- a/ext/pdo_sqlite/pdo_sqlite.c
+++ b/ext/pdo_sqlite/pdo_sqlite.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_sqlite/php_pdo_sqlite.h b/ext/pdo_sqlite/php_pdo_sqlite.h
index 6fa3bab1ff..607b3ddedb 100644
--- a/ext/pdo_sqlite/php_pdo_sqlite.h
+++ b/ext/pdo_sqlite/php_pdo_sqlite.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_sqlite/php_pdo_sqlite_int.h b/ext/pdo_sqlite/php_pdo_sqlite_int.h
index 8e20ca5cf4..288cc6335e 100644
--- a/ext/pdo_sqlite/php_pdo_sqlite_int.h
+++ b/ext/pdo_sqlite/php_pdo_sqlite_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_sqlite/sqlite_driver.c b/ext/pdo_sqlite/sqlite_driver.c
index 0f4a2456a1..35fa547f27 100644
--- a/ext/pdo_sqlite/sqlite_driver.c
+++ b/ext/pdo_sqlite/sqlite_driver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_sqlite/sqlite_statement.c b/ext/pdo_sqlite/sqlite_statement.c
index e970ad3e06..ba49f7324c 100644
--- a/ext/pdo_sqlite/sqlite_statement.c
+++ b/ext/pdo_sqlite/sqlite_statement.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pdo_sqlite/tests/bug66033.phpt b/ext/pdo_sqlite/tests/bug66033.phpt
new file mode 100644
index 0000000000..28da3b54bf
--- /dev/null
+++ b/ext/pdo_sqlite/tests/bug66033.phpt
@@ -0,0 +1,33 @@
+--TEST--
+Bug #66033 (Segmentation Fault when constructor of PDO statement throws an exception)
+--SKIPIF--
+<?php
+if (!extension_loaded('pdo_sqlite')) print 'skip not loaded';
+?>
+--FILE--
+<?php
+class DBStatement extends PDOStatement {
+ public $dbh;
+ protected function __construct($dbh) {
+ $this->dbh = $dbh;
+ throw new Exception("Blah");
+ }
+}
+
+$pdo = new PDO('sqlite::memory:', null, null);
+$pdo->setAttribute(PDO::ATTR_STATEMENT_CLASS, array('DBStatement',
+ array($pdo)));
+$pdo->exec("CREATE TABLE IF NOT EXISTS messages (
+ id INTEGER PRIMARY KEY,
+ title TEXT,
+ message TEXT,
+ time INTEGER)");
+
+try {
+ $pdoStatement = $pdo->query("select * from messages");
+} catch (Exception $e) {
+ var_dump($e->getMessage());
+}
+?>
+--EXPECTF--
+string(4) "Blah"
diff --git a/ext/pgsql/pgsql.c b/ext/pgsql/pgsql.c
index 32d407af70..be915ae5ae 100644
--- a/ext/pgsql/pgsql.c
+++ b/ext/pgsql/pgsql.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -15,8 +15,8 @@
| Authors: Zeev Suraski <zeev@zend.com> |
| Jouni Ahto <jouni.ahto@exdec.fi> |
| Yasuo Ohgaki <yohgaki@php.net> |
- | Youichi Iwakiri <yiwakiri@st.rim.or.jp> (pg_copy_*) |
- | Chris Kings-Lynne <chriskl@php.net> (v3 protocol) |
+ | Youichi Iwakiri <yiwakiri@st.rim.or.jp> (pg_copy_*) |
+ | Chris Kings-Lynne <chriskl@php.net> (v3 protocol) |
+----------------------------------------------------------------------+
*/
@@ -37,6 +37,9 @@
#include "ext/standard/php_standard.h"
#include "ext/standard/php_smart_str.h"
#include "ext/ereg/php_regex.h"
+#ifdef PHP_WIN32
+# include "win32/time.h"
+#endif
#undef PACKAGE_BUGREPORT
#undef PACKAGE_NAME
@@ -743,6 +746,105 @@ ZEND_GET_MODULE(pgsql)
static int le_link, le_plink, le_result, le_lofp, le_string;
+/* Compatibility definitions */
+
+#ifndef HAVE_PGSQL_WITH_MULTIBYTE_SUPPORT
+#define pg_encoding_to_char(x) "SQL_ASCII"
+#endif
+
+#if !HAVE_PQESCAPE_CONN
+#define PQescapeStringConn(conn, to, form, len, error) PQescapeString(to, from, len)
+#endif
+
+#if HAVE_PQESCAPELITERAL
+#define PGSQLescapeLiteral(conn, str, len) PQescapeLiteral(conn, str, len)
+#define PGSQLescapeIdentifier(conn, str, len) PQescapeIdentifier(conn, str, len)
+#define PGSQLfree(a) PQfreemem(a)
+#else
+#define PGSQLescapeLiteral(conn, str, len) php_pgsql_PQescapeInternal(conn, str, len, 1, 0)
+#define PGSQLescapeLiteral2(conn, str, len) php_pgsql_PQescapeInternal(conn, str, len, 1, 1)
+#define PGSQLescapeIdentifier(conn, str, len) php_pgsql_PQescapeInternal(conn, str, len, 0, 0)
+#define PGSQLfree(a) efree(a)
+
+/* emulate libpq's PQescapeInternal() 9.0 or later */
+static char* php_pgsql_PQescapeInternal(PGconn *conn, const char *str, size_t len, int escape_literal, int safe) {
+ char *result, *rp, *s;
+ size_t tmp_len;
+
+ if (!conn) {
+ return NULL;
+ }
+
+ /* allocate enough memory */
+ rp = result = (char *)safe_emalloc(len, 2, 5); /* leading " E" needs extra 2 bytes + quote_chars on both end for 2 bytes + NULL */
+
+ if (escape_literal) {
+ size_t new_len;
+
+ if (safe) {
+ char *tmp = (char *)safe_emalloc(len, 2, 1);
+ *rp++ = '\'';
+ /* PQescapeString does not escape \, but it handles multibyte chars safely.
+ This escape is incompatible with PQescapeLiteral. */
+ new_len = PQescapeStringConn(conn, tmp, str, len, NULL);
+ strncpy(rp, tmp, new_len);
+ efree(tmp);
+ rp += new_len;
+ } else {
+ char *encoding;
+ /* This is compatible with PQescapeLiteral, but it cannot handle multbyte chars
+ such as SJIS, BIG5. Raise warning and return NULL by checking
+ client_encoding. */
+ encoding = (char *) pg_encoding_to_char(PQclientEncoding(conn));
+ if (!strncmp(encoding, "SJIS", sizeof("SJIS")-1) ||
+ !strncmp(encoding, "SHIFT_JIS_2004", sizeof("SHIFT_JIS_2004")-1) ||
+ !strncmp(encoding, "BIG5", sizeof("BIG5")-1) ||
+ !strncmp(encoding, "GB18030", sizeof("GB18030")-1) ||
+ !strncmp(encoding, "GBK", sizeof("GBK")-1) ||
+ !strncmp(encoding, "JOHAB", sizeof("JOHAB")-1) ||
+ !strncmp(encoding, "UHC", sizeof("UHC")-1) ) {
+ TSRMLS_FETCH();
+
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "Unsafe encoding is used. Do not use '%s' encoding or use PostgreSQL 9.0 or later libpq.", encoding);
+ }
+ /* check backslashes */
+ tmp_len = strspn(str, "\\");
+ if (tmp_len != len) {
+ /* add " E" for escaping slashes */
+ *rp++ = ' ';
+ *rp++ = 'E';
+ }
+ *rp++ = '\'';
+ for (s = (char *)str; s - str < len; ++s) {
+ if (*s == '\'' || *s == '\\') {
+ *rp++ = *s;
+ *rp++ = *s;
+ } else {
+ *rp++ = *s;
+ }
+ }
+ }
+ *rp++ = '\'';
+ } else {
+ /* Identifier escape. */
+ *rp++ = '"';
+ for (s = (char *)str; s - str < len; ++s) {
+ if (*s == '"') {
+ *rp++ = '"';
+ *rp++ = '"';
+ } else {
+ *rp++ = *s;
+ }
+ }
+ *rp++ = '"';
+ }
+ *rp = '\0';
+
+ return result;
+}
+#endif
+
+
/* {{{ _php_pgsql_trim_message */
static char * _php_pgsql_trim_message(const char *message, int *len)
{
@@ -771,16 +873,16 @@ static inline char * _php_pgsql_trim_result(PGconn * pgsql, char **buf)
#define PQErrorMessageTrim(pgsql, buf) _php_pgsql_trim_result(pgsql, buf)
-#define PHP_PQ_ERROR(text, pgsql) { \
- char *msgbuf = _php_pgsql_trim_message(PQerrorMessage(pgsql), NULL); \
- php_error_docref(NULL TSRMLS_CC, E_WARNING, text, msgbuf); \
- efree(msgbuf); \
+#define PHP_PQ_ERROR(text, pgsql) { \
+ char *msgbuf = _php_pgsql_trim_message(PQerrorMessage(pgsql), NULL); \
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, text, msgbuf); \
+ efree(msgbuf); \
} \
/* {{{ php_pgsql_set_default_link
*/
static void php_pgsql_set_default_link(int id TSRMLS_DC)
-{
+{
zend_list_addref(id);
if (PGG(default_link) != -1) {
@@ -848,10 +950,10 @@ static void _php_pgsql_notice_ptr_dtor(void **ptr)
{
php_pgsql_notice *notice = (php_pgsql_notice *)*ptr;
if (notice) {
- efree(notice->message);
- efree(notice);
- notice = NULL;
- }
+ efree(notice->message);
+ efree(notice);
+ notice = NULL;
+ }
}
/* }}} */
@@ -941,57 +1043,7 @@ static int _php_pgsql_detect_identifier_escape(const char *identifier, size_t le
return SUCCESS;
}
-#if !HAVE_PQESCAPELITERAL
-/* {{{ _php_pgsql_escape_identifier
- * Since PQescapeIdentifier() is unavailable (PostgreSQL 9.0 <), idenfifers
- * should be escaped by pgsql module.
- * Note: this function does not care for encoding. Therefore users should not
- * use this with SJIS/BIG5 etc. (i.e. Encoding base injection may possible with
- * before PostgreSQL 9.0)
- */
-static char *_php_pgsql_escape_identifier(const char *field, size_t field_len)
-{
- ulong field_escaped_len = field_len*2 + 3;
- ulong i, j = 0;
- char *field_escaped;
-
- field_escaped = (char *)malloc(field_escaped_len);
- field_escaped[j++] = '"';
- for (i = 0; i < field_len; i++) {
- if (field[i] == '"') {
- field_escaped[j++] = '"';
- field_escaped[j++] = '"';
- } else {
- field_escaped[j++] = field[i];
- }
- }
- field_escaped[j++] = '"';
- field_escaped[j] = '\0';
- return field_escaped;
-}
-/* }}} */
-#endif
-
-/* {{{ _php_pgsql_strndup, no strndup should be used */
-static char *_php_pgsql_strndup(const char *s, size_t len)
-{
- char *new;
-
- if (NULL == s) {
- return (char *)NULL;
- }
-
- new = (char *) malloc(len + 1);
-
- if (NULL == new) {
- return (char *)NULL;
- }
- new[len] = '\0';
-
- return memmove(new, s, len);
-}
-/* }}} */
/* {{{ PHP_INI
*/
@@ -1020,7 +1072,7 @@ static PHP_GINIT_FUNCTION(pgsql)
PHP_MINIT_FUNCTION(pgsql)
{
REGISTER_INI_ENTRIES();
-
+
le_link = zend_register_list_destructors_ex(_close_pgsql_link, NULL, "pgsql link", module_number);
le_plink = zend_register_list_destructors_ex(NULL, _close_pgsql_plink, "pgsql link persistent", module_number);
le_result = zend_register_list_destructors_ex(_free_result, NULL, "pgsql result", module_number);
@@ -1156,7 +1208,7 @@ PHP_MINFO_FUNCTION(pgsql)
#else
php_info_print_table_row(2, "SSL support", "disabled");
#endif
-#endif /* HAVE_PG_CONFIG_H */
+#endif /* HAVE_PG_CONFIG_H */
snprintf(buf, sizeof(buf), "%ld", PGG(num_persistent));
php_info_print_table_row(2, "Active Persistent Links", buf);
snprintf(buf, sizeof(buf), "%ld", PGG(num_links));
@@ -1224,7 +1276,7 @@ static void php_pgsql_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent)
break;
}
}
-
+
if (persistent && PGG(allow_persistent)) {
zend_rsrc_list_entry *le;
@@ -1307,7 +1359,7 @@ static void php_pgsql_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent)
ZEND_REGISTER_RESOURCE(return_value, pgsql, le_plink);
} else { /* Non persistent connection */
zend_rsrc_list_entry *index_ptr,new_index_ptr;
-
+
/* first we check the hash for the hashed_details key. if it exists,
* it should point us to the right offset where the actual pgsql link sits.
* if it doesn't, open a new pgsql link, add it to the resource list,
@@ -1371,7 +1423,7 @@ static void php_pgsql_do_connect(INTERNAL_FUNCTION_PARAMETERS, int persistent)
cleanup:
smart_str_free(&str);
return;
-
+
err:
smart_str_free(&str);
RETURN_FALSE;
@@ -1415,11 +1467,11 @@ PHP_FUNCTION(pg_close)
zval *pgsql_link = NULL;
int id = -1, argc = ZEND_NUM_ARGS();
PGconn *pgsql;
-
+
if (zend_parse_parameters(argc TSRMLS_CC, "|r", &pgsql_link) == FAILURE) {
return;
}
-
+
if (argc == 0) {
id = PGG(default_link);
CHECK_DEFAULT_LINK(id);
@@ -1427,7 +1479,7 @@ PHP_FUNCTION(pg_close)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -1435,7 +1487,7 @@ PHP_FUNCTION(pg_close)
zend_list_delete(Z_RESVAL_P(pgsql_link));
}
- if (id!=-1
+ if (id!=-1
|| (pgsql_link && Z_RESVAL_P(pgsql_link)==PGG(default_link))) {
zend_list_delete(PGG(default_link));
PGG(default_link) = -1;
@@ -1454,6 +1506,7 @@ PHP_FUNCTION(pg_close)
#define PHP_PG_HOST 6
#define PHP_PG_VERSION 7
+
/* {{{ php_pgsql_get_link_info
*/
static void php_pgsql_get_link_info(INTERNAL_FUNCTION_PARAMETERS, int entry_type)
@@ -1474,7 +1527,7 @@ static void php_pgsql_get_link_info(INTERNAL_FUNCTION_PARAMETERS, int entry_type
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -1600,7 +1653,7 @@ PHP_FUNCTION(pg_parameter_status)
}
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -1631,7 +1684,7 @@ PHP_FUNCTION(pg_ping)
}
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -1706,7 +1759,7 @@ PHP_FUNCTION(pg_query)
} else {
status = (ExecStatusType) PQstatus(pgsql);
}
-
+
switch (status) {
case PGRES_EMPTY_QUERY:
case PGRES_BAD_RESPONSE:
@@ -1802,7 +1855,7 @@ PHP_FUNCTION(pg_query_params)
if (num_params > 0) {
int i = 0;
params = (char **)safe_emalloc(sizeof(char *), num_params, 0);
-
+
for(i = 0; i < num_params; i++) {
if (zend_hash_get_current_data(Z_ARRVAL_P(pv_param_arr), (void **) &tmp) == FAILURE) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,"Error getting parameter");
@@ -1899,10 +1952,10 @@ PHP_FUNCTION(pg_prepare)
return;
}
}
-
+
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -1929,7 +1982,7 @@ PHP_FUNCTION(pg_prepare)
} else {
status = (ExecStatusType) PQstatus(pgsql);
}
-
+
switch (status) {
case PGRES_EMPTY_QUERY:
case PGRES_BAD_RESPONSE:
@@ -2009,7 +2062,7 @@ PHP_FUNCTION(pg_execute)
if (num_params > 0) {
int i = 0;
params = (char **)safe_emalloc(sizeof(char *), num_params, 0);
-
+
for(i = 0; i < num_params; i++) {
if (zend_hash_get_current_data(Z_ARRVAL_P(pv_param_arr), (void **) &tmp) == FAILURE) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,"Error getting parameter");
@@ -2051,7 +2104,7 @@ PHP_FUNCTION(pg_execute)
} else {
status = (ExecStatusType) PQstatus(pgsql);
}
-
+
_php_pgsql_free_params(params, num_params);
switch (status) {
@@ -2203,7 +2256,7 @@ static char *get_field_name(PGconn *pgsql, Oid oid, HashTable *list TSRMLS_DC)
num_rows = PQntuples(result);
oid_offset = PQfnumber(result,"oid");
name_offset = PQfnumber(result,"typname");
-
+
for (i=0; i<num_rows; i++) {
if ((tmp_oid = PQgetvalue(result,i,oid_offset))==NULL) {
continue;
@@ -2213,7 +2266,7 @@ static char *get_field_name(PGconn *pgsql, Oid oid, HashTable *list TSRMLS_DC)
smart_str_appends(&str, "pgsql_oid_");
smart_str_appends(&str, tmp_oid);
smart_str_0(&str);
-
+
if ((tmp_name = PQgetvalue(result,i,name_offset))==NULL) {
continue;
}
@@ -2230,7 +2283,7 @@ static char *get_field_name(PGconn *pgsql, Oid oid, HashTable *list TSRMLS_DC)
smart_str_free(&str);
return ret;
}
-/* }}} */
+/* }}} */
#ifdef HAVE_PQFTABLE
/* {{{ proto mixed pg_field_table(resource result, int field_number[, bool oid_only])
@@ -2263,7 +2316,6 @@ PHP_FUNCTION(pg_field_table)
RETURN_FALSE;
}
-
if (return_oid) {
#if UINT_MAX > LONG_MAX /* Oid is unsigned int, we don't need this code, where LONG is wider */
if (oid > LONG_MAX) {
@@ -2293,7 +2345,6 @@ PHP_FUNCTION(pg_field_table)
smart_str_append_unsigned(&querystr, oid);
smart_str_0(&querystr);
-
if ((tmp_res = PQexec(pg_result->conn, querystr.c)) == NULL || PQresultStatus(tmp_res) != PGRES_TUPLES_OK) {
if (tmp_res) {
PQclear(tmp_res);
@@ -2321,8 +2372,8 @@ PHP_FUNCTION(pg_field_table)
}
}
-/* }}} */
-#endif
+/* }}} */
+#endif
#define PHP_PG_FIELD_NAME 1
#define PHP_PG_FIELD_SIZE 2
@@ -2338,11 +2389,11 @@ static void php_pgsql_get_field_info(INTERNAL_FUNCTION_PARAMETERS, int entry_typ
PGresult *pgsql_result;
pgsql_result_handle *pg_result;
Oid oid;
-
+
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rl", &result, &field) == FAILURE) {
return;
}
-
+
ZEND_FETCH_RESOURCE(pg_result, pgsql_result_handle *, &result, -1, "PostgreSQL result", le_result);
pgsql_result = pg_result->result;
@@ -2351,7 +2402,7 @@ static void php_pgsql_get_field_info(INTERNAL_FUNCTION_PARAMETERS, int entry_typ
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Bad field offset specified");
RETURN_FALSE;
}
-
+
switch (entry_type) {
case PHP_PG_FIELD_NAME:
Z_STRVAL_P(return_value) = PQfname(pgsql_result, field);
@@ -2438,11 +2489,11 @@ PHP_FUNCTION(pg_field_num)
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs", &result, &field, &field_len) == FAILURE) {
return;
}
-
+
ZEND_FETCH_RESOURCE(pg_result, pgsql_result_handle *, &result, -1, "PostgreSQL result", le_result);
pgsql_result = pg_result->result;
-
+
Z_LVAL_P(return_value) = PQfnumber(pgsql_result, field);
Z_TYPE_P(return_value) = IS_LONG;
}
@@ -2457,7 +2508,7 @@ PHP_FUNCTION(pg_fetch_result)
PGresult *pgsql_result;
pgsql_result_handle *pg_result;
int field_offset, pgsql_row, argc = ZEND_NUM_ARGS();
-
+
if (argc == 2) {
if (zend_parse_parameters(argc TSRMLS_CC, "rZ", &result, &field) == FAILURE) {
return;
@@ -2500,7 +2551,7 @@ PHP_FUNCTION(pg_fetch_result)
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Bad column offset specified");
RETURN_FALSE;
}
-
+
if (PQgetisnull(pgsql_result, pgsql_row, field_offset)) {
Z_TYPE_P(return_value) = IS_NULL;
} else {
@@ -2603,12 +2654,12 @@ static void php_pgsql_fetch_hash(INTERNAL_FUNCTION_PARAMETERS, long result_type,
data = safe_estrndup(element, element_len);
data_len = element_len;
-
+
if (result_type & PGSQL_NUM) {
add_index_stringl(return_value, i, data, data_len, should_copy);
should_copy=1;
}
-
+
if (result_type & PGSQL_ASSOC) {
field_name = PQfname(pgsql_result, i);
add_assoc_stringl(return_value, field_name, data, data_len, should_copy);
@@ -2621,11 +2672,11 @@ static void php_pgsql_fetch_hash(INTERNAL_FUNCTION_PARAMETERS, long result_type,
zval dataset = *return_value;
zend_fcall_info fci;
zend_fcall_info_cache fcc;
- zval *retval_ptr;
-
+ zval *retval_ptr;
+
object_and_properties_init(return_value, ce, NULL);
zend_merge_properties(return_value, Z_ARRVAL(dataset), 1 TSRMLS_CC);
-
+
if (ce->constructor) {
fci.size = sizeof(fci);
fci.function_table = &ce->function_table;
@@ -2637,7 +2688,7 @@ static void php_pgsql_fetch_hash(INTERNAL_FUNCTION_PARAMETERS, long result_type,
if (Z_TYPE_P(ctor_params) == IS_ARRAY) {
HashTable *ht = Z_ARRVAL_P(ctor_params);
Bucket *p;
-
+
fci.param_count = 0;
fci.params = safe_emalloc(sizeof(zval***), ht->nNumOfElements, 0);
p = ht->pListHead;
@@ -2666,7 +2717,7 @@ static void php_pgsql_fetch_hash(INTERNAL_FUNCTION_PARAMETERS, long result_type,
fcc.calling_scope = EG(scope);
fcc.called_scope = Z_OBJCE_P(return_value);
fcc.object_ptr = return_value;
-
+
if (zend_call_function(&fci, &fcc TSRMLS_CC) == FAILURE) {
zend_throw_exception_ex(zend_exception_get_default(TSRMLS_C), 0 TSRMLS_CC, "Could not execute %s::%s()", ce->name, ce->constructor->common.function_name);
} else {
@@ -2772,7 +2823,7 @@ PHP_FUNCTION(pg_fetch_all_columns)
array_init(return_value);
- if ((pg_numrows = PQntuples(pgsql_result)) <= 0) {
+ if ((pg_numrows = PQntuples(pgsql_result)) <= 0) {
return;
}
@@ -2781,7 +2832,7 @@ PHP_FUNCTION(pg_fetch_all_columns)
add_next_index_null(return_value);
} else {
add_next_index_string(return_value, PQgetvalue(pgsql_result, pg_row, colno), 1);
- }
+ }
}
}
/* }}} */
@@ -2803,7 +2854,7 @@ PHP_FUNCTION(pg_result_seek)
if (row < 0 || row >= PQntuples(pg_result->result)) {
RETURN_FALSE;
}
-
+
/* seek to offset */
pg_result->row = row;
RETURN_TRUE;
@@ -2833,7 +2884,7 @@ static void php_pgsql_data_info(INTERNAL_FUNCTION_PARAMETERS, int entry_type)
return;
}
}
-
+
ZEND_FETCH_RESOURCE(pg_result, pgsql_result_handle *, &result, -1, "PostgreSQL result", le_result);
pgsql_result = pg_result->result;
@@ -2853,7 +2904,7 @@ static void php_pgsql_data_info(INTERNAL_FUNCTION_PARAMETERS, int entry_type)
RETURN_FALSE;
}
}
-
+
switch(Z_TYPE_PP(field)) {
case IS_STRING:
convert_to_string_ex(field);
@@ -2868,7 +2919,7 @@ static void php_pgsql_data_info(INTERNAL_FUNCTION_PARAMETERS, int entry_type)
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Bad column offset specified");
RETURN_FALSE;
}
-
+
switch (entry_type) {
case PHP_PG_DATA_LENGTH:
Z_LVAL_P(return_value) = PQgetlength(pgsql_result, pgsql_row, field_offset);
@@ -2903,7 +2954,7 @@ PHP_FUNCTION(pg_free_result)
{
zval *result;
pgsql_result_handle *pg_result;
-
+
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &result) == FAILURE) {
return;
}
@@ -2931,7 +2982,7 @@ PHP_FUNCTION(pg_last_oid)
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "r", &result) == FAILURE) {
return;
}
-
+
ZEND_FETCH_RESOURCE(pg_result, pgsql_result_handle *, &result, -1, "PostgreSQL result", le_result);
pgsql_result = pg_result->result;
#ifdef HAVE_PQOIDVALUE
@@ -2962,18 +3013,18 @@ PHP_FUNCTION(pg_trace)
FILE *fp = NULL;
php_stream *stream;
id = PGG(default_link);
-
+
if (zend_parse_parameters(argc TSRMLS_CC, "s|sr", &z_filename, &z_filename_len, &mode, &mode_len, &pgsql_link) == FAILURE) {
return;
}
if (argc < 3) {
CHECK_DEFAULT_LINK(id);
- }
+ }
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3012,7 +3063,7 @@ PHP_FUNCTION(pg_untrace)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
PQuntrace(pgsql);
@@ -3024,10 +3075,10 @@ PHP_FUNCTION(pg_untrace)
Create a large object */
PHP_FUNCTION(pg_lo_create)
{
- zval *pgsql_link = NULL, *oid = NULL;
- PGconn *pgsql;
- Oid pgsql_oid, wanted_oid = InvalidOid;
- int id = -1, argc = ZEND_NUM_ARGS();
+ zval *pgsql_link = NULL, *oid = NULL;
+ PGconn *pgsql;
+ Oid pgsql_oid, wanted_oid = InvalidOid;
+ int id = -1, argc = ZEND_NUM_ARGS();
if (zend_parse_parameters(argc TSRMLS_CC, "|zz", &pgsql_link, &oid) == FAILURE) {
return;
@@ -3049,12 +3100,12 @@ PHP_FUNCTION(pg_lo_create)
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
if (oid) {
-#ifndef HAVE_PG_LO_CREATE
- php_error_docref(NULL TSRMLS_CC, E_NOTICE, "OID value passing not supported");
+#ifndef HAVE_PG_LO_CREATE
+ php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Passing OID value is not supported. Upgrade your PostgreSQL");
#else
switch (Z_TYPE_P(oid)) {
case IS_STRING:
- {
+ {
char *end_ptr;
wanted_oid = (Oid)strtoul(Z_STRVAL_P(oid), &end_ptr, 10);
if ((Z_STRVAL_P(oid)+Z_STRLEN_P(oid)) != end_ptr) {
@@ -3080,7 +3131,7 @@ PHP_FUNCTION(pg_lo_create)
RETURN_FALSE;
}
- PGSQL_RETURN_OID(pgsql_oid);
+ PGSQL_RETURN_OID(pgsql_oid);
#endif
}
@@ -3089,7 +3140,7 @@ PHP_FUNCTION(pg_lo_create)
RETURN_FALSE;
}
- PGSQL_RETURN_OID(pgsql_oid);
+ PGSQL_RETURN_OID(pgsql_oid);
}
/* }}} */
@@ -3151,7 +3202,7 @@ PHP_FUNCTION(pg_lo_unlink)
}
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3223,7 +3274,7 @@ PHP_FUNCTION(pg_lo_open)
}
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3315,8 +3366,8 @@ PHP_FUNCTION(pg_lo_close)
Read a large object */
PHP_FUNCTION(pg_lo_read)
{
- zval *pgsql_id;
- long len;
+ zval *pgsql_id;
+ long len;
int buf_len = PGSQL_LO_READ_BUF_SIZE, nbytes, argc = ZEND_NUM_ARGS();
char *buf;
pgLofp *pgsql;
@@ -3443,7 +3494,7 @@ PHP_FUNCTION(pg_lo_import)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3454,7 +3505,7 @@ PHP_FUNCTION(pg_lo_import)
Oid wanted_oid;
switch (Z_TYPE_P(oid)) {
case IS_STRING:
- {
+ {
char *end_ptr;
wanted_oid = (Oid)strtoul(Z_STRVAL_P(oid), &end_ptr, 10);
if ((Z_STRVAL_P(oid)+Z_STRLEN_P(oid)) != end_ptr) {
@@ -3576,13 +3627,13 @@ PHP_FUNCTION(pg_lo_export)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
if (lo_export(pgsql, oid, file_out)) {
RETURN_TRUE;
- }
+ }
RETURN_FALSE;
}
/* }}} */
@@ -3697,7 +3748,7 @@ PHP_FUNCTION(pg_set_client_encoding)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3731,10 +3782,6 @@ PHP_FUNCTION(pg_client_encoding)
/* Just do the same as found in PostgreSQL sources... */
-#ifndef HAVE_PGSQL_WITH_MULTIBYTE_SUPPORT
-#define pg_encoding_to_char(x) "SQL_ASCII"
-#endif
-
Z_STRVAL_P(return_value) = (char *) pg_encoding_to_char(PQclientEncoding(pgsql));
Z_STRLEN_P(return_value) = strlen(Z_STRVAL_P(return_value));
Z_STRVAL_P(return_value) = (char *) estrdup(Z_STRVAL_P(return_value));
@@ -3767,7 +3814,7 @@ PHP_FUNCTION(pg_end_copy)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -3903,7 +3950,7 @@ PHP_FUNCTION(pg_copy_to)
PHP_PQ_ERROR("getline failed: %s", pgsql);
RETURN_FALSE;
}
-
+
if (copybuf[0] == '\\' &&
copybuf[1] == '.' &&
copybuf[2] == '\0')
@@ -4111,12 +4158,11 @@ PHP_FUNCTION(pg_escape_string)
}
to = (char *) safe_emalloc(from_len, 2, 1);
-
#ifdef HAVE_PQESCAPE_CONN
if (pgsql_link != NULL || id != -1) {
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
to_len = (int) PQescapeStringConn(pgsql, to, from, (size_t)from_len, NULL);
- } else
+ } else
#endif
to_len = (int) PQescapeString(to, from, (size_t)from_len);
@@ -4191,7 +4237,7 @@ PHP_FUNCTION(pg_escape_bytea)
*/
static unsigned char * php_pgsql_unescape_bytea(unsigned char *strtext, size_t *retbuflen)
{
- size_t buflen;
+ size_t buflen;
unsigned char *buffer,
*sp,
*bp;
@@ -4251,7 +4297,7 @@ static unsigned char * php_pgsql_unescape_bytea(unsigned char *strtext, size_t *
memcpy(buf, sp-2, 3);
buf[3] = '\0';
start = buf;
- *bp = (unsigned char)strtoul(start, (char **)&end, 8);
+ *bp = (unsigned char)strtoul(start, (char **)&end, 8);
buflen -= 3;
state = 0;
}
@@ -4300,61 +4346,13 @@ PHP_FUNCTION(pg_unescape_bytea)
#endif
#ifdef HAVE_PQESCAPE
-#if !HAVE_PQESCAPELITERAL
-/* emulate libpq's PQescapeInternal() 9.0 or later */
-static char* php_pgsql_PQescapeInternal(PGconn *conn, const char *str, size_t len, int escape_literal) {
- char *result, *rp;
- const char *s;
- size_t tmp_len;
- int input_len = len;
- char quote_char = escape_literal ? '\'' : '"';
-
- if (!conn) {
- return NULL;
- }
-
- /*
- * NOTE: multibyte strings that could cointain slashes should be considered.
- * (e.g. SJIS, BIG5) However, it cannot be done without valid PGconn and mbstring.
- * Therefore, this function does not support such encodings currently.
- * FIXME: add encoding check and skip multibyte char bytes if there is vaild PGconn.
- */
-
- /* allocate enough memory */
- rp = result = (char *)emalloc(len*2 + 5); /* leading " E" needs extra 2 bytes + quote_chars on both end for 2 bytes + NULL */
-
- if (escape_literal) {
- /* check backslashes */
- tmp_len = strspn(str, "\\");
- if (tmp_len != len) {
- /* add " E" for escaping slashes */
- *rp++ = ' ';
- *rp++ = 'E';
- }
- }
- /* open quote */
- *rp++ = quote_char;
- for (s = str; s - str < input_len; ++s) {
- if (*s == quote_char || (escape_literal && *s == '\\')) {
- *rp++ = *s;
- *rp++ = *s;
- } else {
- *rp++ = *s;
- }
- }
- *rp++ = quote_char;
- *rp = '\0';
-
- return result;
-}
-#endif
-
static void php_pgsql_escape_internal(INTERNAL_FUNCTION_PARAMETERS, int escape_literal) {
char *from = NULL, *to = NULL;
zval *pgsql_link = NULL;
PGconn *pgsql;
int from_len;
int id = -1;
+ char *tmp;
switch (ZEND_NUM_ARGS()) {
case 1:
@@ -4382,30 +4380,18 @@ static void php_pgsql_escape_internal(INTERNAL_FUNCTION_PARAMETERS, int escape_l
php_error_docref(NULL TSRMLS_CC, E_WARNING,"Cannot get pgsql link");
RETURN_FALSE;
}
-#ifdef HAVE_PQESCAPELITERAL
- /* Use a block with a local var to avoid unused variable warnings */
- {
- char *tmp;
- if (escape_literal) {
- tmp = PQescapeLiteral(pgsql, from, (size_t)from_len);
- } else {
- tmp = PQescapeIdentifier(pgsql, from, (size_t)from_len);
- }
- if (!tmp) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING,"Failed to escape");
- RETURN_FALSE;
- }
- to = estrdup(tmp);
- PQfreemem(tmp);
+ if (escape_literal) {
+ tmp = PGSQLescapeLiteral(pgsql, from, (size_t)from_len);
+ } else {
+ tmp = PGSQLescapeIdentifier(pgsql, from, (size_t)from_len);
}
-#else
- to = php_pgsql_PQescapeInternal(pgsql, from, (size_t)from_len, escape_literal);
- if (!to) {
+ if (!tmp) {
php_error_docref(NULL TSRMLS_CC, E_WARNING,"Failed to escape");
RETURN_FALSE;
}
-#endif
+ to = estrdup(tmp);
+ PGSQLfree(tmp);
RETURN_STRING(to, 0);
}
@@ -4453,6 +4439,7 @@ PHP_FUNCTION(pg_result_error)
}
/* }}} */
+
#if HAVE_PQRESULTERRORFIELD
/* {{{ proto string pg_result_error_field(resource result, int fieldcode)
Get error message field associated with result */
@@ -4498,6 +4485,7 @@ PHP_FUNCTION(pg_result_error_field)
/* }}} */
#endif
+
/* {{{ proto int pg_connection_status(resource connection)
Get connection status */
PHP_FUNCTION(pg_connection_status)
@@ -4518,6 +4506,7 @@ PHP_FUNCTION(pg_connection_status)
/* }}} */
+
#if HAVE_PGTRANSACTIONSTATUS
/* {{{ proto int pg_transaction_status(resource connection)
Get transaction status */
@@ -4540,6 +4529,7 @@ PHP_FUNCTION(pg_transaction_status)
/* }}} */
+
/* {{{ proto bool pg_connection_reset(resource connection)
Reset connection (reconnect) */
PHP_FUNCTION(pg_connection_reset)
@@ -4561,12 +4551,13 @@ PHP_FUNCTION(pg_connection_reset)
}
RETURN_TRUE;
}
-
/* }}} */
+
#define PHP_PG_ASYNC_IS_BUSY 1
#define PHP_PG_ASYNC_REQUEST_CANCEL 2
-
+
+
/* {{{ php_pgsql_flush_query
*/
static int php_pgsql_flush_query(PGconn *pgsql TSRMLS_DC)
@@ -4586,7 +4577,8 @@ static int php_pgsql_flush_query(PGconn *pgsql TSRMLS_DC)
return leftover;
}
/* }}} */
-
+
+
/* {{{ php_pgsql_do_async
*/
static void php_pgsql_do_async(INTERNAL_FUNCTION_PARAMETERS, int entry_type)
@@ -4816,7 +4808,7 @@ PHP_FUNCTION(pg_send_prepare)
if (pgsql_link == NULL && id == -1) {
RETURN_FALSE;
- }
+ }
ZEND_FETCH_RESOURCE2(pgsql, PGconn *, &pgsql_link, id, "PostgreSQL link", le_link, le_plink);
@@ -5104,7 +5096,7 @@ PHP_PGSQL_API int php_pgsql_meta_data(PGconn *pg_link, const char *table_name, z
size_t new_len;
int i, num_rows;
zval *elem;
-
+
if (!*table_name) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "The table name must be specified");
return FAILURE;
@@ -5124,25 +5116,17 @@ PHP_PGSQL_API int php_pgsql_meta_data(PGconn *pg_link, const char *table_name, z
"FROM pg_class as c, pg_attribute a, pg_type t, pg_namespace n "
"WHERE a.attnum > 0 AND a.attrelid = c.oid AND c.relname = '");
escaped = (char *)safe_emalloc(strlen(tmp_name2), 2, 1);
-#if HAVE_PQESCAPE_CONN
new_len = PQescapeStringConn(pg_link, escaped, tmp_name2, strlen(tmp_name2), NULL);
-#else
- new_len = PQescapeString(escaped, tmp_name2, strlen(tmp_name2));
-#endif
if (new_len) {
- smart_str_appends(&querystr, escaped);
+ smart_str_appendl(&querystr, escaped, new_len);
}
efree(escaped);
smart_str_appends(&querystr, "' AND c.relnamespace = n.oid AND n.nspname = '");
escaped = (char *)safe_emalloc(strlen(tmp_name), 2, 1);
-#if HAVE_PQESCAPE_CONN
new_len = PQescapeStringConn(pg_link, escaped, tmp_name, strlen(tmp_name), NULL);
-#else
- new_len = PQescapeString(escaped, tmp_name, strlen(tmp_name));
-#endif
if (new_len) {
- smart_str_appends(&querystr, escaped);
+ smart_str_appendl(&querystr, escaped, new_len);
}
efree(escaped);
@@ -5205,7 +5189,7 @@ PHP_FUNCTION(pg_meta_data)
uint table_name_len;
PGconn *pgsql;
int id = -1;
-
+
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rs",
&pgsql_link, &table_name, &table_name_len) == FAILURE) {
return;
@@ -5232,13 +5216,14 @@ PHP_FUNCTION(pg_meta_data)
}
/* }}} */
+
/* {{{ php_pgsql_get_data_type
*/
static php_pgsql_data_type php_pgsql_get_data_type(const char *type_name, size_t len)
{
- /* This is stupid way to do. I'll fix it when I decied how to support
+ /* This is stupid way to do. I'll fix it when I decied how to support
user defined types. (Yasuo) */
-
+
/* boolean */
if (!strcmp(type_name, "bool")|| !strcmp(type_name, "boolean"))
return PG_BOOL;
@@ -5317,25 +5302,35 @@ static php_pgsql_data_type php_pgsql_get_data_type(const char *type_name, size_t
return PG_POLYGON;
if (!strcmp(type_name, "circle"))
return PG_CIRCLE;
-
+
return PG_UNKNOWN;
}
/* }}} */
/* {{{ php_pgsql_convert_match
- * test field value with regular expression specified.
+ * test field value with regular expression specified.
*/
-static int php_pgsql_convert_match(const char *str, const char *regex , int icase TSRMLS_DC)
+static int php_pgsql_convert_match(const char *str, size_t str_len, const char *regex , int icase TSRMLS_DC)
{
- regex_t re;
+ regex_t re;
regmatch_t *subs;
int regopt = REG_EXTENDED;
int regerr, ret = SUCCESS;
+ int i;
+
+ /* Check invalid chars for POSIX regex */
+ for (i = 0; i < str_len; i++) {
+ if (str[i] == '\n' ||
+ str[i] == '\r' ||
+ str[i] == '\0' ) {
+ return FAILURE;
+ }
+ }
if (icase) {
regopt |= REG_ICASE;
}
-
+
regerr = regcomp(&re, regex, regopt);
if (regerr) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot compile regex");
@@ -5346,7 +5341,7 @@ static int php_pgsql_convert_match(const char *str, const char *regex , int icas
regerr = regexec(&re, str, re.re_nsub+1, subs, 0);
if (regerr == REG_NOMATCH) {
-#ifdef PHP_DEBUG
+#ifdef PHP_DEBUG
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "'%s' does not match with '%s'", str, regex);
#endif
ret = FAILURE;
@@ -5368,7 +5363,7 @@ static int php_pgsql_convert_match(const char *str, const char *regex , int icas
static int php_pgsql_add_quotes(zval *src, zend_bool should_free TSRMLS_DC)
{
smart_str str = {0};
-
+
assert(Z_TYPE_P(src) == IS_STRING);
assert(should_free == 1 || should_free == 0);
@@ -5377,7 +5372,7 @@ static int php_pgsql_add_quotes(zval *src, zend_bool should_free TSRMLS_DC)
smart_str_appendl(&str, Z_STRVAL_P(src), Z_STRLEN_P(src));
smart_str_appendc(&str, '\'');
smart_str_0(&str);
-
+
if (should_free) {
efree(Z_STRVAL_P(src));
}
@@ -5401,7 +5396,7 @@ static int php_pgsql_add_quotes(zval *src, zend_bool should_free TSRMLS_DC)
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Detected NULL for 'NOT NULL' field '%s'", field ); \
err = 1; \
} \
- }
+ }
/* {{{ php_pgsql_convert
* check and convert array values (fieldname=>vlaue pair) for sql
@@ -5415,7 +5410,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
zval *meta, **def, **type, **not_null, **has_default, **is_enum, **val, *new_val;
int key_type, err = 0, skip_field;
php_pgsql_data_type data_type;
-
+
assert(pg_link != NULL);
assert(Z_TYPE_P(values) == IS_ARRAY);
assert(Z_TYPE_P(result) == IS_ARRAY);
@@ -5438,7 +5433,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
zend_hash_move_forward_ex(Z_ARRVAL_P(values), &pos)) {
skip_field = 0;
new_val = NULL;
-
+
if ((key_type = zend_hash_get_current_key_ex(Z_ARRVAL_P(values), &field, &field_len, &num_idx, 0, &pos)) == HASH_KEY_NON_EXISTENT) {
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Failed to get array key type");
err = 1;
@@ -5519,7 +5514,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_LONG:
case IS_BOOL:
if (Z_LVAL_PP(val)) {
@@ -5542,7 +5537,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects string, null, long or boolelan value for PostgreSQL '%s' (%s)", Z_STRVAL_PP(type), field);
}
break;
-
+
case PG_OID:
case PG_INT2:
case PG_INT4:
@@ -5554,7 +5549,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([+-]{0,1}[0-9]+)$", 0 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([+-]{0,1}[0-9]+)$", 0 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5562,7 +5557,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_DOUBLE:
ZVAL_DOUBLE(new_val, Z_DVAL_PP(val));
convert_to_long_ex(&new_val);
@@ -5596,7 +5591,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([+-]{0,1}[0-9]+)|([+-]{0,1}[0-9]*[\\.][0-9]+)|([+-]{0,1}[0-9]+[\\.][0-9]*)$", 0 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([+-]{0,1}[0-9]+)|([+-]{0,1}[0-9]*[\\.][0-9]+)|([+-]{0,1}[0-9]+[\\.][0-9]*)$", 0 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5604,15 +5599,15 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_LONG:
ZVAL_LONG(new_val, Z_LVAL_PP(val));
break;
-
+
case IS_DOUBLE:
ZVAL_DOUBLE(new_val, Z_DVAL_PP(val));
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -5639,26 +5634,20 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
else {
+ char *tmp;
Z_TYPE_P(new_val) = IS_STRING;
-#if HAVE_PQESCAPE_CONN
- {
- char *tmp;
- tmp = (char *)safe_emalloc(Z_STRLEN_PP(val), 2, 1);
- Z_STRLEN_P(new_val) = (int)PQescapeStringConn(pg_link, tmp, Z_STRVAL_PP(val), Z_STRLEN_PP(val), NULL);
- Z_STRVAL_P(new_val) = tmp;
- }
-#else
- Z_STRVAL_P(new_val) = (int)PQescapeString(Z_STRVAL_PP(val), Z_STRLEN_PP(val), &Z_STRLEN_P(new_val), 0 TSRMLS_CC);
-#endif
+ tmp = (char *)safe_emalloc(Z_STRLEN_PP(val), 2, 1);
+ Z_STRLEN_P(new_val) = (int)PQescapeStringConn(pg_link, tmp, Z_STRVAL_PP(val), Z_STRLEN_PP(val), NULL);
+ Z_STRVAL_P(new_val) = tmp;
php_pgsql_add_quotes(new_val, 1 TSRMLS_CC);
}
break;
-
+
case IS_LONG:
ZVAL_LONG(new_val, Z_LVAL_PP(val));
convert_to_string_ex(&new_val);
break;
-
+
case IS_DOUBLE:
ZVAL_DOUBLE(new_val, Z_DVAL_PP(val));
convert_to_string_ex(&new_val);
@@ -5676,7 +5665,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects NULL, string, long or double value for PostgreSQL '%s' (%s)", Z_STRVAL_PP(type), field);
}
break;
-
+
case PG_UNIX_TIME:
case PG_UNIX_TIME_INTERVAL:
/* these are the actallay a integer */
@@ -5687,25 +5676,25 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: Better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^[0-9]+$", 0 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^[0-9]+$", 0 TSRMLS_CC) == FAILURE) {
err = 1;
- }
+ }
else {
ZVAL_STRING(new_val, Z_STRVAL_PP(val), 1);
convert_to_long_ex(&new_val);
}
}
break;
-
+
case IS_DOUBLE:
ZVAL_DOUBLE(new_val, Z_DVAL_PP(val));
convert_to_long_ex(&new_val);
break;
-
+
case IS_LONG:
ZVAL_LONG(new_val, Z_LVAL_PP(val));
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -5718,7 +5707,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects NULL, string, long or double value for '%s' (%s)", Z_STRVAL_PP(type), field);
}
break;
-
+
case PG_CIDR:
case PG_INET:
switch (Z_TYPE_PP(val)) {
@@ -5728,7 +5717,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: Better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([0-9]{1,3}\\.){3}[0-9]{1,3}(/[0-9]{1,2}){0,1}$", 0 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([0-9]{1,3}\\.){3}[0-9]{1,3}(/[0-9]{1,2}){0,1}$", 0 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5744,13 +5733,13 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
default:
err = 1;
- }
+ }
PGSQL_CONV_CHECK_IGNORE();
if (err) {
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects NULL or string for '%s' (%s)", Z_STRVAL_PP(type), field);
}
break;
-
+
case PG_TIME_WITH_TIMEZONE:
case PG_TIMESTAMP:
case PG_TIMESTAMP_WITH_TIMEZONE:
@@ -5762,7 +5751,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
ZVAL_STRINGL(new_val, "NOW()", sizeof("NOW()")-1, 1);
} else {
/* FIXME: better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([0-9]{4}[/-][0-9]{1,2}[/-][0-9]{1,2})([ \\t]+(([0-9]{1,2}:[0-9]{1,2}){1}(:[0-9]{1,2}){0,1}(\\.[0-9]+){0,1}([ \\t]*([+-][0-9]{1,4}(:[0-9]{1,2}){0,1}|[-a-zA-Z_/+]{1,50})){0,1})){0,1}$", 1 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([0-9]{4}[/-][0-9]{1,2}[/-][0-9]{1,2})([ \\t]+(([0-9]{1,2}:[0-9]{1,2}){1}(:[0-9]{1,2}){0,1}(\\.[0-9]+){0,1}([ \\t]*([+-][0-9]{1,4}(:[0-9]{1,2}){0,1}|[-a-zA-Z_/+]{1,50})){0,1})){0,1}$", 1 TSRMLS_CC) == FAILURE) {
err = 1;
} else {
ZVAL_STRING(new_val, Z_STRVAL_PP(val), 1);
@@ -5770,7 +5759,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_NULL:
ZVAL_STRINGL(new_val, "NULL", sizeof("NULL")-1, 1);
break;
@@ -5783,7 +5772,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects NULL or string for PostgreSQL %s field (%s)", Z_STRVAL_PP(type), field);
}
break;
-
+
case PG_DATE:
switch(Z_TYPE_PP(val)) {
case IS_STRING:
@@ -5792,7 +5781,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([0-9]{4}[/-][0-9]{1,2}[/-][0-9]{1,2})$", 1 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([0-9]{4}[/-][0-9]{1,2}[/-][0-9]{1,2})$", 1 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5801,7 +5790,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -5823,7 +5812,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
else {
/* FIXME: better regex must be used */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^(([0-9]{1,2}:[0-9]{1,2}){1}(:[0-9]{1,2}){0,1})){0,1}$", 1 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^(([0-9]{1,2}:[0-9]{1,2}){1}(:[0-9]{1,2}){0,1})){0,1}$", 1 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5832,7 +5821,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -5869,10 +5858,10 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
Quantities of days, hours, minutes, and seconds can be specified without explicit
unit markings. For example, '1 12:59:10' is read the same as '1 day 12 hours 59 min 10
sec'.
- */
- if (php_pgsql_convert_match(Z_STRVAL_PP(val),
+ */
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val),
"^(@?[ \\t]+)?("
-
+
/* Textual time units and their abbreviations: */
"(([-+]?[ \\t]+)?"
"[0-9]+(\\.[0-9]*)?[ \\t]*"
@@ -5909,9 +5898,9 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
ZVAL_STRING(new_val, Z_STRVAL_PP(val), 1);
php_pgsql_add_quotes(new_val, 1 TSRMLS_CC);
}
- }
+ }
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -5953,12 +5942,12 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
Z_STRLEN_P(new_val) = s.len;
}
break;
-
+
case IS_LONG:
ZVAL_LONG(new_val, Z_LVAL_PP(val));
convert_to_string_ex(&new_val);
break;
-
+
case IS_DOUBLE:
ZVAL_DOUBLE(new_val, Z_DVAL_PP(val));
convert_to_string_ex(&new_val);
@@ -5985,7 +5974,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
ZVAL_STRING(new_val, "NULL", 1);
}
else {
- if (php_pgsql_convert_match(Z_STRVAL_PP(val), "^([0-9a-f]{2,2}:){5,5}[0-9a-f]{2,2}$", 1 TSRMLS_CC) == FAILURE) {
+ if (php_pgsql_convert_match(Z_STRVAL_PP(val), Z_STRLEN_PP(val), "^([0-9a-f]{2,2}:){5,5}[0-9a-f]{2,2}$", 1 TSRMLS_CC) == FAILURE) {
err = 1;
}
else {
@@ -5994,7 +5983,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
}
}
break;
-
+
case IS_NULL:
ZVAL_STRING(new_val, "NULL", 1);
break;
@@ -6029,7 +6018,7 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
err = 1;
break;
} /* switch */
-
+
if (err) {
zval_dtor(new_val);
FREE_ZVAL(new_val);
@@ -6041,16 +6030,12 @@ PHP_PGSQL_API int php_pgsql_convert(PGconn *pg_link, const char *table_name, con
size_t field_len = strlen(field);
if (_php_pgsql_detect_identifier_escape(field, field_len) == SUCCESS) {
- escaped = _php_pgsql_strndup(field, field_len);
+ add_assoc_zval(result, field, new_val);
} else {
-#if HAVE_PQESCAPELITERAL
- escaped = PQescapeIdentifier(pg_link, field, field_len);
-#else
- escaped = _php_pgsql_escape_identifier(field, field_len);
-#endif
+ escaped = PGSQLescapeIdentifier(pg_link, field, field_len);
+ add_assoc_zval(result, escaped, new_val);
+ PGSQLfree(escaped);
}
- add_assoc_zval(result, escaped, new_val);
- free(escaped);
}
} /* for */
zval_dtor(meta);
@@ -6075,7 +6060,7 @@ PHP_FUNCTION(pg_convert)
ulong option = 0;
PGconn *pg_link;
int id = -1;
-
+
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC,
"rsa|l", &pgsql_link, &table_name, &table_name_len, &values, &option) == FAILURE) {
return;
@@ -6135,31 +6120,24 @@ static inline void build_tablename(smart_str *querystr, PGconn *pg_link, const c
token = php_strtok_r(table_copy, ".", &tmp);
len = strlen(token);
if (_php_pgsql_detect_identifier_escape(token, len) == SUCCESS) {
- escaped = _php_pgsql_strndup(token, len);
+ smart_str_appendl(querystr, token, len);
} else {
-#if HAVE_PQESCAPELITERAL
- escaped = PQescapeIdentifier(pg_link, token, len);
-#else
- escaped = _php_pgsql_escape_identifier(token, len);
-#endif
+ escaped = PGSQLescapeIdentifier(pg_link, token, len);
+ smart_str_appends(querystr, escaped);
+ PGSQLfree(escaped);
}
- smart_str_appends(querystr, escaped);
- free(escaped);
if (tmp && *tmp) {
len = strlen(tmp);
/* "schema"."table" format */
if (_php_pgsql_detect_identifier_escape(tmp, len) == SUCCESS) {
- escaped = _php_pgsql_strndup(tmp, len);
+ smart_str_appendc(querystr, '.');
+ smart_str_appendl(querystr, tmp, len);
} else {
-#if HAVE_PQESCAPELITERAL
- escaped = PQescapeIdentifier(pg_link, tmp, len);
-#else
- escaped = _php_pgsql_escape_identifier(tmp, len);
-#endif
+ escaped = PGSQLescapeIdentifier(pg_link, tmp, len);
+ smart_str_appendc(querystr, '.');
+ smart_str_appends(querystr, escaped);
+ PGSQLfree(escaped);
}
- smart_str_appendc(querystr, '.');
- smart_str_appends(querystr, escaped);
- free(escaped);
}
efree(table_copy);
}
@@ -6259,7 +6237,7 @@ no_values:
cleanup:
if (!(opt & PGSQL_DML_NO_CONV) && converted) {
- zval_dtor(converted);
+ zval_dtor(converted);
FREE_ZVAL(converted);
}
if (ret == SUCCESS && (opt & PGSQL_DML_STRING)) {
@@ -6320,7 +6298,7 @@ static inline int build_assignment_string(smart_str *querystr, HashTable *ht, in
for (zend_hash_internal_pointer_reset_ex(ht, &pos);
zend_hash_get_current_data_ex(ht, (void **)&val, &pos) == SUCCESS;
zend_hash_move_forward_ex(ht, &pos)) {
- key_type = zend_hash_get_current_key_ex(ht, &fld, &fld_len, &num_idx, 0, &pos);
+ key_type = zend_hash_get_current_key_ex(ht, &fld, &fld_len, &num_idx, 0, &pos);
if (key_type == HASH_KEY_IS_LONG) {
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Expects associative array for values to be inserted");
return -1;
@@ -6331,7 +6309,7 @@ static inline int build_assignment_string(smart_str *querystr, HashTable *ht, in
} else {
smart_str_appendc(querystr, '=');
}
-
+
switch(Z_TYPE_PP(val)) {
case IS_STRING:
smart_str_appendl(querystr, Z_STRVAL_PP(val), Z_STRLEN_PP(val));
@@ -6460,7 +6438,7 @@ PHP_FUNCTION(pg_update)
RETURN_STRING(sql, 0);
}
RETURN_TRUE;
-}
+}
/* }}} */
/* {{{ php_pgsql_delete
@@ -6507,7 +6485,7 @@ PHP_PGSQL_API int php_pgsql_delete(PGconn *pg_link, const char *table, zval *ids
cleanup:
if (!(opt & PGSQL_DML_NO_CONV)) {
- zval_dtor(ids_converted);
+ zval_dtor(ids_converted);
FREE_ZVAL(ids_converted);
}
if (ret == SUCCESS && (opt & PGSQL_DML_STRING)) {
@@ -6611,7 +6589,7 @@ PHP_PGSQL_API int php_pgsql_select(PGconn *pg_link, const char *table, zval *ids
assert(Z_TYPE_P(ids_array) == IS_ARRAY);
assert(Z_TYPE_P(ret_array) == IS_ARRAY);
assert(!(opt & ~(PGSQL_CONV_OPTS|PGSQL_DML_NO_CONV|PGSQL_DML_EXEC|PGSQL_DML_ASYNC|PGSQL_DML_STRING)));
-
+
if (zend_hash_num_elements(Z_ARRVAL_P(ids_array)) == 0) {
return FAILURE;
}
@@ -6645,7 +6623,7 @@ PHP_PGSQL_API int php_pgsql_select(PGconn *pg_link, const char *table, zval *ids
cleanup:
if (!(opt & PGSQL_DML_NO_CONV)) {
- zval_dtor(ids_converted);
+ zval_dtor(ids_converted);
FREE_ZVAL(ids_converted);
}
if (ret == SUCCESS && (opt & PGSQL_DML_STRING)) {
@@ -6693,7 +6671,7 @@ PHP_FUNCTION(pg_select)
RETURN_STRING(sql, 0);
}
return;
-}
+}
/* }}} */
#endif
diff --git a/ext/pgsql/php_pgsql.h b/ext/pgsql/php_pgsql.h
index 63f50f0f99..d0853d603e 100644
--- a/ext/pgsql/php_pgsql.h
+++ b/ext/pgsql/php_pgsql.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -16,7 +16,7 @@
| Jouni Ahto <jouni.ahto@exdec.fi> |
+----------------------------------------------------------------------+
*/
-
+
/* $Id$ */
#ifndef PHP_PGSQL_H
@@ -257,7 +257,7 @@ typedef enum _php_pgsql_data_type {
PG_PATH,
PG_POLYGON,
PG_CIRCLE,
- /* unkown and system */
+ /* unknown and system */
PG_UNKNOWN
} php_pgsql_data_type;
diff --git a/ext/phar/dirstream.c b/ext/phar/dirstream.c
index 98af1bffc2..c5c2c69448 100644
--- a/ext/phar/dirstream.c
+++ b/ext/phar/dirstream.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar:// stream wrapper support |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/dirstream.h b/ext/phar/dirstream.h
index 9b07c9d799..1fe2344d2e 100644
--- a/ext/phar/dirstream.h
+++ b/ext/phar/dirstream.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/func_interceptors.c b/ext/phar/func_interceptors.c
index 00cb92ff13..87411fc98d 100644
--- a/ext/phar/func_interceptors.c
+++ b/ext/phar/func_interceptors.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/func_interceptors.h b/ext/phar/func_interceptors.h
index 59d6bf6291..ff271460fe 100644
--- a/ext/phar/func_interceptors.h
+++ b/ext/phar/func_interceptors.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/phar.1.in b/ext/phar/phar.1.in
index 259a2bae86..52c3046222 100644
--- a/ext/phar/phar.1.in
+++ b/ext/phar/phar.1.in
@@ -507,7 +507,7 @@ contributors all around the world.
.SH VERSION INFORMATION
This manpage describes \fBphar\fP, version @PHP_VERSION@.
.SH COPYRIGHT
-Copyright \(co 1997\-2013 The PHP Group
+Copyright \(co 1997\-2014 The PHP Group
.LP
This source file is subject to version 3.01 of the PHP license,
that is bundled with this package in the file LICENSE, and is
diff --git a/ext/phar/phar.c b/ext/phar/phar.c
index ec8e5fbde7..a5488937a8 100644
--- a/ext/phar/phar.c
+++ b/ext/phar/phar.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -27,9 +27,7 @@
static void destroy_phar_data(void *pDest);
ZEND_DECLARE_MODULE_GLOBALS(phar)
-#if PHP_VERSION_ID >= 50300
char *(*phar_save_resolve_path)(const char *filename, int filename_len TSRMLS_DC);
-#endif
/**
* set's phar->is_writeable based on the current INI value
@@ -3321,31 +3319,18 @@ static size_t phar_zend_stream_reader(void *handle, char *buf, size_t len TSRMLS
}
/* }}} */
-#if PHP_VERSION_ID >= 50300
static size_t phar_zend_stream_fsizer(void *handle TSRMLS_DC) /* {{{ */
{
return ((phar_archive_data*)handle)->halt_offset + 32;
} /* }}} */
-#else /* PHP_VERSION_ID */
-
-static long phar_stream_fteller_for_zend(void *handle TSRMLS_DC) /* {{{ */
-{
- return (long)php_stream_tell(phar_get_pharfp((phar_archive_data*)handle TSRMLS_CC));
-}
-/* }}} */
-#endif
-
zend_op_array *(*phar_orig_compile_file)(zend_file_handle *file_handle, int type TSRMLS_DC);
-#if PHP_VERSION_ID >= 50300
#define phar_orig_zend_open zend_stream_open_function
+
static char *phar_resolve_path(const char *filename, int filename_len TSRMLS_DC)
{
return phar_find_in_include_path((char *) filename, filename_len, NULL TSRMLS_CC);
}
-#else
-int (*phar_orig_zend_open)(const char *filename, zend_file_handle *handle TSRMLS_DC);
-#endif
static zend_op_array *phar_compile_file(zend_file_handle *file_handle, int type TSRMLS_DC) /* {{{ */
{
@@ -3378,7 +3363,6 @@ static zend_op_array *phar_compile_file(zend_file_handle *file_handle, int type
}
} else if (phar->flags & PHAR_FILE_COMPRESSION_MASK) {
/* compressed phar */
-#if PHP_VERSION_ID >= 50300
file_handle->type = ZEND_HANDLE_STREAM;
/* we do our own reading directly from the phar, don't change the next line */
file_handle->handle.stream.handle = phar;
@@ -3390,18 +3374,6 @@ static zend_op_array *phar_compile_file(zend_file_handle *file_handle, int type
php_stream_rewind(PHAR_GLOBALS->cached_fp[phar->phar_pos].fp) :
php_stream_rewind(phar->fp);
memset(&file_handle->handle.stream.mmap, 0, sizeof(file_handle->handle.stream.mmap));
-#else /* PHP_VERSION_ID */
- file_handle->type = ZEND_HANDLE_STREAM;
- /* we do our own reading directly from the phar, don't change the next line */
- file_handle->handle.stream.handle = phar;
- file_handle->handle.stream.reader = phar_zend_stream_reader;
- file_handle->handle.stream.closer = NULL; /* don't close - let phar handle this one */
- file_handle->handle.stream.fteller = phar_stream_fteller_for_zend;
- file_handle->handle.stream.interactive = 0;
- phar->is_persistent ?
- php_stream_rewind(PHAR_GLOBALS->cached_fp[phar->phar_pos].fp) :
- php_stream_rewind(phar->fp);
-#endif
}
}
}
@@ -3426,60 +3398,6 @@ static zend_op_array *phar_compile_file(zend_file_handle *file_handle, int type
}
/* }}} */
-#if PHP_VERSION_ID < 50300
-int phar_zend_open(const char *filename, zend_file_handle *handle TSRMLS_DC) /* {{{ */
-{
- char *arch, *entry;
- int arch_len, entry_len;
-
- /* this code is obsoleted in php 5.3 */
- entry = (char *) filename;
- if (!IS_ABSOLUTE_PATH(entry, strlen(entry)) && !strstr(entry, "://")) {
- phar_archive_data **pphar = NULL;
- char *fname;
- int fname_len;
-
- fname = (char*)zend_get_executed_filename(TSRMLS_C);
- fname_len = strlen(fname);
-
- if (fname_len > 7 && !strncasecmp(fname, "phar://", 7)) {
- if (SUCCESS == phar_split_fname(fname, fname_len, &arch, &arch_len, &entry, &entry_len, 1, 0 TSRMLS_CC)) {
- zend_hash_find(&(PHAR_GLOBALS->phar_fname_map), arch, arch_len, (void **) &pphar);
- if (!pphar && PHAR_G(manifest_cached)) {
- zend_hash_find(&cached_phars, arch, arch_len, (void **) &pphar);
- }
- efree(arch);
- efree(entry);
- }
- }
-
- /* retrieving an include within the current directory, so use this if possible */
- if (!(entry = phar_find_in_include_path((char *) filename, strlen(filename), NULL TSRMLS_CC))) {
- /* this file is not in the phar, use the original path */
- goto skip_phar;
- }
-
- if (SUCCESS == phar_orig_zend_open(entry, handle TSRMLS_CC)) {
- if (!handle->opened_path) {
- handle->opened_path = entry;
- }
- if (entry != filename) {
- handle->free_filename = 1;
- }
- return SUCCESS;
- }
-
- if (entry != filename) {
- efree(entry);
- }
-
- return FAILURE;
- }
-skip_phar:
- return phar_orig_zend_open(filename, handle TSRMLS_CC);
-}
-/* }}} */
-#endif
typedef zend_op_array* (zend_compile_t)(zend_file_handle*, int TSRMLS_DC);
typedef zend_compile_t* (compile_hook)(zend_compile_t *ptr);
@@ -3556,13 +3474,8 @@ PHP_MINIT_FUNCTION(phar) /* {{{ */
phar_orig_compile_file = zend_compile_file;
zend_compile_file = phar_compile_file;
-#if PHP_VERSION_ID >= 50300
phar_save_resolve_path = zend_resolve_path;
zend_resolve_path = phar_resolve_path;
-#else
- phar_orig_zend_open = zend_stream_open_function;
- zend_stream_open_function = phar_zend_open;
-#endif
phar_object_init(TSRMLS_C);
@@ -3583,11 +3496,6 @@ PHP_MSHUTDOWN_FUNCTION(phar) /* {{{ */
zend_compile_file = phar_orig_compile_file;
}
-#if PHP_VERSION_ID < 50300
- if (zend_stream_open_function == phar_zend_open) {
- zend_stream_open_function = phar_orig_zend_open;
- }
-#endif
if (PHAR_G(manifest_cached)) {
zend_hash_destroy(&(cached_phars));
zend_hash_destroy(&(cached_alias));
diff --git a/ext/phar/phar_internal.h b/ext/phar/phar_internal.h
index daa85f1b70..a24a5ace70 100644
--- a/ext/phar/phar_internal.h
+++ b/ext/phar/phar_internal.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -516,76 +516,17 @@ union _phar_entry_object {
#endif
#ifndef PHAR_MAIN
-# if PHP_VERSION_ID >= 50300
extern char *(*phar_save_resolve_path)(const char *filename, int filename_len TSRMLS_DC);
-# endif
#endif
-#if PHP_VERSION_ID < 50209
-static inline size_t phar_stream_copy_to_stream(php_stream *src, php_stream *dest, size_t maxlen, size_t *len STREAMS_DC TSRMLS_DC)
-{
- size_t ret = php_stream_copy_to_stream(src, dest, maxlen);
- if (len) {
- *len = ret;
- }
- if (ret) {
- return SUCCESS;
- }
- return FAILURE;
-}
-#else
# define phar_stream_copy_to_stream(src, dest, maxlen, len) _php_stream_copy_to_stream_ex((src), (dest), (maxlen), (len) STREAMS_CC TSRMLS_CC)
-#endif
-
-#if PHP_VERSION_ID >= 60000
-typedef zstr phar_zstr;
-#define PHAR_STR(a, b) \
- spprintf(&b, 0, "%s", a.s);
-#define PHAR_ZSTR(a, b) \
- b = ZSTR(a);
-#define PHAR_STR_FREE(a) \
- efree(a);
-static inline int phar_make_unicode(zstr *c_var, char *arKey, uint nKeyLength TSRMLS_DC)
-{
- int c_var_len;
- UConverter *conv = ZEND_U_CONVERTER(UG(runtime_encoding_conv));
-
- c_var->u = NULL;
- if (zend_string_to_unicode(conv, &c_var->u, &c_var_len, arKey, nKeyLength TSRMLS_CC) == FAILURE) {
-
- if (c_var->u) {
- efree(c_var->u);
- }
- return 0;
-
- }
- return c_var_len;
-}
-static inline int phar_find_key(HashTable *_SERVER, char *key, int len, void **stuff TSRMLS_DC)
-{
- if (SUCCESS == zend_hash_find(_SERVER, key, len, stuff)) {
- return 1;
- } else {
- int s = len;
- zstr var;
- s = phar_make_unicode(&var, key, len TSRMLS_CC);
- if (SUCCESS == zend_u_hash_find(_SERVER, IS_UNICODE, var, s, stuff)) {
- efree(var.u);
- return 1;
- }
- efree(var.u);
- return 0;
- }
-}
-#else
typedef char *phar_zstr;
#define PHAR_STR(a, b) \
b = a;
#define PHAR_ZSTR(a, b) \
b = a;
#define PHAR_STR_FREE(a)
-#endif
BEGIN_EXTERN_C()
diff --git a/ext/phar/phar_object.c b/ext/phar/phar_object.c
index dcb67fe9fa..7857fa71c8 100644
--- a/ext/phar/phar_object.c
+++ b/ext/phar/phar_object.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -685,11 +685,7 @@ PHP_METHOD(Phar, webPhar)
ZVAL_STRINGL(params, entry, entry_len, 1);
zp[0] = &params;
-#if PHP_VERSION_ID < 50300
- if (FAILURE == zend_fcall_info_init(rewrite, &fci, &fcc TSRMLS_CC)) {
-#else
if (FAILURE == zend_fcall_info_init(rewrite, 0, &fci, &fcc, NULL, NULL TSRMLS_CC)) {
-#endif
zend_throw_exception_ex(phar_ce_PharException, 0 TSRMLS_CC, "phar error: invalid rewrite callback");
if (free_pathinfo) {
@@ -701,11 +697,7 @@ PHP_METHOD(Phar, webPhar)
fci.param_count = 1;
fci.params = zp;
-#if PHP_VERSION_ID < 50300
- ++(params->refcount);
-#else
Z_ADDREF_P(params);
-#endif
fci.retval_ptr_ptr = &retval_ptr;
if (FAILURE == zend_call_function(&fci, &fcc TSRMLS_CC)) {
@@ -729,11 +721,6 @@ PHP_METHOD(Phar, webPhar)
}
switch (Z_TYPE_P(retval_ptr)) {
-#if PHP_VERSION_ID >= 60000
- case IS_UNICODE:
- zval_unicode_to_string(retval_ptr TSRMLS_CC);
- /* break intentionally omitted */
-#endif
case IS_STRING:
efree(entry);
@@ -1155,11 +1142,7 @@ PHP_METHOD(Phar, __construct)
#else
char *fname, *alias = NULL, *error, *arch = NULL, *entry = NULL, *save_fname;
int fname_len, alias_len = 0, arch_len, entry_len, is_data;
-#if PHP_VERSION_ID < 50300
- long flags = 0;
-#else
long flags = SPL_FILE_DIR_SKIPDOTS|SPL_FILE_DIR_UNIXPATHS;
-#endif
long format = 0;
phar_archive_object *phar_obj;
phar_archive_data *phar_data;
@@ -1459,11 +1442,6 @@ static int phar_build(zend_object_iterator *iter, void *puser TSRMLS_DC) /* {{{
}
switch (Z_TYPE_PP(value)) {
-#if PHP_VERSION_ID >= 60000
- case IS_UNICODE:
- zval_unicode_to_string(*(value) TSRMLS_CC);
- /* break intentionally omitted */
-#endif
case IS_STRING:
break;
case IS_RESOURCE:
@@ -1514,13 +1492,7 @@ static int phar_build(zend_object_iterator *iter, void *puser TSRMLS_DC) /* {{{
switch (intern->type) {
case SPL_FS_DIR:
-#if PHP_VERSION_ID >= 60000
- test = spl_filesystem_object_get_path(intern, NULL, NULL TSRMLS_CC).s;
-#elif PHP_VERSION_ID >= 50300
test = spl_filesystem_object_get_path(intern, NULL TSRMLS_CC);
-#else
- test = intern->path;
-#endif
fname_len = spprintf(&fname, 0, "%s%c%s", test, DEFAULT_SLASH, intern->u.dir.entry.d_name);
php_stat(fname, fname_len, FS_IS_DIR, &dummy TSRMLS_CC);
@@ -1545,25 +1517,7 @@ static int phar_build(zend_object_iterator *iter, void *puser TSRMLS_DC) /* {{{
goto phar_spl_fileinfo;
case SPL_FS_INFO:
case SPL_FS_FILE:
-#if PHP_VERSION_ID >= 60000
- if (intern->file_name_type == IS_UNICODE) {
- zval zv;
-
- INIT_ZVAL(zv);
- Z_UNIVAL(zv) = intern->file_name;
- Z_UNILEN(zv) = intern->file_name_len;
- Z_TYPE(zv) = IS_UNICODE;
-
- zval_copy_ctor(&zv);
- zval_unicode_to_string(&zv TSRMLS_CC);
- fname = expand_filepath(Z_STRVAL(zv), NULL TSRMLS_CC);
- ezfree(Z_UNIVAL(zv));
- } else {
- fname = expand_filepath(intern->file_name.s, NULL TSRMLS_CC);
- }
-#else
fname = expand_filepath(intern->file_name, NULL TSRMLS_CC);
-#endif
if (!fname) {
zend_throw_exception_ex(spl_ce_UnexpectedValueException, 0 TSRMLS_CC, "Could not resolve file path");
return ZEND_HASH_APPLY_STOP;
@@ -1816,11 +1770,7 @@ PHP_METHOD(Phar, buildFromDirectory)
INIT_PZVAL(&arg);
ZVAL_STRINGL(&arg, dir, dir_len, 0);
INIT_PZVAL(&arg2);
-#if PHP_VERSION_ID < 50300
- ZVAL_LONG(&arg2, 0);
-#else
ZVAL_LONG(&arg2, SPL_FILE_DIR_SKIPDOTS|SPL_FILE_DIR_UNIXPATHS);
-#endif
zend_call_method_with_2_params(&iter, spl_ce_RecursiveDirectoryIterator,
&spl_ce_RecursiveDirectoryIterator->constructor, "__construct", NULL, &arg, &arg2);
@@ -2313,11 +2263,7 @@ static zval *phar_convert_to_other(phar_archive_data *source, int convert, char
ALLOC_ZVAL(phar->metadata);
*phar->metadata = *t;
zval_copy_ctor(phar->metadata);
-#if PHP_VERSION_ID < 50300
- phar->metadata->refcount = 1;
-#else
Z_SET_REFCOUNT_P(phar->metadata, 1);
-#endif
phar->metadata_len = 0;
}
@@ -2365,11 +2311,7 @@ no_copy:
ALLOC_ZVAL(newentry.metadata);
*newentry.metadata = *t;
zval_copy_ctor(newentry.metadata);
-#if PHP_VERSION_ID < 50300
- newentry.metadata->refcount = 1;
-#else
Z_SET_REFCOUNT_P(newentry.metadata, 1);
-#endif
newentry.metadata_str.c = NULL;
newentry.metadata_str.len = 0;
@@ -3552,11 +3494,7 @@ PHP_METHOD(Phar, copy)
ALLOC_ZVAL(newentry.metadata);
*newentry.metadata = *t;
zval_copy_ctor(newentry.metadata);
-#if PHP_VERSION_ID < 50300
- newentry.metadata->refcount = 1;
-#else
Z_SET_REFCOUNT_P(newentry.metadata, 1);
-#endif
newentry.metadata_str.c = NULL;
newentry.metadata_str.len = 0;
@@ -4371,11 +4309,6 @@ PHP_METHOD(Phar, extractTo)
switch (Z_TYPE_P(zval_files)) {
case IS_NULL:
goto all_files;
-#if PHP_VERSION_ID >= 60000
- case IS_UNICODE:
- zval_unicode_to_string(zval_files TSRMLS_CC);
- /* break intentionally omitted */
-#endif
case IS_STRING:
filename = Z_STRVAL_P(zval_files);
filename_len = Z_STRLEN_P(zval_files);
@@ -4389,11 +4322,6 @@ PHP_METHOD(Phar, extractTo)
zval **zval_file;
if (zend_hash_index_find(Z_ARRVAL_P(zval_files), i, (void **) &zval_file) == SUCCESS) {
switch (Z_TYPE_PP(zval_file)) {
-#if PHP_VERSION_ID >= 60000
- case IS_UNICODE:
- zval_unicode_to_string(*(zval_file) TSRMLS_CC);
- /* break intentionally omitted */
-#endif
case IS_STRING:
break;
default:
@@ -5414,11 +5342,7 @@ zend_function_entry phar_exception_methods[] = {
#define REGISTER_PHAR_CLASS_CONST_LONG(class_name, const_name, value) \
zend_declare_class_constant_long(class_name, const_name, sizeof(const_name)-1, (long)value TSRMLS_CC);
-#if PHP_VERSION_ID < 50200
-# define phar_exception_get_default() zend_exception_get_default()
-#else
-# define phar_exception_get_default() zend_exception_get_default(TSRMLS_C)
-#endif
+#define phar_exception_get_default() zend_exception_get_default(TSRMLS_C)
void phar_object_init(TSRMLS_D) /* {{{ */
{
diff --git a/ext/phar/phar_path_check.c b/ext/phar/phar_path_check.c
index d3a3aab6b9..db97efcbe3 100644
--- a/ext/phar/phar_path_check.c
+++ b/ext/phar/phar_path_check.c
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2007-2013 The PHP Group |
+ | Copyright (c) 2007-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/pharzip.h b/ext/phar/pharzip.h
index 9c088d3a08..62e3de7376 100644
--- a/ext/phar/pharzip.h
+++ b/ext/phar/pharzip.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/php_phar.h b/ext/phar/php_phar.h
index f8325d0c63..41c379bfa9 100644
--- a/ext/phar/php_phar.h
+++ b/ext/phar/php_phar.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/stream.c b/ext/phar/stream.c
index 401d81e109..5db866c422 100644
--- a/ext/phar/stream.c
+++ b/ext/phar/stream.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar:// stream wrapper support |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -942,11 +942,7 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, char *url_from, char
entry->filename_len = new_key_len;
PHAR_ZSTR(new_str_key, new_key);
-#if PHP_VERSION_ID < 50300
- zend_hash_update_current_key_ex(&phar->manifest, key_type, new_key, new_key_len, 0, NULL);
-#else
zend_hash_update_current_key_ex(&phar->manifest, key_type, new_key, new_key_len, 0, HASH_UPDATE_KEY_ANYWAY, NULL);
-#endif
}
PHAR_STR_FREE(str_key);
}
@@ -968,11 +964,7 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, char *url_from, char
new_str_key[new_key_len] = 0;
PHAR_ZSTR(new_str_key, new_key);
-#if PHP_VERSION_ID < 50300
- zend_hash_update_current_key_ex(&phar->virtual_dirs, key_type, new_key, new_key_len, 0, NULL);
-#else
zend_hash_update_current_key_ex(&phar->virtual_dirs, key_type, new_key, new_key_len, 0, HASH_UPDATE_KEY_ANYWAY, NULL);
-#endif
efree(new_str_key);
}
PHAR_STR_FREE(str_key);
@@ -996,11 +988,7 @@ static int phar_wrapper_rename(php_stream_wrapper *wrapper, char *url_from, char
new_str_key[new_key_len] = 0;
PHAR_ZSTR(new_str_key, new_key);
-#if PHP_VERSION_ID < 50300
- zend_hash_update_current_key_ex(&phar->mounted_dirs, key_type, new_key, new_key_len, 0, NULL);
-#else
zend_hash_update_current_key_ex(&phar->mounted_dirs, key_type, new_key, new_key_len, 0, HASH_UPDATE_KEY_ANYWAY, NULL);
-#endif
efree(new_str_key);
}
PHAR_STR_FREE(str_key);
diff --git a/ext/phar/stream.h b/ext/phar/stream.h
index b22b67ab01..097bf2ca52 100644
--- a/ext/phar/stream.h
+++ b/ext/phar/stream.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension |
+----------------------------------------------------------------------+
- | Copyright (c) 2006-2013 The PHP Group |
+ | Copyright (c) 2006-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/stub.h b/ext/phar/stub.h
index daafa391ca..6d524c69d1 100644
--- a/ext/phar/stub.h
+++ b/ext/phar/stub.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| phar php single-file executable PHP extension generated stub |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/tar.c b/ext/phar/tar.c
index 0e60e3db13..ca8eafcc8a 100644
--- a/ext/phar/tar.c
+++ b/ext/phar/tar.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| TAR archive support for Phar |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/tar.h b/ext/phar/tar.h
index 8bfc3817a1..0305812849 100644
--- a/ext/phar/tar.h
+++ b/ext/phar/tar.h
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| TAR archive support for Phar |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/phar/util.c b/ext/phar/util.c
index f2271dffd4..d8152cf459 100644
--- a/ext/phar/util.c
+++ b/ext/phar/util.c
@@ -3,7 +3,7 @@
| phar php single-file executable PHP extension |
| utility functions |
+----------------------------------------------------------------------+
- | Copyright (c) 2005-2013 The PHP Group |
+ | Copyright (c) 2005-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -41,10 +41,6 @@
static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end, char *key, int key_len, char **signature, int *signature_len TSRMLS_DC);
#endif
-#if !defined(PHP_VERSION_ID) || PHP_VERSION_ID < 50300
-extern php_stream_wrapper php_stream_phar_wrapper;
-#endif
-
/* for links to relative location, prepend cwd of the entry */
static char *phar_get_link_location(phar_entry_info *entry TSRMLS_DC) /* {{{ */
{
@@ -256,7 +252,6 @@ int phar_mount_entry(phar_archive_data *phar, char *filename, int filename_len,
char *phar_find_in_include_path(char *filename, int filename_len, phar_archive_data **pphar TSRMLS_DC) /* {{{ */
{
-#if PHP_VERSION_ID >= 50300
char *path, *fname, *arch, *entry, *ret, *test;
int arch_len, entry_len, fname_len, ret_len;
phar_archive_data *phar;
@@ -344,223 +339,6 @@ splitted:
}
return ret;
-#else /* PHP 5.2 */
- char resolved_path[MAXPATHLEN];
- char trypath[MAXPATHLEN];
- char *ptr, *end, *path = PG(include_path);
- php_stream_wrapper *wrapper;
- const char *p;
- int n = 0;
- char *fname, *arch, *entry, *ret, *test;
- int arch_len, entry_len;
- phar_archive_data *phar = NULL;
-
- if (!filename) {
- return NULL;
- }
-
- if (!zend_is_executing(TSRMLS_C) || !PHAR_G(cwd)) {
- goto doit;
- }
-
- fname = (char*)zend_get_executed_filename(TSRMLS_C);
-
- if (SUCCESS != phar_split_fname(fname, strlen(fname), &arch, &arch_len, &entry, &entry_len, 1, 0 TSRMLS_CC)) {
- goto doit;
- }
-
- efree(entry);
-
- if (*filename == '.') {
- int try_len;
-
- if (FAILURE == phar_get_archive(&phar, arch, arch_len, NULL, 0, NULL TSRMLS_CC)) {
- efree(arch);
- goto doit;
- }
-
- try_len = filename_len;
- test = phar_fix_filepath(estrndup(filename, filename_len), &try_len, 1 TSRMLS_CC);
-
- if (*test == '/') {
- if (zend_hash_exists(&(phar->manifest), test + 1, try_len - 1)) {
- spprintf(&ret, 0, "phar://%s%s", arch, test);
- efree(arch);
- efree(test);
- return ret;
- }
- } else {
- if (zend_hash_exists(&(phar->manifest), test, try_len)) {
- spprintf(&ret, 0, "phar://%s/%s", arch, test);
- efree(arch);
- efree(test);
- return ret;
- }
- }
-
- efree(test);
- }
-
- efree(arch);
-doit:
- if (*filename == '.' || IS_ABSOLUTE_PATH(filename, filename_len) || !path || !*path) {
- if (tsrm_realpath(filename, resolved_path TSRMLS_CC)) {
- return estrdup(resolved_path);
- } else {
- return NULL;
- }
- }
-
- /* test for stream wrappers and return */
- for (p = filename; p - filename < filename_len && (isalnum((int)*p) || *p == '+' || *p == '-' || *p == '.'); ++p, ++n);
-
- if (n < filename_len - 3 && (*p == ':') && (!strncmp("//", p+1, 2) || ( filename_len > 4 && !memcmp("data", filename, 4)))) {
- /* found stream wrapper, this is an absolute path until stream wrappers implement realpath */
- return estrndup(filename, filename_len);
- }
-
- ptr = (char *) path;
- while (ptr && *ptr) {
- int len, is_stream_wrapper = 0, maybe_stream = 1;
-
- end = strchr(ptr, DEFAULT_DIR_SEPARATOR);
-#ifndef PHP_WIN32
- /* search for stream wrapper */
- if (end - ptr <= 1) {
- maybe_stream = 0;
- goto not_stream;
- }
-
- for (p = ptr, n = 0; p < end && (isalnum((int)*p) || *p == '+' || *p == '-' || *p == '.'); ++p, ++n);
-
- if (n == end - ptr && *p && !strncmp("//", p+1, 2)) {
- is_stream_wrapper = 1;
- /* seek to real end of include_path portion */
- end = strchr(end + 1, DEFAULT_DIR_SEPARATOR);
- } else {
- maybe_stream = 0;
- }
-not_stream:
-#endif
- if (end) {
- if ((end-ptr) + 1 + filename_len + 1 >= MAXPATHLEN) {
- ptr = end + 1;
- continue;
- }
-
- memcpy(trypath, ptr, end-ptr);
- len = end-ptr;
- trypath[end-ptr] = '/';
- memcpy(trypath+(end-ptr)+1, filename, filename_len+1);
- ptr = end+1;
- } else {
- len = strlen(ptr);
-
- if (len + 1 + filename_len + 1 >= MAXPATHLEN) {
- break;
- }
-
- memcpy(trypath, ptr, len);
- trypath[len] = '/';
- memcpy(trypath+len+1, filename, filename_len+1);
- ptr = NULL;
- }
-
- if (!is_stream_wrapper && maybe_stream) {
- /* search for stream wrapper */
- for (p = trypath, n = 0; isalnum((int)*p) || *p == '+' || *p == '-' || *p == '.'; ++p, ++n);
- }
-
- if (is_stream_wrapper || (n < len - 3 && (*p == ':') && (n > 1) && (!strncmp("//", p+1, 2) || !memcmp("data", trypath, 4)))) {
- char *actual;
-
- wrapper = php_stream_locate_url_wrapper(trypath, &actual, STREAM_OPEN_FOR_INCLUDE TSRMLS_CC);
- if (wrapper == &php_plain_files_wrapper) {
- strlcpy(trypath, actual, sizeof(trypath));
- } else if (!wrapper) {
- /* if wrapper is NULL, there was a mal-formed include_path stream wrapper, so skip this ptr */
- continue;
- } else {
- if (wrapper->wops->url_stat) {
- php_stream_statbuf ssb;
-
- if (SUCCESS == wrapper->wops->url_stat(wrapper, trypath, 0, &ssb, NULL TSRMLS_CC)) {
- if (wrapper == &php_stream_phar_wrapper) {
- char *arch, *entry;
- int arch_len, entry_len, ret_len;
-
- ret_len = strlen(trypath);
- /* found phar:// */
-
- if (SUCCESS != phar_split_fname(trypath, ret_len, &arch, &arch_len, &entry, &entry_len, 1, 0 TSRMLS_CC)) {
- return estrndup(trypath, ret_len);
- }
-
- zend_hash_find(&(PHAR_GLOBALS->phar_fname_map), arch, arch_len, (void **) &pphar);
-
- if (!pphar && PHAR_G(manifest_cached)) {
- zend_hash_find(&cached_phars, arch, arch_len, (void **) &pphar);
- }
-
- efree(arch);
- efree(entry);
-
- return estrndup(trypath, ret_len);
- }
- return estrdup(trypath);
- }
- }
- continue;
- }
- }
-
- if (tsrm_realpath(trypath, resolved_path TSRMLS_CC)) {
- return estrdup(resolved_path);
- }
- } /* end provided path */
-
- /* check in calling scripts' current working directory as a fall back case */
- if (zend_is_executing(TSRMLS_C)) {
- char *exec_fname = (char*)zend_get_executed_filename(TSRMLS_C);
- int exec_fname_length = strlen(exec_fname);
- const char *p;
- int n = 0;
-
- while ((--exec_fname_length >= 0) && !IS_SLASH(exec_fname[exec_fname_length]));
- if (exec_fname && exec_fname[0] != '[' &&
- exec_fname_length > 0 &&
- exec_fname_length + 1 + filename_len + 1 < MAXPATHLEN) {
- memcpy(trypath, exec_fname, exec_fname_length + 1);
- memcpy(trypath+exec_fname_length + 1, filename, filename_len+1);
-
- /* search for stream wrapper */
- for (p = trypath; isalnum((int)*p) || *p == '+' || *p == '-' || *p == '.'; ++p, ++n);
-
- if (n < exec_fname_length - 3 && (*p == ':') && (n > 1) && (!strncmp("//", p+1, 2) || !memcmp("data", trypath, 4))) {
- char *actual;
-
- wrapper = php_stream_locate_url_wrapper(trypath, &actual, STREAM_OPEN_FOR_INCLUDE TSRMLS_CC);
-
- if (wrapper == &php_plain_files_wrapper) {
- /* this should never technically happen, but we'll leave it here for completeness */
- strlcpy(trypath, actual, sizeof(trypath));
- } else if (!wrapper) {
- /* if wrapper is NULL, there was a malformed include_path stream wrapper
- this also should be impossible */
- return NULL;
- } else {
- return estrdup(trypath);
- }
- }
-
- if (tsrm_realpath(trypath, resolved_path TSRMLS_CC)) {
- return estrdup(resolved_path);
- }
- }
- }
-
- return NULL;
-#endif /* PHP 5.2 */
}
/* }}} */
@@ -850,11 +628,6 @@ int phar_open_archive_fp(phar_archive_data *phar TSRMLS_DC) /* {{{ */
if (phar_get_pharfp(phar TSRMLS_CC)) {
return SUCCESS;
}
-#if PHP_API_VERSION < 20100412
- if (PG(safe_mode) && (!php_checkuid(phar->fname, NULL, CHECKUID_ALLOW_ONLY_FILE))) {
- return FAILURE;
- }
-#endif
if (php_check_open_basedir(phar->fname TSRMLS_CC)) {
return FAILURE;
@@ -1031,47 +804,12 @@ int phar_open_entry_fp(phar_entry_info *entry, char **error, int follow_links TS
}
/* }}} */
-#if defined(PHP_VERSION_ID) && PHP_VERSION_ID < 50202
-typedef struct {
- char *data;
- size_t fpos;
- size_t fsize;
- size_t smax;
- int mode;
- php_stream **owner_ptr;
-} php_stream_memory_data;
-#endif
-
int phar_create_writeable_entry(phar_archive_data *phar, phar_entry_info *entry, char **error TSRMLS_DC) /* {{{ */
{
if (entry->fp_type == PHAR_MOD) {
/* already newly created, truncate */
-#if PHP_VERSION_ID >= 50202
php_stream_truncate_set_size(entry->fp, 0);
-#else
- if (php_stream_is(entry->fp, PHP_STREAM_IS_TEMP)) {
- if (php_stream_is(*(php_stream**)entry->fp->abstract, PHP_STREAM_IS_MEMORY)) {
- php_stream *inner = *(php_stream**)entry->fp->abstract;
- php_stream_memory_data *memfp = (php_stream_memory_data*)inner->abstract;
- memfp->fpos = 0;
- memfp->fsize = 0;
- } else if (php_stream_is(*(php_stream**)entry->fp->abstract, PHP_STREAM_IS_STDIO)) {
- php_stream_truncate_set_size(*(php_stream**)entry->fp->abstract, 0);
- } else {
- if (error) {
- spprintf(error, 0, "phar error: file \"%s\" cannot be opened for writing, no truncate support", phar->fname);
- }
- return FAILURE;
- }
- } else if (php_stream_is(entry->fp, PHP_STREAM_IS_STDIO)) {
- php_stream_truncate_set_size(entry->fp, 0);
- } else {
- if (error) {
- spprintf(error, 0, "phar error: file \"%s\" cannot be opened for writing, no truncate support", phar->fname);
- }
- return FAILURE;
- }
-#endif
+
entry->old_flags = entry->flags;
entry->is_modified = 1;
phar->is_modified = 1;
@@ -1689,11 +1427,7 @@ static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end,
Z_TYPE_P(zdata) = IS_STRING;
Z_STRLEN_P(zdata) = end;
-#if PHP_MAJOR_VERSION > 5
- if (end != (off_t) php_stream_copy_to_mem(fp, (void **) &(Z_STRVAL_P(zdata)), (size_t) end, 0)) {
-#else
if (end != (off_t) php_stream_copy_to_mem(fp, &(Z_STRVAL_P(zdata)), (size_t) end, 0)) {
-#endif
zval_dtor(zdata);
zval_dtor(zsig);
zval_dtor(zkey);
@@ -1705,11 +1439,7 @@ static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end,
return FAILURE;
}
-#if PHP_VERSION_ID < 50300
- if (FAILURE == zend_fcall_info_init(openssl, &fci, &fcc TSRMLS_CC)) {
-#else
if (FAILURE == zend_fcall_info_init(openssl, 0, &fci, &fcc, NULL, NULL TSRMLS_CC)) {
-#endif
zval_dtor(zdata);
zval_dtor(zsig);
zval_dtor(zkey);
@@ -1723,13 +1453,6 @@ static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end,
fci.param_count = 3;
fci.params = zp;
-#if PHP_VERSION_ID < 50300
- ++(zdata->refcount);
- if (!is_sign) {
- ++(zsig->refcount);
- }
- ++(zkey->refcount);
-#else
Z_ADDREF_P(zdata);
if (is_sign) {
Z_SET_ISREF_P(zsig);
@@ -1737,7 +1460,7 @@ static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end,
Z_ADDREF_P(zsig);
}
Z_ADDREF_P(zkey);
-#endif
+
fci.retval_ptr_ptr = &retval_ptr;
if (FAILURE == zend_call_function(&fci, &fcc TSRMLS_CC)) {
@@ -1754,21 +1477,15 @@ static int phar_call_openssl_signverify(int is_sign, php_stream *fp, off_t end,
zval_dtor(openssl);
efree(openssl);
-#if PHP_VERSION_ID < 50300
- --(zdata->refcount);
- if (!is_sign) {
- --(zsig->refcount);
- }
- --(zkey->refcount);
-#else
Z_DELREF_P(zdata);
+
if (is_sign) {
Z_UNSET_ISREF_P(zsig);
} else {
Z_DELREF_P(zsig);
}
Z_DELREF_P(zkey);
-#endif
+
zval_dtor(zdata);
efree(zdata);
zval_dtor(zkey);
@@ -2294,11 +2011,7 @@ static int phar_update_cached_entry(void *data, void *argument) /* {{{ */
ALLOC_ZVAL(entry->metadata);
*entry->metadata = *t;
zval_copy_ctor(entry->metadata);
-#if PHP_VERSION_ID < 50300
- entry->metadata->refcount = 1;
-#else
Z_SET_REFCOUNT_P(entry->metadata, 1);
-#endif
entry->metadata_str.c = NULL;
entry->metadata_str.len = 0;
}
@@ -2342,11 +2055,7 @@ static void phar_copy_cached_phar(phar_archive_data **pphar TSRMLS_DC) /* {{{ */
ALLOC_ZVAL(phar->metadata);
*phar->metadata = *t;
zval_copy_ctor(phar->metadata);
-#if PHP_VERSION_ID < 50300
- phar->metadata->refcount = 1;
-#else
Z_SET_REFCOUNT_P(phar->metadata, 1);
-#endif
}
}
diff --git a/ext/phar/zip.c b/ext/phar/zip.c
index 6ba745e9cb..ba03687315 100644
--- a/ext/phar/zip.c
+++ b/ext/phar/zip.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| ZIP archive support for Phar |
+----------------------------------------------------------------------+
- | Copyright (c) 2007-2013 The PHP Group |
+ | Copyright (c) 2007-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -578,10 +578,6 @@ foundit:
/* construct actual offset to file start - local extra_len can be different from central extra_len */
entry.offset = entry.offset_abs =
sizeof(local) + entry.header_offset + PHAR_GET_16(local.filename_len) + PHAR_GET_16(local.extra_len);
-#if PHP_VERSION_ID < 50207
- /* work around Bug #46147 */
- fp->writepos = fp->readpos = 0;
-#endif
php_stream_seek(fp, entry.offset, SEEK_SET);
/* these next lines should be for php < 5.2.6 after 5.3 filters are fixed */
fp->writepos = 0;
@@ -605,9 +601,6 @@ foundit:
if (!(entry.uncompressed_filesize = php_stream_copy_to_mem(fp, &actual_alias, entry.uncompressed_filesize, 0)) || !actual_alias) {
pefree(entry.filename, entry.is_persistent);
-#if PHP_VERSION_ID < 50207
- PHAR_ZIP_FAIL("unable to read in alias, truncated (PHP 5.2.7 and newer has a potential fix for this problem)");
-#endif
PHAR_ZIP_FAIL("unable to read in alias, truncated");
}
@@ -626,9 +619,6 @@ foundit:
if (!(entry.uncompressed_filesize = php_stream_copy_to_mem(fp, &actual_alias, entry.uncompressed_filesize, 0)) || !actual_alias) {
pefree(entry.filename, entry.is_persistent);
-#if PHP_VERSION_ID < 50207
- PHAR_ZIP_FAIL("unable to read in alias, truncated (PHP 5.2.7 and newer has a potential fix for this problem)");
-#endif
PHAR_ZIP_FAIL("unable to read in alias, truncated");
}
diff --git a/ext/posix/php_posix.h b/ext/posix/php_posix.h
index 2c073496b5..8ace07c1c0 100644
--- a/ext/posix/php_posix.h
+++ b/ext/posix/php_posix.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/posix/posix.c b/ext/posix/posix.c
index 32db6705f5..1dfa9997ed 100644
--- a/ext/posix/posix.c
+++ b/ext/posix/posix.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pspell/php_pspell.h b/ext/pspell/php_pspell.h
index b4e97f3a6f..83103fae74 100644
--- a/ext/pspell/php_pspell.h
+++ b/ext/pspell/php_pspell.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/pspell/pspell.c b/ext/pspell/pspell.c
index 79a597e862..85199d621d 100644
--- a/ext/pspell/pspell.c
+++ b/ext/pspell/pspell.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/readline/php_readline.h b/ext/readline/php_readline.h
index a9f8287ad2..5660bdb7f6 100644
--- a/ext/readline/php_readline.h
+++ b/ext/readline/php_readline.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/readline/readline.c b/ext/readline/readline.c
index bd460696bd..4bd9103462 100644
--- a/ext/readline/readline.c
+++ b/ext/readline/readline.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -170,7 +170,10 @@ ZEND_GET_MODULE(readline)
PHP_MINIT_FUNCTION(readline)
{
- using_history();
+#if HAVE_LIBREADLINE
+ /* libedit don't need this call which set the tty in cooked mode */
+ using_history();
+#endif
return PHP_MINIT(cli_readline)(INIT_FUNC_ARGS_PASSTHRU);
}
@@ -351,6 +354,11 @@ PHP_FUNCTION(readline_clear_history)
return;
}
+#if HAVE_LIBEDIT
+ /* clear_history is the only function where rl_initialize
+ is not call to ensure correct allocation */
+ using_history();
+#endif
clear_history();
RETURN_TRUE;
diff --git a/ext/readline/readline_cli.c b/ext/readline/readline_cli.c
index f4ce12bade..c2bf8764cb 100644
--- a/ext/readline/readline_cli.c
+++ b/ext/readline/readline_cli.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/readline/readline_cli.h b/ext/readline/readline_cli.h
index d9deb8a04c..becd9d3342 100644
--- a/ext/readline/readline_cli.h
+++ b/ext/readline/readline_cli.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/readline/tests/libedit_callback_handler_install_001.phpt b/ext/readline/tests/libedit_callback_handler_install_001.phpt
new file mode 100644
index 0000000000..b5d921e279
--- /dev/null
+++ b/ext/readline/tests/libedit_callback_handler_install_001.phpt
@@ -0,0 +1,26 @@
+--TEST--
+readline_callback_handler_install(): Basic test
+--SKIPIF--
+<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_install')) die("skip");
+if (READLINE_LIB != "libedit") die("skip libedit only");
+?>
+--FILE--
+<?php
+
+function foo() {
+ readline_callback_handler_remove();
+}
+
+var_dump(readline_callback_handler_install('testing: ', 'foo'));
+var_dump(readline_callback_handler_install('testing: ', 'foobar!'));
+var_dump(readline_callback_handler_install('testing: '));
+
+?>
+--EXPECTF--
+bool(true)
+
+Warning: readline_callback_handler_install(): foobar! is not callable in %s on line %d
+bool(false)
+
+Warning: readline_callback_handler_install() expects exactly 2 parameters, 1 given in %s on line %d
+NULL
diff --git a/ext/readline/tests/libedit_callback_handler_remove_001.phpt b/ext/readline/tests/libedit_callback_handler_remove_001.phpt
new file mode 100644
index 0000000000..b7eaa2103f
--- /dev/null
+++ b/ext/readline/tests/libedit_callback_handler_remove_001.phpt
@@ -0,0 +1,22 @@
+--TEST--
+readline_callback_handler_remove(): Basic test
+--SKIPIF--
+<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_remove')) die("skip");
+if (READLINE_LIB != "libedit") die("skip libedit only");
+?>
+--FILE--
+<?php
+
+var_dump(readline_callback_handler_remove());
+var_dump(readline_callback_handler_install('testing: ', 'foo'));
+
+function foo() { }
+var_dump(readline_callback_handler_install('testing: ', 'foo'));
+var_dump(readline_callback_handler_remove());
+
+?>
+--EXPECTF--
+bool(false)
+bool(true)
+bool(true)
+bool(true)
diff --git a/ext/readline/tests/libedit_info_001.phpt b/ext/readline/tests/libedit_info_001.phpt
new file mode 100644
index 0000000000..1d79f4ad0c
--- /dev/null
+++ b/ext/readline/tests/libedit_info_001.phpt
@@ -0,0 +1,43 @@
+--TEST--
+readline_info(): Basic test
+--SKIPIF--
+<?php if (!extension_loaded("readline")) die("skip");
+if (READLINE_LIB != "libedit") die("skip libedit only");
+?>
+--FILE--
+<?php
+
+var_dump(readline_info());
+var_dump(readline_info(1));
+var_dump(readline_info(1,1));
+var_dump(readline_info('line_buffer'));
+var_dump(readline_info('readline_name'));
+var_dump(readline_info('readline_name', 1));
+var_dump(readline_info('readline_name'));
+var_dump(readline_info('attempted_completion_over',1));
+var_dump(readline_info('attempted_completion_over'));
+
+?>
+--EXPECTF--
+array(6) {
+ ["line_buffer"]=>
+ string(0) ""
+ ["point"]=>
+ int(0)
+ ["end"]=>
+ int(0)
+ ["library_version"]=>
+ string(%d) "%s"
+ ["readline_name"]=>
+ string(0) ""
+ ["attempted_completion_over"]=>
+ int(0)
+}
+NULL
+NULL
+string(0) ""
+string(0) ""
+string(0) ""
+string(1) "1"
+int(0)
+int(1)
diff --git a/ext/readline/tests/libedit_write_history_001.phpt b/ext/readline/tests/libedit_write_history_001.phpt
new file mode 100644
index 0000000000..e9b6dbee8d
--- /dev/null
+++ b/ext/readline/tests/libedit_write_history_001.phpt
@@ -0,0 +1,29 @@
+--TEST--
+readline_write_history(): Basic test
+--SKIPIF--
+<?php if (!extension_loaded("readline") || !function_exists('readline_add_history')) die("skip");
+if (READLINE_LIB != "libedit") die("skip libedit only");
+?>
+--FILE--
+<?php
+
+$name = tempnam('/tmp', 'readline.tmp');
+
+readline_add_history('foo');
+readline_add_history('');
+readline_add_history(1);
+readline_add_history(NULL);
+readline_write_history($name);
+
+var_dump(file_get_contents($name));
+
+unlink($name);
+
+?>
+--EXPECT--
+string(21) "_HiStOrY_V2_
+foo
+
+1
+
+"
diff --git a/ext/readline/tests/readline_callback_handler_install_001.phpt b/ext/readline/tests/readline_callback_handler_install_001.phpt
index c88a4e86f1..cc054b0aa6 100644
--- a/ext/readline/tests/readline_callback_handler_install_001.phpt
+++ b/ext/readline/tests/readline_callback_handler_install_001.phpt
@@ -1,7 +1,9 @@
--TEST--
readline_callback_handler_install(): Basic test
--SKIPIF--
-<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_install')) die("skip"); ?>
+<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_install')) die("skip");
+if (READLINE_LIB == "libedit") die("skip readline only");
+?>
--FILE--
<?php
diff --git a/ext/readline/tests/readline_callback_handler_remove_001.phpt b/ext/readline/tests/readline_callback_handler_remove_001.phpt
index 83b592e055..17ef220b65 100644
--- a/ext/readline/tests/readline_callback_handler_remove_001.phpt
+++ b/ext/readline/tests/readline_callback_handler_remove_001.phpt
@@ -1,7 +1,9 @@
--TEST--
readline_callback_handler_remove(): Basic test
--SKIPIF--
-<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_remove')) die("skip"); ?>
+<?php if (!extension_loaded("readline") || !function_exists('readline_callback_handler_remove')) die("skip");
+if (READLINE_LIB == "libedit") die("skip readline only");
+?>
--FILE--
<?php
diff --git a/ext/readline/tests/readline_info_001.phpt b/ext/readline/tests/readline_info_001.phpt
index ebab3bf68b..81b7806b43 100644
--- a/ext/readline/tests/readline_info_001.phpt
+++ b/ext/readline/tests/readline_info_001.phpt
@@ -1,7 +1,9 @@
--TEST--
readline_info(): Basic test
--SKIPIF--
-<?php if (!extension_loaded("readline")) die("skip"); ?>
+<?php if (!extension_loaded("readline")) die("skip");
+if (READLINE_LIB == "libedit") die("skip readline only");
+?>
--FILE--
<?php
diff --git a/ext/readline/tests/readline_write_history_001.phpt b/ext/readline/tests/readline_write_history_001.phpt
index fc0ae3225e..95c34e3e89 100644
--- a/ext/readline/tests/readline_write_history_001.phpt
+++ b/ext/readline/tests/readline_write_history_001.phpt
@@ -1,7 +1,9 @@
--TEST--
readline_write_history(): Basic test
--SKIPIF--
-<?php if (!extension_loaded("readline") || !function_exists('readline_add_history')) die("skip"); ?>
+<?php if (!extension_loaded("readline") || !function_exists('readline_add_history')) die("skip");
+if (READLINE_LIB == "libedit") die("skip readline only");
+?>
--FILE--
<?php
diff --git a/ext/recode/php_recode.h b/ext/recode/php_recode.h
index 9faa01cc20..76ae292c56 100644
--- a/ext/recode/php_recode.h
+++ b/ext/recode/php_recode.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/recode/recode.c b/ext/recode/recode.c
index 7203cb24ea..3fff0a7f7f 100644
--- a/ext/recode/recode.c
+++ b/ext/recode/recode.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/reflection/php_reflection.c b/ext/reflection/php_reflection.c
index b1f7484f24..31d836a7ac 100644
--- a/ext/reflection/php_reflection.c
+++ b/ext/reflection/php_reflection.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1105,29 +1105,26 @@ static void _extension_string(string *str, zend_module_entry *module, char *inde
string_free(&str_constants);
}
- if (module->functions && module->functions->fname) {
+ {
+ HashPosition iterator;
zend_function *fptr;
- const zend_function_entry *func = module->functions;
-
- string_printf(str, "\n - Functions {\n");
-
- /* Is there a better way of doing this? */
- while (func->fname) {
- int fname_len = strlen(func->fname);
- char *lc_name = zend_str_tolower_dup(func->fname, fname_len);
-
- if (zend_hash_find(EG(function_table), lc_name, fname_len + 1, (void**) &fptr) == FAILURE) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "Internal error: Cannot find extension function %s in global function table", func->fname);
- func++;
- efree(lc_name);
- continue;
+ int first = 1;
+
+ zend_hash_internal_pointer_reset_ex(CG(function_table), &iterator);
+ while (zend_hash_get_current_data_ex(CG(function_table), (void **) &fptr, &iterator) == SUCCESS) {
+ if (fptr->common.type==ZEND_INTERNAL_FUNCTION
+ && fptr->internal_function.module == module) {
+ if (first) {
+ string_printf(str, "\n - Functions {\n");
+ first = 0;
+ }
+ _function_string(str, fptr, NULL, " " TSRMLS_CC);
}
-
- _function_string(str, fptr, NULL, " " TSRMLS_CC);
- efree(lc_name);
- func++;
+ zend_hash_move_forward_ex(CG(function_table), &iterator);
+ }
+ if (!first) {
+ string_printf(str, "%s }\n", indent);
}
- string_printf(str, "%s }\n", indent);
}
{
@@ -5264,6 +5261,9 @@ ZEND_METHOD(reflection_extension, getFunctions)
{
reflection_object *intern;
zend_module_entry *module;
+ HashPosition iterator;
+ zval *function;
+ zend_function *fptr;
if (zend_parse_parameters_none() == FAILURE) {
return;
@@ -5271,29 +5271,15 @@ ZEND_METHOD(reflection_extension, getFunctions)
GET_REFLECTION_OBJECT_PTR(module);
array_init(return_value);
- if (module->functions) {
- zval *function;
- zend_function *fptr;
- const zend_function_entry *func = module->functions;
-
- /* Is there a better way of doing this? */
- while (func->fname) {
- int fname_len = strlen(func->fname);
- char *lc_name = zend_str_tolower_dup(func->fname, fname_len);
-
- if (zend_hash_find(EG(function_table), lc_name, fname_len + 1, (void**) &fptr) == FAILURE) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "Internal error: Cannot find extension function %s in global function table", func->fname);
- func++;
- efree(lc_name);
- continue;
- }
-
+ zend_hash_internal_pointer_reset_ex(CG(function_table), &iterator);
+ while (zend_hash_get_current_data_ex(CG(function_table), (void **) &fptr, &iterator) == SUCCESS) {
+ if (fptr->common.type==ZEND_INTERNAL_FUNCTION
+ && fptr->internal_function.module == module) {
ALLOC_ZVAL(function);
reflection_function_factory(fptr, NULL, function TSRMLS_CC);
- add_assoc_zval_ex(return_value, func->fname, fname_len+1, function);
- func++;
- efree(lc_name);
+ add_assoc_zval(return_value, fptr->common.function_name, function);
}
+ zend_hash_move_forward_ex(CG(function_table), &iterator);
}
}
/* }}} */
diff --git a/ext/reflection/php_reflection.h b/ext/reflection/php_reflection.h
index 48470f4f63..2c03bd6e7e 100644
--- a/ext/reflection/php_reflection.h
+++ b/ext/reflection/php_reflection.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/reflection/tests/ReflectionClass_getStaticPropertyValue_001_2_4.phpt b/ext/reflection/tests/ReflectionClass_getStaticPropertyValue_001_2_4.phpt
index c299412e13..8bb62d95f1 100644
--- a/ext/reflection/tests/ReflectionClass_getStaticPropertyValue_001_2_4.phpt
+++ b/ext/reflection/tests/ReflectionClass_getStaticPropertyValue_001_2_4.phpt
@@ -56,6 +56,6 @@ string(13) "default value"
Fatal error: Uncaught exception 'ReflectionException' with message 'Class A does not have a property named ' in %sReflectionClass_getStaticPropertyValue_001_2_4.php:%d
Stack trace:
-#0 %sReflectionClass_getStaticPropertyValue_001_2_4.php(%d): ReflectionClass->getStaticPropertyValue('?A?privateOverr...')
+#0 %sReflectionClass_getStaticPropertyValue_001_2_4.php(%d): ReflectionClass->getStaticPropertyValue('\x00A\x00privateOverr...')
#1 {main}
thrown in %sReflectionClass_getStaticPropertyValue_001_2_4.php on line %d
diff --git a/ext/reflection/tests/ReflectionClass_setStaticPropertyValue_001_2_4.phpt b/ext/reflection/tests/ReflectionClass_setStaticPropertyValue_001_2_4.phpt
index 1092f6553d..dc13bf562d 100644
--- a/ext/reflection/tests/ReflectionClass_setStaticPropertyValue_001_2_4.phpt
+++ b/ext/reflection/tests/ReflectionClass_setStaticPropertyValue_001_2_4.phpt
@@ -56,6 +56,6 @@ Set static values in A:
Fatal error: Uncaught exception 'ReflectionException' with message 'Class A does not have a property named ' in %sReflectionClass_setStaticPropertyValue_001_2_4.php:%d
Stack trace:
-#0 %sReflectionClass_setStaticPropertyValue_001_2_4.php(%d): ReflectionClass->setStaticPropertyValue('?A?privateOverr...', 'new value 1')
+#0 %sReflectionClass_setStaticPropertyValue_001_2_4.php(%d): ReflectionClass->setStaticPropertyValue('\x00A\x00privateOverr...', 'new value 1')
#1 {main}
thrown in %sReflectionClass_setStaticPropertyValue_001_2_4.php on line %d
diff --git a/ext/reflection/tests/ReflectionExtension_bug66218.phpt b/ext/reflection/tests/ReflectionExtension_bug66218.phpt
new file mode 100644
index 0000000000..e263624bad
--- /dev/null
+++ b/ext/reflection/tests/ReflectionExtension_bug66218.phpt
@@ -0,0 +1,21 @@
+--TEST--
+ReflectionExtension::getFunctions() ##6218 zend_register_functions breaks reflection
+--SKIPIF--
+<?php
+if (!extension_loaded('reflection')) print 'skip missing reflection extension';
+if (PHP_SAPI != "cli") die("skip CLI only test");
+if (!function_exists("dl")) die("skip need dl");
+?>
+--FILE--
+<?php
+$r = new ReflectionExtension('standard');
+$t = $r->getFunctions();
+var_dump($t['dl']);
+?>
+Done
+--EXPECTF--
+object(ReflectionFunction)#%d (1) {
+ ["name"]=>
+ string(2) "dl"
+}
+Done
diff --git a/ext/session/mod_files.c b/ext/session/mod_files.c
index 004d9d4637..47140436e7 100644
--- a/ext/session/mod_files.c
+++ b/ext/session/mod_files.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -145,10 +145,12 @@ static void ps_files_open(ps_files *data, const char *key TSRMLS_DC)
if (fstat(data->fd, &sbuf)) {
close(data->fd);
+ data->fd = -1;
return;
}
if (S_ISLNK(sbuf.st_mode) && php_check_open_basedir(buf TSRMLS_CC)) {
close(data->fd);
+ data->fd = -1;
return;
}
}
@@ -342,6 +344,7 @@ PS_READ_FUNC(files)
PS(send_cookie) = 1;
}
php_session_reset_id(TSRMLS_C);
+ PS(session_status) = php_session_active;
}
ps_files_open(data, PS(id) TSRMLS_CC);
diff --git a/ext/session/mod_files.h b/ext/session/mod_files.h
index 94cbd6d025..d1d26cd39b 100644
--- a/ext/session/mod_files.h
+++ b/ext/session/mod_files.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/mod_mm.c b/ext/session/mod_mm.c
index 3d37b981bc..319f1d3c79 100644
--- a/ext/session/mod_mm.c
+++ b/ext/session/mod_mm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -371,6 +371,7 @@ PS_READ_FUNC(mm)
PS(send_cookie) = 1;
}
php_session_reset_id(TSRMLS_C);
+ PS(session_status) = php_session_active;
}
sd = ps_sd_lookup(data, PS(id), 0);
diff --git a/ext/session/mod_mm.h b/ext/session/mod_mm.h
index 3ddadced4e..cafbfa0932 100644
--- a/ext/session/mod_mm.h
+++ b/ext/session/mod_mm.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/mod_user.c b/ext/session/mod_user.c
index 1b606b9a33..5573d4cdfd 100644
--- a/ext/session/mod_user.c
+++ b/ext/session/mod_user.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/mod_user.h b/ext/session/mod_user.h
index 6b2998c426..b1f3688a25 100644
--- a/ext/session/mod_user.h
+++ b/ext/session/mod_user.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/mod_user_class.c b/ext/session/mod_user_class.c
index ea53af9ebe..3b6687741e 100644
--- a/ext/session/mod_user_class.c
+++ b/ext/session/mod_user_class.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/php_session.h b/ext/session/php_session.h
index e8e79f0fa6..d4de7a5c80 100644
--- a/ext/session/php_session.h
+++ b/ext/session/php_session.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/session/session.c b/ext/session/session.c
index 7bb6584621..7822ffe59c 100644
--- a/ext/session/session.c
+++ b/ext/session/session.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -492,18 +492,26 @@ static void php_session_initialize(TSRMLS_D) /* {{{ */
}
}
- php_session_reset_id(TSRMLS_C);
- PS(session_status) = php_session_active;
+ /* Set session ID for compatibility for older/3rd party save handlers */
+ if (!PS(use_strict_mode)) {
+ php_session_reset_id(TSRMLS_C);
+ PS(session_status) = php_session_active;
+ }
/* Read data */
php_session_track_init(TSRMLS_C);
if (PS(mod)->s_read(&PS(mod_data), PS(id), &val, &vallen TSRMLS_CC) == FAILURE) {
/* Some broken save handler implementation returns FAILURE for non-existent session ID */
- /* It's better to rase error for this, but disabled error for better compatibility */
+ /* It's better to raise error for this, but disabled error for better compatibility */
/*
php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Failed to read session data: %s (path: %s)", PS(mod)->s_name, PS(save_path));
*/
}
+ /* Set session ID if session read didn't activated session */
+ if (PS(use_strict_mode) && PS(session_status) != php_session_active) {
+ php_session_reset_id(TSRMLS_C);
+ PS(session_status) = php_session_active;
+ }
if (val) {
php_session_decode(val, vallen TSRMLS_CC);
efree(val);
@@ -661,11 +669,10 @@ static PHP_INI_MH(OnUpdateSaveDir) /* {{{ */
static PHP_INI_MH(OnUpdateName) /* {{{ */
{
/* Numeric session.name won't work at all */
- if (PG(modules_activated) &&
- (!new_value_length || is_numeric_string(new_value, new_value_length, NULL, NULL, 0))) {
+ if ((!new_value_length || is_numeric_string(new_value, new_value_length, NULL, NULL, 0))) {
int err_type;
- if (stage == ZEND_INI_STAGE_RUNTIME) {
+ if (stage == ZEND_INI_STAGE_RUNTIME || stage == ZEND_INI_STAGE_ACTIVATE || stage == ZEND_INI_STAGE_STARTUP) {
err_type = E_WARNING;
} else {
err_type = E_ERROR;
@@ -1268,6 +1275,49 @@ static int php_session_cache_limiter(TSRMLS_D) /* {{{ */
#define COOKIE_SECURE "; secure"
#define COOKIE_HTTPONLY "; HttpOnly"
+/*
+ * Remove already sent session ID cookie.
+ * It must be directly removed from SG(sapi_header) because sapi_add_header_ex()
+ * removes all of matching cookie. i.e. It deletes all of Set-Cookie headers.
+ */
+static void php_session_remove_cookie(TSRMLS_D) {
+ sapi_header_struct *header;
+ zend_llist *l = &SG(sapi_headers).headers;
+ zend_llist_element *next;
+ zend_llist_element *current;
+ char *session_cookie, *e_session_name;
+ int session_cookie_len, len = sizeof("Set-Cookie")-1;
+
+ e_session_name = php_url_encode(PS(session_name), strlen(PS(session_name)), NULL);
+ spprintf(&session_cookie, 0, "Set-Cookie: %s=", e_session_name);
+ efree(e_session_name);
+
+ session_cookie_len = strlen(session_cookie);
+ current = l->head;
+ while (current) {
+ header = (sapi_header_struct *)(current->data);
+ next = current->next;
+ if (header->header_len > len && header->header[len] == ':'
+ && !strncmp(header->header, session_cookie, session_cookie_len)) {
+ if (current->prev) {
+ current->prev->next = next;
+ } else {
+ l->head = next;
+ }
+ if (next) {
+ next->prev = current->prev;
+ } else {
+ l->tail = current->prev;
+ }
+ sapi_free_header(header);
+ efree(current);
+ --l->count;
+ }
+ current = next;
+ }
+ efree(session_cookie);
+}
+
static void php_session_send_cookie(TSRMLS_D) /* {{{ */
{
smart_str ncookie = {0};
@@ -1336,8 +1386,7 @@ static void php_session_send_cookie(TSRMLS_D) /* {{{ */
smart_str_0(&ncookie);
- /* 'replace' must be 0 here, else a previous Set-Cookie
- header, probably sent with setcookie() will be replaced! */
+ php_session_remove_cookie(TSRMLS_C); /* remove already sent session ID cookie */
sapi_add_header_ex(ncookie.c, ncookie.len, 0, 0 TSRMLS_CC);
}
/* }}} */
diff --git a/ext/session/tests/bug60634.phpt b/ext/session/tests/bug60634.phpt
index e2dfd15b37..86dcb11526 100644
--- a/ext/session/tests/bug60634.phpt
+++ b/ext/session/tests/bug60634.phpt
@@ -43,3 +43,4 @@ echo "um, hi\n";
--EXPECTF--
write: goodbye cruel world
close: goodbye cruel world
+
diff --git a/ext/session/tests/bug60634_error_4.phpt b/ext/session/tests/bug60634_error_4.phpt
index f21d077b54..d0b5786af9 100644
--- a/ext/session/tests/bug60634_error_4.phpt
+++ b/ext/session/tests/bug60634_error_4.phpt
@@ -49,3 +49,4 @@ Stack trace:
#1 {main}
thrown in %s on line %d
close: goodbye cruel world
+
diff --git a/ext/session/tests/bug66481-win32.phpt b/ext/session/tests/bug66481-win32.phpt
new file mode 100644
index 0000000000..cf06cb6b95
--- /dev/null
+++ b/ext/session/tests/bug66481-win32.phpt
@@ -0,0 +1,17 @@
+--TEST--
+Bug #66481: Calls to session_name() segfault when session.name is null, Windows.
+--INI--
+session.name=
+--SKIPIF--
+<?php include('skipif.inc'); ?>
+<?php if(substr(PHP_OS, 0, 3) != "WIN") die("skip Windows only"); ?>
+--FILE--
+<?php
+
+var_dump(session_name("foo"));
+var_dump(session_name("bar"));
+--EXPECTF--
+Warning: PHP Startup: session.name cannot be a numeric or empty '' in Unknown on line 0
+string(9) "PHPSESSID"
+string(3) "foo"
+PHP Warning: PHP Startup: session.name cannot be a numeric or empty '' in Unknown on line 0
diff --git a/ext/session/tests/bug66481.phpt b/ext/session/tests/bug66481.phpt
new file mode 100644
index 0000000000..5525ae8a38
--- /dev/null
+++ b/ext/session/tests/bug66481.phpt
@@ -0,0 +1,18 @@
+--TEST--
+Bug #66481: Calls to session_name() segfault when session.name is null.
+--INI--
+session.name=
+--SKIPIF--
+<?php include('skipif.inc'); ?>
+<?php if(substr(PHP_OS, 0, 3) == "WIN") die("skip Not for Windows"); ?>
+--FILE--
+<?php
+
+var_dump(session_name("foo"));
+var_dump(session_name("bar"));
+--EXPECTF--
+PHP Warning: PHP Startup: session.name cannot be a numeric or empty '' in Unknown on line 0
+
+Warning: PHP Startup: session.name cannot be a numeric or empty '' in Unknown on line 0
+string(9) "PHPSESSID"
+string(3) "foo"
diff --git a/ext/session/tests/session_name_error.phpt b/ext/session/tests/session_name_error.phpt
index 1b99d4ea35..9f0101d98b 100644
--- a/ext/session/tests/session_name_error.phpt
+++ b/ext/session/tests/session_name_error.phpt
@@ -231,6 +231,6 @@ string(12) "Hello World!"
-- Iteration 24 --
Warning: session_name() expects parameter 1 to be string, resource given in %s on line %d
-resource(5) of type (stream)
+resource(%d) of type (stream)
NULL
Done \ No newline at end of file
diff --git a/ext/shmop/php_shmop.h b/ext/shmop/php_shmop.h
index 0abc703d1f..2779fe14be 100644
--- a/ext/shmop/php_shmop.h
+++ b/ext/shmop/php_shmop.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/shmop/shmop.c b/ext/shmop/shmop.c
index a14a0b7e45..73372d4e8c 100644
--- a/ext/shmop/shmop.c
+++ b/ext/shmop/shmop.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/simplexml/php_simplexml.h b/ext/simplexml/php_simplexml.h
index c340a5e8a6..7314d8c825 100644
--- a/ext/simplexml/php_simplexml.h
+++ b/ext/simplexml/php_simplexml.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/simplexml/php_simplexml_exports.h b/ext/simplexml/php_simplexml_exports.h
index 66ec3bd28d..2c858566b9 100644
--- a/ext/simplexml/php_simplexml_exports.h
+++ b/ext/simplexml/php_simplexml_exports.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/simplexml/simplexml.c b/ext/simplexml/simplexml.c
index eba46b9091..363ea1fc44 100644
--- a/ext/simplexml/simplexml.c
+++ b/ext/simplexml/simplexml.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/simplexml/sxe.c b/ext/simplexml/sxe.c
index e3278da631..9a513e946f 100644
--- a/ext/simplexml/sxe.c
+++ b/ext/simplexml/sxe.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/simplexml/sxe.h b/ext/simplexml/sxe.h
index 5a40fefcb9..629e7b31d4 100644
--- a/ext/simplexml/sxe.h
+++ b/ext/simplexml/sxe.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/snmp/php_snmp.h b/ext/snmp/php_snmp.h
index a9e7eb3f2d..09ab8b9e81 100644
--- a/ext/snmp/php_snmp.h
+++ b/ext/snmp/php_snmp.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/snmp/snmp.c b/ext/snmp/snmp.c
index 4e2510afc8..4dd4badcd2 100644
--- a/ext/snmp/snmp.c
+++ b/ext/snmp/snmp.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -533,7 +533,7 @@ static void php_snmp_error(zval *object, const char *docref TSRMLS_DC, int type,
}
if (object && (snmp_object->exceptions_enabled & type)) {
- zend_throw_exception_ex(php_snmp_exception_ce, type, snmp_object->snmp_errstr TSRMLS_CC);
+ zend_throw_exception_ex(php_snmp_exception_ce, type TSRMLS_CC, snmp_object->snmp_errstr);
} else {
va_start(args, format);
php_verror(docref, "", E_WARNING, format, args TSRMLS_CC);
@@ -896,6 +896,12 @@ retry:
keepwalking = 1;
}
} else {
+ if (st & SNMP_CMD_WALK && response->errstat == SNMP_ERR_TOOBIG && objid_query->max_repetitions > 1) { /* Answer will not fit into single packet */
+ objid_query->max_repetitions /= 2;
+ snmp_free_pdu(response);
+ keepwalking = 1;
+ continue;
+ }
if (!(st & SNMP_CMD_WALK) || response->errstat != SNMP_ERR_NOSUCHNAME || Z_TYPE_P(return_value) == IS_BOOL) {
for ( count=1, vars = response->variables;
vars && count != response->errindex;
diff --git a/ext/soap/php_encoding.c b/ext/soap/php_encoding.c
index 5cec3e558e..32e88510e7 100644
--- a/ext/soap/php_encoding.c
+++ b/ext/soap/php_encoding.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_encoding.h b/ext/soap/php_encoding.h
index 31a8469390..5a8186ff74 100644
--- a/ext/soap/php_encoding.h
+++ b/ext/soap/php_encoding.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_http.c b/ext/soap/php_http.c
index 86ab03d9c8..3d62bbe2f8 100644
--- a/ext/soap/php_http.c
+++ b/ext/soap/php_http.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_http.h b/ext/soap/php_http.h
index 70d2cfd4c2..d927daa37f 100644
--- a/ext/soap/php_http.h
+++ b/ext/soap/php_http.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_packet_soap.c b/ext/soap/php_packet_soap.c
index f4d249c4a9..3f4553b16a 100644
--- a/ext/soap/php_packet_soap.c
+++ b/ext/soap/php_packet_soap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_packet_soap.h b/ext/soap/php_packet_soap.h
index 210539bcd0..dacf5055a2 100644
--- a/ext/soap/php_packet_soap.h
+++ b/ext/soap/php_packet_soap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_schema.c b/ext/soap/php_schema.c
index 25bb177273..58037199d9 100644
--- a/ext/soap/php_schema.c
+++ b/ext/soap/php_schema.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_schema.h b/ext/soap/php_schema.h
index 81748f5f65..62075b9531 100644
--- a/ext/soap/php_schema.h
+++ b/ext/soap/php_schema.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_sdl.c b/ext/soap/php_sdl.c
index a7a5071c08..03c0748217 100644
--- a/ext/soap/php_sdl.c
+++ b/ext/soap/php_sdl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_sdl.h b/ext/soap/php_sdl.h
index 78757d15fc..fd2d78db9e 100644
--- a/ext/soap/php_sdl.h
+++ b/ext/soap/php_sdl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_soap.h b/ext/soap/php_soap.h
index 7d0a3c16f1..fb8d1d60fb 100644
--- a/ext/soap/php_soap.h
+++ b/ext/soap/php_soap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_xml.c b/ext/soap/php_xml.c
index 939385557d..f7c8fd51e5 100644
--- a/ext/soap/php_xml.c
+++ b/ext/soap/php_xml.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/php_xml.h b/ext/soap/php_xml.h
index 61c0feb58c..1eddcf9503 100644
--- a/ext/soap/php_xml.h
+++ b/ext/soap/php_xml.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/soap/soap.c b/ext/soap/soap.c
index 00e80efbcb..60f6e21380 100644
--- a/ext/soap/soap.c
+++ b/ext/soap/soap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -2546,7 +2546,7 @@ static int do_request(zval *this_ptr, xmlDoc *request, char *location, char *act
int ret = TRUE;
char *buf;
int buf_size;
- zval func, param0, param1, param2, param3, param4;
+ zval func;
zval *params[5];
zval **trace;
zval **fault;
@@ -2566,29 +2566,24 @@ static int do_request(zval *this_ptr, xmlDoc *request, char *location, char *act
INIT_ZVAL(func);
ZVAL_STRINGL(&func,"__doRequest",sizeof("__doRequest")-1,0);
- INIT_ZVAL(param0);
- params[0] = &param0;
- ZVAL_STRINGL(params[0], buf, buf_size, 0);
- INIT_ZVAL(param1);
- params[1] = &param1;
+ ALLOC_INIT_ZVAL(params[0]);
+ ZVAL_STRINGL(params[0], buf, buf_size, 1);
+ ALLOC_INIT_ZVAL(params[1]);
if (location == NULL) {
ZVAL_NULL(params[1]);
} else {
- ZVAL_STRING(params[1], location, 0);
+ ZVAL_STRING(params[1], location, 1);
}
- INIT_ZVAL(param2);
- params[2] = &param2;
+ ALLOC_INIT_ZVAL(params[2]);
if (action == NULL) {
ZVAL_NULL(params[2]);
} else {
- ZVAL_STRING(params[2], action, 0);
+ ZVAL_STRING(params[2], action, 1);
}
- INIT_ZVAL(param3);
- params[3] = &param3;
+ ALLOC_INIT_ZVAL(params[3]);
ZVAL_LONG(params[3], version);
- INIT_ZVAL(param4);
- params[4] = &param4;
+ ALLOC_INIT_ZVAL(params[4]);
ZVAL_LONG(params[4], one_way);
if (call_user_function(NULL, &this_ptr, &func, response, 5, params TSRMLS_CC) != SUCCESS) {
@@ -2603,6 +2598,11 @@ static int do_request(zval *this_ptr, xmlDoc *request, char *location, char *act
Z_LVAL_PP(trace) > 0) {
add_property_stringl(this_ptr, "__last_response", Z_STRVAL_P(response), Z_STRLEN_P(response), 1);
}
+ zval_ptr_dtor(&params[4]);
+ zval_ptr_dtor(&params[3]);
+ zval_ptr_dtor(&params[2]);
+ zval_ptr_dtor(&params[1]);
+ zval_ptr_dtor(&params[0]);
xmlFree(buf);
if (ret && zend_hash_find(Z_OBJPROP_P(this_ptr), "__soap_fault", sizeof("__soap_fault"), (void **) &fault) == SUCCESS) {
return FALSE;
@@ -2694,124 +2694,134 @@ static void do_soap_call(zval* this_ptr,
SOAP_GLOBAL(features) = 0;
}
- if (sdl != NULL) {
- fn = get_function(sdl, function);
- if (fn != NULL) {
- sdlBindingPtr binding = fn->binding;
- int one_way = 0;
-
- if (fn->responseName == NULL &&
- fn->responseParameters == NULL &&
- soap_headers == NULL) {
- one_way = 1;
- }
-
- if (location == NULL) {
- location = binding->location;
- }
- if (binding->bindingType == BINDING_SOAP) {
- sdlSoapBindingFunctionPtr fnb = (sdlSoapBindingFunctionPtr)fn->bindingAttributes;
- request = serialize_function_call(this_ptr, fn, NULL, fnb->input.ns, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
- ret = do_request(this_ptr, request, location, fnb->soapAction, soap_version, one_way, &response TSRMLS_CC);
- } else {
- request = serialize_function_call(this_ptr, fn, NULL, sdl->target_ns, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
- ret = do_request(this_ptr, request, location, NULL, soap_version, one_way, &response TSRMLS_CC);
- }
-
- xmlFreeDoc(request);
-
- if (ret && Z_TYPE(response) == IS_STRING) {
- encode_reset_ns();
- ret = parse_packet_soap(this_ptr, Z_STRVAL(response), Z_STRLEN(response), fn, NULL, return_value, output_headers TSRMLS_CC);
- encode_finish();
- }
+ zend_try {
+ if (sdl != NULL) {
+ fn = get_function(sdl, function);
+ if (fn != NULL) {
+ sdlBindingPtr binding = fn->binding;
+ int one_way = 0;
+
+ if (fn->responseName == NULL &&
+ fn->responseParameters == NULL &&
+ soap_headers == NULL) {
+ one_way = 1;
+ }
- zval_dtor(&response);
+ if (location == NULL) {
+ location = binding->location;
+ }
+ if (binding->bindingType == BINDING_SOAP) {
+ sdlSoapBindingFunctionPtr fnb = (sdlSoapBindingFunctionPtr)fn->bindingAttributes;
+ request = serialize_function_call(this_ptr, fn, NULL, fnb->input.ns, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
+ ret = do_request(this_ptr, request, location, fnb->soapAction, soap_version, one_way, &response TSRMLS_CC);
+ } else {
+ request = serialize_function_call(this_ptr, fn, NULL, sdl->target_ns, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
+ ret = do_request(this_ptr, request, location, NULL, soap_version, one_way, &response TSRMLS_CC);
+ }
+
+ xmlFreeDoc(request);
+
+ if (ret && Z_TYPE(response) == IS_STRING) {
+ encode_reset_ns();
+ ret = parse_packet_soap(this_ptr, Z_STRVAL(response), Z_STRLEN(response), fn, NULL, return_value, output_headers TSRMLS_CC);
+ encode_finish();
+ }
- } else {
- smart_str error = {0};
- smart_str_appends(&error,"Function (\"");
- smart_str_appends(&error,function);
- smart_str_appends(&error,"\") is not a valid method for this service");
- smart_str_0(&error);
- add_soap_fault(this_ptr, "Client", error.c, NULL, NULL TSRMLS_CC);
- smart_str_free(&error);
- }
- } else {
- zval **uri;
- smart_str action = {0};
+ zval_dtor(&response);
- if (zend_hash_find(Z_OBJPROP_P(this_ptr), "uri", sizeof("uri"), (void *)&uri) == FAILURE) {
- add_soap_fault(this_ptr, "Client", "Error finding \"uri\" property", NULL, NULL TSRMLS_CC);
- } else if (location == NULL) {
- add_soap_fault(this_ptr, "Client", "Error could not find \"location\" property", NULL, NULL TSRMLS_CC);
- } else {
- if (call_uri == NULL) {
- call_uri = Z_STRVAL_PP(uri);
+ } else {
+ smart_str error = {0};
+ smart_str_appends(&error,"Function (\"");
+ smart_str_appends(&error,function);
+ smart_str_appends(&error,"\") is not a valid method for this service");
+ smart_str_0(&error);
+ add_soap_fault(this_ptr, "Client", error.c, NULL, NULL TSRMLS_CC);
+ smart_str_free(&error);
}
- request = serialize_function_call(this_ptr, NULL, function, call_uri, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
+ } else {
+ zval **uri;
+ smart_str action = {0};
- if (soap_action == NULL) {
- smart_str_appends(&action, call_uri);
- smart_str_appendc(&action, '#');
- smart_str_appends(&action, function);
+ if (zend_hash_find(Z_OBJPROP_P(this_ptr), "uri", sizeof("uri"), (void *)&uri) == FAILURE) {
+ add_soap_fault(this_ptr, "Client", "Error finding \"uri\" property", NULL, NULL TSRMLS_CC);
+ } else if (location == NULL) {
+ add_soap_fault(this_ptr, "Client", "Error could not find \"location\" property", NULL, NULL TSRMLS_CC);
} else {
- smart_str_appends(&action, soap_action);
- }
- smart_str_0(&action);
+ if (call_uri == NULL) {
+ call_uri = Z_STRVAL_PP(uri);
+ }
+ request = serialize_function_call(this_ptr, NULL, function, call_uri, real_args, arg_count, soap_version, soap_headers TSRMLS_CC);
- ret = do_request(this_ptr, request, location, action.c, soap_version, 0, &response TSRMLS_CC);
+ if (soap_action == NULL) {
+ smart_str_appends(&action, call_uri);
+ smart_str_appendc(&action, '#');
+ smart_str_appends(&action, function);
+ } else {
+ smart_str_appends(&action, soap_action);
+ }
+ smart_str_0(&action);
- smart_str_free(&action);
- xmlFreeDoc(request);
+ ret = do_request(this_ptr, request, location, action.c, soap_version, 0, &response TSRMLS_CC);
- if (ret && Z_TYPE(response) == IS_STRING) {
- encode_reset_ns();
- ret = parse_packet_soap(this_ptr, Z_STRVAL(response), Z_STRLEN(response), NULL, function, return_value, output_headers TSRMLS_CC);
- encode_finish();
- }
+ smart_str_free(&action);
+ xmlFreeDoc(request);
- zval_dtor(&response);
- }
- }
+ if (ret && Z_TYPE(response) == IS_STRING) {
+ encode_reset_ns();
+ ret = parse_packet_soap(this_ptr, Z_STRVAL(response), Z_STRLEN(response), NULL, function, return_value, output_headers TSRMLS_CC);
+ encode_finish();
+ }
- if (!ret) {
- zval** fault;
- if (zend_hash_find(Z_OBJPROP_P(this_ptr), "__soap_fault", sizeof("__soap_fault"), (void **) &fault) == SUCCESS) {
- *return_value = **fault;
- zval_copy_ctor(return_value);
+ zval_dtor(&response);
+ }
+ }
+
+ if (!ret) {
+ zval** fault;
+ if (zend_hash_find(Z_OBJPROP_P(this_ptr), "__soap_fault", sizeof("__soap_fault"), (void **) &fault) == SUCCESS) {
+ *return_value = **fault;
+ zval_copy_ctor(return_value);
+ } else {
+ *return_value = *add_soap_fault(this_ptr, "Client", "Unknown Error", NULL, NULL TSRMLS_CC);
+ zval_copy_ctor(return_value);
+ }
} else {
- *return_value = *add_soap_fault(this_ptr, "Client", "Unknown Error", NULL, NULL TSRMLS_CC);
- zval_copy_ctor(return_value);
- }
- } else {
- zval** fault;
- if (zend_hash_find(Z_OBJPROP_P(this_ptr), "__soap_fault", sizeof("__soap_fault"), (void **) &fault) == SUCCESS) {
- *return_value = **fault;
- zval_copy_ctor(return_value);
+ zval** fault;
+ if (zend_hash_find(Z_OBJPROP_P(this_ptr), "__soap_fault", sizeof("__soap_fault"), (void **) &fault) == SUCCESS) {
+ *return_value = **fault;
+ zval_copy_ctor(return_value);
+ }
}
- }
- if (!EG(exception) &&
- Z_TYPE_P(return_value) == IS_OBJECT &&
- instanceof_function(Z_OBJCE_P(return_value), soap_fault_class_entry TSRMLS_CC) &&
- (zend_hash_find(Z_OBJPROP_P(this_ptr), "_exceptions", sizeof("_exceptions"), (void **) &tmp) != SUCCESS ||
- Z_TYPE_PP(tmp) != IS_BOOL || Z_LVAL_PP(tmp) != 0)) {
- zval *exception;
+ if (!EG(exception) &&
+ Z_TYPE_P(return_value) == IS_OBJECT &&
+ instanceof_function(Z_OBJCE_P(return_value), soap_fault_class_entry TSRMLS_CC) &&
+ (zend_hash_find(Z_OBJPROP_P(this_ptr), "_exceptions", sizeof("_exceptions"), (void **) &tmp) != SUCCESS ||
+ Z_TYPE_PP(tmp) != IS_BOOL || Z_LVAL_PP(tmp) != 0)) {
+ zval *exception;
- MAKE_STD_ZVAL(exception);
- MAKE_COPY_ZVAL(&return_value, exception);
- zend_throw_exception_object(exception TSRMLS_CC);
- }
+ MAKE_STD_ZVAL(exception);
+ MAKE_COPY_ZVAL(&return_value, exception);
+ zend_throw_exception_object(exception TSRMLS_CC);
+ }
+ } zend_catch {
+ _bailout = 1;
+ } zend_end_try();
+
if (SOAP_GLOBAL(encoding) != NULL) {
xmlCharEncCloseFunc(SOAP_GLOBAL(encoding));
}
+
SOAP_GLOBAL(features) = old_features;
SOAP_GLOBAL(typemap) = old_typemap;
SOAP_GLOBAL(class_map) = old_class_map;
SOAP_GLOBAL(encoding) = old_encoding;
SOAP_GLOBAL(sdl) = old_sdl;
+ if (_bailout) {
+ _bailout = 0;
+ zend_bailout();
+ }
SOAP_CLIENT_END_CODE();
}
diff --git a/ext/soap/tests/bugs/bug66112.phpt b/ext/soap/tests/bugs/bug66112.phpt
new file mode 100644
index 0000000000..4d5be79296
--- /dev/null
+++ b/ext/soap/tests/bugs/bug66112.phpt
@@ -0,0 +1,36 @@
+--TEST--
+Bug #66112 (Use after free condition in SOAP extension)
+--SKIPIF--
+<?php require_once('skipif.inc'); ?>
+--INI--
+soap.wsdl_cache_enabled=0
+--FILE--
+<?php
+define('WSDL', dirname(__FILE__)."/bug66112.wsdl");
+function Mist($p) {
+ $client=new soapclient(WSDL, array('typemap'=>array(array("type_ns"=>"uri:mist", "type_name"=>"A"))));
+ try{
+ $client->Mist(array("XX"=>"xx"));
+ }catch(SoapFault $x){
+ }
+ return array("A"=>"ABC","B"=>"sss");
+}
+$s = new SoapServer(WSDL, array('typemap'=>array(array("type_ns"=>"uri:mist", "type_name"=>"A"))));
+$s->addFunction("Mist");
+$_SERVER["REQUEST_METHOD"] = "POST";
+$HTTP_RAW_POST_DATA=<<<EOF
+<?xml version="1.0" encoding="UTF-8"?>
+<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:uri="uri:mist">
+ <soapenv:Header/>
+ <soapenv:Body>
+ <uri:Request><uri:A>XXX</uri:A><uri:B>yyy</uri:B></uri:Request>
+ </soapenv:Body>
+</soapenv:Envelope>
+EOF;
+$s->handle($HTTP_RAW_POST_DATA);
+echo "OK\n";
+?>
+--EXPECT--
+<?xml version="1.0" encoding="UTF-8"?>
+<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="uri:mist"><SOAP-ENV:Body><ns1:Response><A>ABC</A><B>sss</B></ns1:Response></SOAP-ENV:Body></SOAP-ENV:Envelope>
+OK
diff --git a/ext/soap/tests/bugs/bug66112.wsdl b/ext/soap/tests/bugs/bug66112.wsdl
new file mode 100644
index 0000000000..8589a46bf2
--- /dev/null
+++ b/ext/soap/tests/bugs/bug66112.wsdl
@@ -0,0 +1,42 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<wsdl:definitions xmlns:tns="uri:mist" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" name="test" targetNamespace="uri:mist">
+ <wsdl:types>
+ <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" targetNamespace="uri:mist">
+ <xs:complexType name="T1">
+ <xs:sequence>
+ <xs:element name="A" type="xsd:string"/><xs:element name="B" type="xsd:string"/>
+ </xs:sequence>
+ </xs:complexType>
+ <xs:element name="Request" type="tns:T1"/><xs:element name="Response" type="tns:T1"/>
+ </xs:schema>
+ </wsdl:types>
+ <wsdl:message name="Request">
+ <wsdl:part name="Request" element="tns:Request"/>
+ </wsdl:message>
+ <wsdl:message name="Response">
+ <wsdl:part name="Response" element="tns:Response"/>
+ </wsdl:message>
+ <wsdl:portType name="test">
+ <wsdl:operation name="Mist">
+ <wsdl:input message="tns:Request"/>
+ <wsdl:output message="tns:Response"/>
+ </wsdl:operation>
+ </wsdl:portType>
+ <wsdl:binding name="test" type="tns:test">
+ <soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
+ <wsdl:operation name="Mist">
+ <soap:operation soapAction="Mist"/>
+ <wsdl:input>
+ <soap:body use="literal"/>
+ </wsdl:input>
+ <wsdl:output>
+ <soap:body use="literal"/>
+ </wsdl:output>
+ </wsdl:operation>
+ </wsdl:binding>
+ <wsdl:service name="test">
+ <wsdl:port name="test" binding="tns:test">
+ <soap:address location="http://127.0.0.1:81/mist.php"/>
+ </wsdl:port>
+ </wsdl:service>
+</wsdl:definitions>
diff --git a/ext/sockets/config.m4 b/ext/sockets/config.m4
index 9c75249646..a5a63dfb61 100644
--- a/ext/sockets/config.m4
+++ b/ext/sockets/config.m4
@@ -16,10 +16,10 @@ if test "$PHP_SOCKETS" != "no"; then
if test "$ac_cv_cmsghdr" = yes; then
AC_DEFINE(HAVE_CMSGHDR,1,[Whether you have struct cmsghdr])
- fi
+ fi
AC_CHECK_FUNCS([hstrerror socketpair if_nametoindex if_indextoname])
- AC_CHECK_HEADERS([netdb.h netinet/tcp.h sys/un.h sys/sockio.h errno.h])
+ AC_CHECK_HEADERS([netdb.h netinet/tcp.h sys/un.h sys/sockio.h errno.h])
AC_TRY_COMPILE([
#include <sys/types.h>
#include <sys/socket.h>
@@ -27,7 +27,7 @@ if test "$PHP_SOCKETS" != "no"; then
[AC_DEFINE(MISSING_MSGHDR_MSGFLAGS, 1, [ ])]
)
AC_DEFINE([HAVE_SOCKETS], 1, [ ])
-
+
dnl Check for fied ss_family in sockaddr_storage (missing in AIX until 5.3)
AC_CACHE_CHECK([for field ss_family in struct sockaddr_storage], ac_cv_ss_family,
[
@@ -38,11 +38,24 @@ if test "$PHP_SOCKETS" != "no"; then
], [struct sockaddr_storage sa_store; sa_store.ss_family = AF_INET6;],
ac_cv_ss_family=yes, ac_cv_ss_family=no)
])
-
+
if test "$ac_cv_ss_family" = yes; then
AC_DEFINE(HAVE_SA_SS_FAMILY,1,[Whether you have sockaddr_storage.ss_family])
fi
+ dnl Check for AI_V4MAPPED flag
+ AC_CACHE_CHECK([if getaddrinfo supports AI_V4MAPPED],[ac_cv_gai_ai_v4mapped],
+ [
+ AC_TRY_COMPILE([
+#include <netdb.h>
+ ], [int flag = AI_V4MAPPED;],
+ ac_cv_gai_ai_v4mapped=yes, ac_cv_gai_ai_v4mapped=no)
+ ])
+
+ if test "$ac_cv_gai_ai_v4mapped" = yes; then
+ AC_DEFINE(HAVE_AI_V4MAPPED,1,[Whether you have AI_V4MAPPED])
+ fi
+
PHP_NEW_EXTENSION([sockets], [sockets.c multicast.c conversions.c sockaddr_conv.c sendrecvmsg.c], [$ext_shared])
PHP_INSTALL_HEADERS([ext/sockets/], [php_sockets.h])
fi
diff --git a/ext/sockets/multicast.c b/ext/sockets/multicast.c
index ecf3a65a32..dc3151a137 100644
--- a/ext/sockets/multicast.c
+++ b/ext/sockets/multicast.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sockets/multicast.h b/ext/sockets/multicast.h
index 81a1bca799..f89f56ed39 100644
--- a/ext/sockets/multicast.h
+++ b/ext/sockets/multicast.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sockets/php_sockets.h b/ext/sockets/php_sockets.h
index 17abf95a19..e872635f9a 100644
--- a/ext/sockets/php_sockets.h
+++ b/ext/sockets/php_sockets.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -109,6 +109,10 @@ php_socket *socket_import_file_descriptor(PHP_SOCKET sock TSRMLS_DC);
#define phpext_sockets_ptr NULL
#endif
+#if defined(_AIX) && !defined(HAVE_SA_SS_FAMILY)
+# define ss_family __ss_family
+#endif
+
#endif
/*
diff --git a/ext/sockets/sockaddr_conv.c b/ext/sockets/sockaddr_conv.c
index 64523c3191..1c1a90d58f 100644
--- a/ext/sockets/sockaddr_conv.c
+++ b/ext/sockets/sockaddr_conv.c
@@ -9,6 +9,8 @@
#include <arpa/inet.h>
#endif
+extern int php_string_to_if_index(const char *val, unsigned *out TSRMLS_DC);
+
#if HAVE_IPV6
/* Sets addr by hostname, or by ip in string form (AF_INET6) */
int php_set_inet6_addr(struct sockaddr_in6 *sin6, char *string, php_socket *php_sock TSRMLS_DC) /* {{{ */
@@ -27,7 +29,11 @@ int php_set_inet6_addr(struct sockaddr_in6 *sin6, char *string, php_socket *php_
memset(&hints, 0, sizeof(struct addrinfo));
hints.ai_family = AF_INET6;
+#if HAVE_AI_V4MAPPED
hints.ai_flags = AI_V4MAPPED | AI_ADDRCONFIG;
+#else
+ hints.ai_flags = AI_ADDRCONFIG;
+#endif
getaddrinfo(string, NULL, &hints, &addrinfo);
if (!addrinfo) {
#ifdef PHP_WIN32
diff --git a/ext/sockets/sockets.c b/ext/sockets/sockets.c
index 4a2a41b5fd..bd0a8f2f70 100644
--- a/ext/sockets/sockets.c
+++ b/ext/sockets/sockets.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -56,9 +56,6 @@
# define IS_INVALID_SOCKET(a) (a->bsd_socket < 0)
# define set_errno(a) (errno = a)
# include "php_sockets.h"
-# if defined(_AIX) && !defined(HAVE_SA_SS_FAMILY)
-# define ss_family __ss_family
-# endif
# if HAVE_IF_NAMETOINDEX
# include <net/if.h>
# endif
diff --git a/ext/sockets/unix_socket_constants.h b/ext/sockets/unix_socket_constants.h
index fb190d82b1..485b2534d2 100644
--- a/ext/sockets/unix_socket_constants.h
+++ b/ext/sockets/unix_socket_constants.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sockets/win32_socket_constants.h b/ext/sockets/win32_socket_constants.h
index 542347dd07..848e14fb51 100644
--- a/ext/sockets/win32_socket_constants.h
+++ b/ext/sockets/win32_socket_constants.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/php_spl.c b/ext/spl/php_spl.c
index 716990d80f..5927e05562 100644
--- a/ext/spl/php_spl.c
+++ b/ext/spl/php_spl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/php_spl.h b/ext/spl/php_spl.h
index 4794f12443..aadb69d212 100644
--- a/ext/spl/php_spl.h
+++ b/ext/spl/php_spl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_array.c b/ext/spl/spl_array.c
index ca8076a957..f41d0fb9cd 100644
--- a/ext/spl/spl_array.c
+++ b/ext/spl/spl_array.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_array.h b/ext/spl/spl_array.h
index 0423d89a3a..23ca80bc8f 100644
--- a/ext/spl/spl_array.h
+++ b/ext/spl/spl_array.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_directory.c b/ext/spl/spl_directory.c
index 3dc7b7925c..6e53c7a947 100644
--- a/ext/spl/spl_directory.c
+++ b/ext/spl/spl_directory.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_directory.h b/ext/spl/spl_directory.h
index d95ba550f8..8cff7d98d0 100644
--- a/ext/spl/spl_directory.h
+++ b/ext/spl/spl_directory.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_dllist.c b/ext/spl/spl_dllist.c
index 273bc7506a..39a0733b9a 100644
--- a/ext/spl/spl_dllist.c
+++ b/ext/spl/spl_dllist.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_dllist.h b/ext/spl/spl_dllist.h
index 8615f748b8..c6f82ce57a 100644
--- a/ext/spl/spl_dllist.h
+++ b/ext/spl/spl_dllist.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_engine.c b/ext/spl/spl_engine.c
index ea2349f41e..c07ce6846f 100644
--- a/ext/spl/spl_engine.c
+++ b/ext/spl/spl_engine.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_engine.h b/ext/spl/spl_engine.h
index 103a5c4c76..a67e60c105 100644
--- a/ext/spl/spl_engine.h
+++ b/ext/spl/spl_engine.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_exceptions.c b/ext/spl/spl_exceptions.c
index d905070f41..221b25df47 100644
--- a/ext/spl/spl_exceptions.c
+++ b/ext/spl/spl_exceptions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_exceptions.h b/ext/spl/spl_exceptions.h
index e4e7f270de..5e4e0f702c 100644
--- a/ext/spl/spl_exceptions.h
+++ b/ext/spl/spl_exceptions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_fixedarray.c b/ext/spl/spl_fixedarray.c
index 86a5371ed3..ca61b3bd97 100644
--- a/ext/spl/spl_fixedarray.c
+++ b/ext/spl/spl_fixedarray.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_fixedarray.h b/ext/spl/spl_fixedarray.h
index 8f1b8df103..9011e8c1d5 100644
--- a/ext/spl/spl_fixedarray.h
+++ b/ext/spl/spl_fixedarray.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_functions.c b/ext/spl/spl_functions.c
index 7f17d5ef23..f1e59c0234 100644
--- a/ext/spl/spl_functions.c
+++ b/ext/spl/spl_functions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_functions.h b/ext/spl/spl_functions.h
index 29ce4a7640..214780f869 100644
--- a/ext/spl/spl_functions.h
+++ b/ext/spl/spl_functions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_heap.c b/ext/spl/spl_heap.c
index cb1f68dcf1..2bc1f5e3d5 100644
--- a/ext/spl/spl_heap.c
+++ b/ext/spl/spl_heap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_heap.h b/ext/spl/spl_heap.h
index 11bce04553..a3ac4a8f5c 100644
--- a/ext/spl/spl_heap.h
+++ b/ext/spl/spl_heap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_iterators.c b/ext/spl/spl_iterators.c
index 30532756cb..2517366330 100644
--- a/ext/spl/spl_iterators.c
+++ b/ext/spl/spl_iterators.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_iterators.h b/ext/spl/spl_iterators.h
index 73d9d2e614..3991ddad33 100644
--- a/ext/spl/spl_iterators.h
+++ b/ext/spl/spl_iterators.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_observer.c b/ext/spl/spl_observer.c
index 5d89566eec..1a706f7642 100644
--- a/ext/spl/spl_observer.c
+++ b/ext/spl/spl_observer.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/spl_observer.h b/ext/spl/spl_observer.h
index e93e304310..51573d732f 100644
--- a/ext/spl/spl_observer.h
+++ b/ext/spl/spl_observer.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/spl/tests/SplFileObject_getflags_basic.phpt b/ext/spl/tests/SplFileObject_getflags_basic.phpt
index 5addadf380..88cf6861a2 100644
--- a/ext/spl/tests/SplFileObject_getflags_basic.phpt
+++ b/ext/spl/tests/SplFileObject_getflags_basic.phpt
@@ -7,16 +7,16 @@ Erwin Poeze <erwin.poeze@gmail.com>
--FILE--
<?php
-file_put_contents('testdata.csv', 'eerste;tweede;derde');
+file_put_contents('SplFileObject_getflags_basic.csv', 'eerste;tweede;derde');
-$fo = new SplFileObject('testdata.csv');
+$fo = new SplFileObject('SplFileObject_getflags_basic.csv');
$fo->setFlags(SplFileObject::DROP_NEW_LINE);
var_dump($fo->getFlags());
?>
--CLEAN--
<?php
-unlink('testdata.csv');
+unlink('SplFileObject_getflags_basic.csv');
?>
--EXPECT--
int(1)
diff --git a/ext/spl/tests/SplFileObject_getflags_error001.phpt b/ext/spl/tests/SplFileObject_getflags_error001.phpt
index 1602f88885..ca53c857e7 100644
--- a/ext/spl/tests/SplFileObject_getflags_error001.phpt
+++ b/ext/spl/tests/SplFileObject_getflags_error001.phpt
@@ -7,10 +7,10 @@ Erwin Poeze <erwin.poeze@gmail.com>
--FILE--
<?php
-file_put_contents('testdata.csv', 'eerste;tweede;derde');
+file_put_contents('SplFileObject_getflags_error001.csv', 'eerste;tweede;derde');
-$fo = new SplFileObject('testdata.csv');
+$fo = new SplFileObject('SplFileObject_getflags_error001.csv');
$fo->setFlags(SplFileObject::READ_CSV);
$fo->setFlags(SplFileObject::DROP_NEW_LINE);
@@ -20,7 +20,7 @@ var_dump($fo->getFlags());
?>
--CLEAN--
<?php
-unlink('testdata.csv');
+unlink('SplFileObject_getflags_error001.csv');
?>
--EXPECT--
int(1)
diff --git a/ext/spl/tests/SplFileObject_getflags_error002.phpt b/ext/spl/tests/SplFileObject_getflags_error002.phpt
index e2c8255f44..00fd351db8 100644
--- a/ext/spl/tests/SplFileObject_getflags_error002.phpt
+++ b/ext/spl/tests/SplFileObject_getflags_error002.phpt
@@ -5,9 +5,9 @@ Erwin Poeze <erwin.poeze@gmail.com>
--FILE--
<?php
-file_put_contents('testdata.csv', 'eerste;tweede;derde');
+file_put_contents('SplFileObject_getflags_error002.csv', 'eerste;tweede;derde');
-$fo = new SplFileObject('testdata.csv');
+$fo = new SplFileObject('SplFileObject_getflags_error002.csv');
$fo->setFlags(SplFileObject::READ_CSV);
$fo->getFlags('fake');
@@ -15,7 +15,7 @@ $fo->getFlags('fake');
?>
--CLEAN--
<?php
-unlink('testdata.csv');
+unlink('SplFileObject_getflags_error002.csv');
?>
--EXPECTF--
Warning: SplFileObject::getFlags() expects exactly 0 parameters, 1 given in %s on line %d
diff --git a/ext/spl/tests/SplFileObject_rewind_error001.phpt b/ext/spl/tests/SplFileObject_rewind_error001.phpt
index ac536a0a44..5f2379aa13 100644
--- a/ext/spl/tests/SplFileObject_rewind_error001.phpt
+++ b/ext/spl/tests/SplFileObject_rewind_error001.phpt
@@ -7,16 +7,16 @@ Erwin Poeze <erwin.poeze@gmail.com>
--FILE--
<?php
-file_put_contents('testdata.csv', 'eerste;tweede;derde');
+file_put_contents('SplFileObject_rewind_error001.csv', 'eerste;tweede;derde');
-$fo = new SplFileObject('testdata.csv');
+$fo = new SplFileObject('SplFileObject_rewind_error001.csv');
$fo->rewind( "invalid" );
?>
--CLEAN--
<?php
-unlink('testdata.csv');
+unlink('SplFileObject_rewind_error001.csv');
?>
--EXPECTF--
Warning: SplFileObject::rewind() expects exactly 0 parameters, 1 given in %s on line %d
diff --git a/ext/spl/tests/bug54291.phpt b/ext/spl/tests/bug54291.phpt
index b8f596e02c..9314b6b9ff 100644
--- a/ext/spl/tests/bug54291.phpt
+++ b/ext/spl/tests/bug54291.phpt
@@ -7,7 +7,7 @@ $dir->isFile();
--EXPECTF--
Fatal error: Uncaught exception 'UnexpectedValueException' with message 'Failed to open directory ""' in %s:%d
Stack trace:
-#0 %s(%d): DirectoryIterator->__construct('?/abc')
+#0 %s(%d): DirectoryIterator->__construct('\x00/abc')
#1 {main}
thrown in %s on line %d
diff --git a/ext/spl/tests/class_implements_variation.phpt b/ext/spl/tests/class_implements_variation.phpt
index 52fdbcaf70..84a52ab2da 100644
--- a/ext/spl/tests/class_implements_variation.phpt
+++ b/ext/spl/tests/class_implements_variation.phpt
@@ -16,8 +16,8 @@ var_dump(class_implements(new fs));
var_dump(class_implements('fs'));
echo "\n--- testing autoload ---\n";
-var_dump(class_implements('non-existent'));
-var_dump(class_implements('non-existent2', false));
+var_dump(class_implements('non_existent'));
+var_dump(class_implements('non_existent2', false));
function __autoload($classname) {
@@ -35,11 +35,11 @@ array(0) {
}
--- testing autoload ---
-attempting to autoload non-existent
+attempting to autoload non_existent
-Warning: class_implements(): Class non-existent does not exist and could not be loaded in %s on line %d
+Warning: class_implements(): Class non_existent does not exist and could not be loaded in %s on line %d
bool(false)
-Warning: class_implements(): Class non-existent2 does not exist in %s on line %d
+Warning: class_implements(): Class non_existent2 does not exist in %s on line %d
bool(false)
===DONE===
diff --git a/ext/spl/tests/class_uses_variation.phpt b/ext/spl/tests/class_uses_variation.phpt
index 9c21521c60..1a13521eaf 100644
--- a/ext/spl/tests/class_uses_variation.phpt
+++ b/ext/spl/tests/class_uses_variation.phpt
@@ -16,8 +16,8 @@ var_dump(class_uses(new fs));
var_dump(class_uses('fs'));
echo "\n--- testing autoload ---\n";
-var_dump(class_uses('non-existent'));
-var_dump(class_uses('non-existent2', false));
+var_dump(class_uses('non_existent'));
+var_dump(class_uses('non_existent2', false));
function __autoload($classname) {
@@ -35,11 +35,11 @@ array(0) {
}
--- testing autoload ---
-attempting to autoload non-existent
+attempting to autoload non_existent
-Warning: class_uses(): Class non-existent does not exist and could not be loaded in %s on line %d
+Warning: class_uses(): Class non_existent does not exist and could not be loaded in %s on line %d
bool(false)
-Warning: class_uses(): Class non-existent2 does not exist in %s on line %d
+Warning: class_uses(): Class non_existent2 does not exist in %s on line %d
bool(false)
===DONE===
diff --git a/ext/sqlite3/php_sqlite3.h b/ext/sqlite3/php_sqlite3.h
index b558f70340..2c19b9d9c4 100644
--- a/ext/sqlite3/php_sqlite3.h
+++ b/ext/sqlite3/php_sqlite3.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sqlite3/php_sqlite3_structs.h b/ext/sqlite3/php_sqlite3_structs.h
index 6c65e02ee7..5336d116fc 100644
--- a/ext/sqlite3/php_sqlite3_structs.h
+++ b/ext/sqlite3/php_sqlite3_structs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sqlite3/sqlite3.c b/ext/sqlite3/sqlite3.c
index 2aef0414aa..21e5634453 100644
--- a/ext/sqlite3/sqlite3.c
+++ b/ext/sqlite3/sqlite3.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/array.c b/ext/standard/array.c
index 360a691d38..1a29afa6dc 100644
--- a/ext/standard/array.c
+++ b/ext/standard/array.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/assert.c b/ext/standard/assert.c
index 631834c97c..cae4c6fd61 100644
--- a/ext/standard/assert.c
+++ b/ext/standard/assert.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/base64.c b/ext/standard/base64.c
index 7534c8f8a4..0df7826642 100644
--- a/ext/standard/base64.c
+++ b/ext/standard/base64.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/base64.h b/ext/standard/base64.h
index 3f9d818baa..2358c58951 100644
--- a/ext/standard/base64.h
+++ b/ext/standard/base64.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/basic_functions.c b/ext/standard/basic_functions.c
index b4128e066b..e22725bdb0 100644
--- a/ext/standard/basic_functions.c
+++ b/ext/standard/basic_functions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1214,7 +1214,7 @@ ZEND_END_ARG_INFO()
ZEND_BEGIN_ARG_INFO(arginfo_fstat, 0)
ZEND_ARG_INFO(0, fp)
ZEND_END_ARG_INFO()
-ZEND_BEGIN_ARG_INFO(arginfo_copy, 0)
+ZEND_BEGIN_ARG_INFO_EX(arginfo_copy, 0, 0, 2)
ZEND_ARG_INFO(0, source_file)
ZEND_ARG_INFO(0, destination_file)
ZEND_ARG_INFO(0, context)
@@ -5776,7 +5776,7 @@ PHP_FUNCTION(unregister_tick_function)
return;
}
- if (Z_TYPE_P(function) != IS_ARRAY) {
+ if (Z_TYPE_P(function) != IS_ARRAY && Z_TYPE_P(function) != IS_OBJECT) {
convert_to_string(function);
}
diff --git a/ext/standard/basic_functions.h b/ext/standard/basic_functions.h
index 7327f7d2d2..3af85b3d40 100644
--- a/ext/standard/basic_functions.h
+++ b/ext/standard/basic_functions.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/browscap.c b/ext/standard/browscap.c
index ed773b851c..a2ff691e8f 100644
--- a/ext/standard/browscap.c
+++ b/ext/standard/browscap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/crc32.c b/ext/standard/crc32.c
index e9c36d4cb4..3ce355a45f 100644
--- a/ext/standard/crc32.c
+++ b/ext/standard/crc32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/crc32.h b/ext/standard/crc32.h
index 2c8ded4587..be9a99e6e2 100644
--- a/ext/standard/crc32.h
+++ b/ext/standard/crc32.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/credits.c b/ext/standard/credits.c
index 530c8d0e63..006c2d4c1a 100644
--- a/ext/standard/credits.c
+++ b/ext/standard/credits.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/credits.h b/ext/standard/credits.h
index 7ad99d9f82..a1f57360a5 100644
--- a/ext/standard/credits.h
+++ b/ext/standard/credits.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/credits_ext.h b/ext/standard/credits_ext.h
index 2770d162fb..1d652857eb 100644
--- a/ext/standard/credits_ext.h
+++ b/ext/standard/credits_ext.h
@@ -17,8 +17,8 @@ CREDIT_LINE("COM and .Net", "Wez Furlong");
CREDIT_LINE("ctype", "Hartmut Holzgraefe");
CREDIT_LINE("cURL", "Sterling Hughes");
CREDIT_LINE("Date/Time Support", "Derick Rethans");
-CREDIT_LINE("DBA", "Sascha Schumann, Marcus Boerger");
CREDIT_LINE("DB-LIB (MS SQL, Sybase)", "Wez Furlong, Frank M. Kromann");
+CREDIT_LINE("DBA", "Sascha Schumann, Marcus Boerger");
CREDIT_LINE("DOM", "Christian Stocker, Rob Richards, Marcus Boerger");
CREDIT_LINE("enchant", "Pierre-Alain Joye, Ilia Alshanetsky");
CREDIT_LINE("ereg", "Rasmus Lerdorf, Jim Winstead, Jaakko Hyvätti");
@@ -41,9 +41,9 @@ CREDIT_LINE("mcrypt", "Sascha Schumann, Derick Rethans");
CREDIT_LINE("MS SQL", "Frank M. Kromann");
CREDIT_LINE("Multibyte String Functions", "Tsukada Takuya, Rui Hirokawa");
CREDIT_LINE("MySQL driver for PDO", "George Schlossnagle, Wez Furlong, Ilia Alshanetsky, Johannes Schlueter");
-CREDIT_LINE("MySQLi", "Zak Greant, Georg Richter, Andrey Hristov, Ulf Wendel");
-CREDIT_LINE("MySQLnd", "Andrey Hristov, Ulf Wendel, Georg Richter, Johannes Schlueter");
CREDIT_LINE("MySQL", "Zeev Suraski, Zak Greant, Georg Richter, Andrey Hristov");
+CREDIT_LINE("MySQLi", "Zak Greant, Georg Richter, Andrey Hristov, Ulf Wendel");
+CREDIT_LINE("MySQLnd", "Andrey Hristov, Ulf Wendel, Georg Richter, Johannes Schlüter");
CREDIT_LINE("OCI8", "Stig Bakken, Thies C. Arntzen, Andy Sautins, David Benson, Maxim Maletsky, Harald Radi, Antony Dovgal, Andi Gutmans, Wez Furlong, Christopher Jones, Oracle Corporation");
CREDIT_LINE("ODBC driver for PDO", "Wez Furlong");
CREDIT_LINE("ODBC", "Stig Bakken, Andreas Karajannis, Frank M. Kromann, Daniel R. Kalowsky");
@@ -68,8 +68,8 @@ CREDIT_LINE("SNMP", "Rasmus Lerdorf, Harrie Hazewinkel, Mike Jackson, Steven Law
CREDIT_LINE("SOAP", "Brad Lafountain, Shane Caraveo, Dmitry Stogov");
CREDIT_LINE("Sockets", "Chris Vandomelen, Sterling Hughes, Daniel Beulshausen, Jason Greene");
CREDIT_LINE("SPL", "Marcus Boerger, Etienne Kneuss");
-CREDIT_LINE("SQLite3", "Scott MacVicar, Ilia Alshanetsky, Brad Dewar");
CREDIT_LINE("SQLite 3.x driver for PDO", "Wez Furlong");
+CREDIT_LINE("SQLite3", "Scott MacVicar, Ilia Alshanetsky, Brad Dewar");
CREDIT_LINE("Sybase-CT", "Zeev Suraski, Tom May, Timm Friebe");
CREDIT_LINE("System V Message based IPC", "Wez Furlong");
CREDIT_LINE("System V Semaphores", "Tom May");
@@ -77,9 +77,9 @@ CREDIT_LINE("System V Shared Memory", "Christian Cartus");
CREDIT_LINE("tidy", "John Coggeshall, Ilia Alshanetsky");
CREDIT_LINE("tokenizer", "Andrei Zmievski, Johannes Schlueter");
CREDIT_LINE("WDDX", "Andrei Zmievski");
+CREDIT_LINE("XML", "Stig Bakken, Thies C. Arntzen, Sterling Hughes");
CREDIT_LINE("XMLReader", "Rob Richards");
CREDIT_LINE("xmlrpc", "Dan Libby");
-CREDIT_LINE("XML", "Stig Bakken, Thies C. Arntzen, Sterling Hughes");
CREDIT_LINE("XMLWriter", "Rob Richards, Pierre-Alain Joye");
CREDIT_LINE("XSL", "Christian Stocker, Rob Richards");
CREDIT_LINE("Zip", "Pierre-Alain Joye");
diff --git a/ext/standard/crypt.c b/ext/standard/crypt.c
index 113a5bd0f5..8750378b53 100644
--- a/ext/standard/crypt.c
+++ b/ext/standard/crypt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/css.c b/ext/standard/css.c
index d76f9ee662..5eaa6ada2f 100644
--- a/ext/standard/css.c
+++ b/ext/standard/css.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/css.h b/ext/standard/css.h
index d7275e08ef..9541a34d2c 100644
--- a/ext/standard/css.h
+++ b/ext/standard/css.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/cyr_convert.c b/ext/standard/cyr_convert.c
index b29b49374e..d8d40cb10f 100644
--- a/ext/standard/cyr_convert.c
+++ b/ext/standard/cyr_convert.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/cyr_convert.h b/ext/standard/cyr_convert.h
index afcb872541..6b16be2960 100644
--- a/ext/standard/cyr_convert.h
+++ b/ext/standard/cyr_convert.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/datetime.c b/ext/standard/datetime.c
index 394153264d..69e17240a7 100644
--- a/ext/standard/datetime.c
+++ b/ext/standard/datetime.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/datetime.h b/ext/standard/datetime.h
index 3612fafae3..bb6673497c 100644
--- a/ext/standard/datetime.h
+++ b/ext/standard/datetime.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/dir.c b/ext/standard/dir.c
index ef28e9feaf..c6d6ddd263 100644
--- a/ext/standard/dir.c
+++ b/ext/standard/dir.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/dl.c b/ext/standard/dl.c
index ceb975e93b..012592381b 100644
--- a/ext/standard/dl.c
+++ b/ext/standard/dl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/dl.h b/ext/standard/dl.h
index 030f50e933..eee70472b5 100644
--- a/ext/standard/dl.h
+++ b/ext/standard/dl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/dns.c b/ext/standard/dns.c
index 3584fc1bfe..6a894467ff 100644
--- a/ext/standard/dns.c
+++ b/ext/standard/dns.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/dns_win32.c b/ext/standard/dns_win32.c
index 2dbf3e2e1d..a784823dd3 100644
--- a/ext/standard/dns_win32.c
+++ b/ext/standard/dns_win32.c
@@ -334,7 +334,7 @@ static void php_parserr(PDNS_RECORD pRec, int type_to_fetch, int store, int raw,
#endif
default:
- /* unkown type */
+ /* unknown type */
zval_ptr_dtor(subarray);
*subarray = NULL;
return;
diff --git a/ext/standard/exec.c b/ext/standard/exec.c
index 7b783ca60f..f8a22adf39 100644
--- a/ext/standard/exec.c
+++ b/ext/standard/exec.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/exec.h b/ext/standard/exec.h
index 14c98c57e3..ddb6367570 100644
--- a/ext/standard/exec.h
+++ b/ext/standard/exec.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/file.c b/ext/standard/file.c
index ad6bdad34f..cae5428363 100644
--- a/ext/standard/file.c
+++ b/ext/standard/file.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/file.h b/ext/standard/file.h
index 2bcdfd64bf..d2b20bf928 100644
--- a/ext/standard/file.h
+++ b/ext/standard/file.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/filestat.c b/ext/standard/filestat.c
index 2713d23f1d..3a95a9f9a4 100644
--- a/ext/standard/filestat.c
+++ b/ext/standard/filestat.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/filters.c b/ext/standard/filters.c
index 15dae1bee6..39ca68f94a 100644
--- a/ext/standard/filters.c
+++ b/ext/standard/filters.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/flock_compat.c b/ext/standard/flock_compat.c
index 41f95eb724..05e0175311 100644
--- a/ext/standard/flock_compat.c
+++ b/ext/standard/flock_compat.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/flock_compat.h b/ext/standard/flock_compat.h
index 819d63c800..ab9c445561 100644
--- a/ext/standard/flock_compat.h
+++ b/ext/standard/flock_compat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/formatted_print.c b/ext/standard/formatted_print.c
index 0035d204f6..3cd5839313 100644
--- a/ext/standard/formatted_print.c
+++ b/ext/standard/formatted_print.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/fsock.c b/ext/standard/fsock.c
index b7d5335927..d5a554725a 100644
--- a/ext/standard/fsock.c
+++ b/ext/standard/fsock.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/fsock.h b/ext/standard/fsock.h
index 70d0a5b50a..8ecb889162 100644
--- a/ext/standard/fsock.h
+++ b/ext/standard/fsock.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/ftok.c b/ext/standard/ftok.c
index 3b0105994c..4833bddc01 100644
--- a/ext/standard/ftok.c
+++ b/ext/standard/ftok.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/ftp_fopen_wrapper.c b/ext/standard/ftp_fopen_wrapper.c
index 86975d7f5b..27390a10d1 100644
--- a/ext/standard/ftp_fopen_wrapper.c
+++ b/ext/standard/ftp_fopen_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/head.c b/ext/standard/head.c
index 5310ff6c03..eca032a97b 100644
--- a/ext/standard/head.c
+++ b/ext/standard/head.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/head.h b/ext/standard/head.h
index 7d657ba445..efca9b8637 100644
--- a/ext/standard/head.h
+++ b/ext/standard/head.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/html.c b/ext/standard/html.c
index b4d9ba109d..91fc050add 100644
--- a/ext/standard/html.c
+++ b/ext/standard/html.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/html.h b/ext/standard/html.h
index ae114765b2..b3da83f307 100644
--- a/ext/standard/html.h
+++ b/ext/standard/html.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/html_tables.h b/ext/standard/html_tables.h
index c24531d11c..05aea46df1 100644
--- a/ext/standard/html_tables.h
+++ b/ext/standard/html_tables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/html_tables/html_table_gen.php b/ext/standard/html_tables/html_table_gen.php
index 7e7314fa35..68dec133f5 100644
--- a/ext/standard/html_tables/html_table_gen.php
+++ b/ext/standard/html_tables/html_table_gen.php
@@ -80,8 +80,11 @@ static const struct {
{ "Shift_JIS", cs_sjis },
{ "SJIS", cs_sjis },
{ "932", cs_sjis },
+ { "SJIS-win", cs_sjis },
+ { "CP932", cs_sjis },
{ "EUCJP", cs_eucjp },
{ "EUC-JP", cs_eucjp },
+ { "eucJP-win", cs_eucjp },
{ "KOI8-R", cs_koi8r },
{ "koi8-ru", cs_koi8r },
{ "koi8r", cs_koi8r },
diff --git a/ext/standard/http.c b/ext/standard/http.c
index f9b8021950..2b1c1390bd 100644
--- a/ext/standard/http.c
+++ b/ext/standard/http.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/http_fopen_wrapper.c b/ext/standard/http_fopen_wrapper.c
index 4605e7494f..7e4fdb43cb 100644
--- a/ext/standard/http_fopen_wrapper.c
+++ b/ext/standard/http_fopen_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/image.c b/ext/standard/image.c
index bd80f11dec..27f60c95a7 100644
--- a/ext/standard/image.c
+++ b/ext/standard/image.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/incomplete_class.c b/ext/standard/incomplete_class.c
index f854fddf49..968a5e2ebd 100644
--- a/ext/standard/incomplete_class.c
+++ b/ext/standard/incomplete_class.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/info.c b/ext/standard/info.c
index 48e0e85cc5..a4996b6bfc 100644
--- a/ext/standard/info.c
+++ b/ext/standard/info.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/info.h b/ext/standard/info.h
index 46a0dfc240..631eb049f1 100644
--- a/ext/standard/info.h
+++ b/ext/standard/info.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/iptc.c b/ext/standard/iptc.c
index 729b0597e3..3257339106 100644
--- a/ext/standard/iptc.c
+++ b/ext/standard/iptc.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/lcg.c b/ext/standard/lcg.c
index 8bbe603516..311173a137 100644
--- a/ext/standard/lcg.c
+++ b/ext/standard/lcg.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/levenshtein.c b/ext/standard/levenshtein.c
index c492982101..786ca052d7 100644
--- a/ext/standard/levenshtein.c
+++ b/ext/standard/levenshtein.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/link.c b/ext/standard/link.c
index 8da63958a7..c57484e766 100644
--- a/ext/standard/link.c
+++ b/ext/standard/link.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/link_win32.c b/ext/standard/link_win32.c
index 674745e0a1..d410d223fb 100644
--- a/ext/standard/link_win32.c
+++ b/ext/standard/link_win32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/mail.c b/ext/standard/mail.c
index 9499981f27..b877b87420 100644
--- a/ext/standard/mail.c
+++ b/ext/standard/mail.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -286,7 +286,7 @@ PHPAPI int php_mail(char *to, char *subject, char *message, char *headers, char
if (headers != NULL) {
spprintf(&hdr, 0, "X-PHP-Originating-Script: %ld:%s\n%s", php_getuid(TSRMLS_C), f, headers);
} else {
- spprintf(&hdr, 0, "X-PHP-Originating-Script: %ld:%s\n", php_getuid(TSRMLS_C), f);
+ spprintf(&hdr, 0, "X-PHP-Originating-Script: %ld:%s", php_getuid(TSRMLS_C), f);
}
efree(f);
}
diff --git a/ext/standard/math.c b/ext/standard/math.c
index f6b3d5406e..2be049f200 100644
--- a/ext/standard/math.c
+++ b/ext/standard/math.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/md5.c b/ext/standard/md5.c
index 7fea069dbb..134b650212 100644
--- a/ext/standard/md5.c
+++ b/ext/standard/md5.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/md5.h b/ext/standard/md5.h
index d7834054e7..43f425e402 100644
--- a/ext/standard/md5.h
+++ b/ext/standard/md5.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/metaphone.c b/ext/standard/metaphone.c
index 62c6df64aa..07143dfa7d 100644
--- a/ext/standard/metaphone.c
+++ b/ext/standard/metaphone.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/microtime.c b/ext/standard/microtime.c
index 219e35df16..fe2236683a 100644
--- a/ext/standard/microtime.c
+++ b/ext/standard/microtime.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/microtime.h b/ext/standard/microtime.h
index 95d4fab294..2af8a677c5 100644
--- a/ext/standard/microtime.h
+++ b/ext/standard/microtime.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/pack.c b/ext/standard/pack.c
index 3f525a793a..16a30668dc 100644
--- a/ext/standard/pack.c
+++ b/ext/standard/pack.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/pack.h b/ext/standard/pack.h
index 22932887ce..601cc202c2 100644
--- a/ext/standard/pack.h
+++ b/ext/standard/pack.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/pageinfo.c b/ext/standard/pageinfo.c
index 6add7269cf..a9a4e58de0 100644
--- a/ext/standard/pageinfo.c
+++ b/ext/standard/pageinfo.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/pageinfo.h b/ext/standard/pageinfo.h
index 9ce76811bc..c3c1846058 100644
--- a/ext/standard/pageinfo.h
+++ b/ext/standard/pageinfo.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/password.c b/ext/standard/password.c
index ca852038a6..ae405096fa 100644
--- a/ext/standard/password.c
+++ b/ext/standard/password.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_array.h b/ext/standard/php_array.h
index 1cf2779071..e2af3310d0 100644
--- a/ext/standard/php_array.h
+++ b/ext/standard/php_array.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_assert.h b/ext/standard/php_assert.h
index 02bf27706c..04c85427c3 100644
--- a/ext/standard/php_assert.h
+++ b/ext/standard/php_assert.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_browscap.h b/ext/standard/php_browscap.h
index da48ccebeb..dbe1891af3 100644
--- a/ext/standard/php_browscap.h
+++ b/ext/standard/php_browscap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_crypt.h b/ext/standard/php_crypt.h
index 6025685539..f0b96010bc 100644
--- a/ext/standard/php_crypt.h
+++ b/ext/standard/php_crypt.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_crypt_r.c b/ext/standard/php_crypt_r.c
index 8497994625..3098f247ef 100644
--- a/ext/standard/php_crypt_r.c
+++ b/ext/standard/php_crypt_r.c
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_crypt_r.h b/ext/standard/php_crypt_r.h
index c7f36eaf21..8b78d95d3d 100644
--- a/ext/standard/php_crypt_r.h
+++ b/ext/standard/php_crypt_r.h
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_dir.h b/ext/standard/php_dir.h
index 432ee33ac3..2b9313aac4 100644
--- a/ext/standard/php_dir.h
+++ b/ext/standard/php_dir.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_dns.h b/ext/standard/php_dns.h
index 0ee8aaab43..5823f5f20f 100644
--- a/ext/standard/php_dns.h
+++ b/ext/standard/php_dns.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_ext_syslog.h b/ext/standard/php_ext_syslog.h
index 21d6cd4762..e3fc582cd2 100644
--- a/ext/standard/php_ext_syslog.h
+++ b/ext/standard/php_ext_syslog.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_filestat.h b/ext/standard/php_filestat.h
index e8e798c510..ef72e584f1 100644
--- a/ext/standard/php_filestat.h
+++ b/ext/standard/php_filestat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_fopen_wrapper.c b/ext/standard/php_fopen_wrapper.c
index f8d7bda482..4b4180230e 100644
--- a/ext/standard/php_fopen_wrapper.c
+++ b/ext/standard/php_fopen_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_fopen_wrappers.h b/ext/standard/php_fopen_wrappers.h
index 5f78256bcb..3964310c50 100644
--- a/ext/standard/php_fopen_wrappers.h
+++ b/ext/standard/php_fopen_wrappers.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_ftok.h b/ext/standard/php_ftok.h
index b339349e49..7e702c942f 100644
--- a/ext/standard/php_ftok.h
+++ b/ext/standard/php_ftok.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_http.h b/ext/standard/php_http.h
index 468fd0508c..54321b39a2 100644
--- a/ext/standard/php_http.h
+++ b/ext/standard/php_http.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_image.h b/ext/standard/php_image.h
index a56e2a0f26..c8bb4ccc7a 100644
--- a/ext/standard/php_image.h
+++ b/ext/standard/php_image.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_incomplete_class.h b/ext/standard/php_incomplete_class.h
index f998996d62..b5a2a322f7 100644
--- a/ext/standard/php_incomplete_class.h
+++ b/ext/standard/php_incomplete_class.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_iptc.h b/ext/standard/php_iptc.h
index 6b8c50efb2..a076aea343 100644
--- a/ext/standard/php_iptc.h
+++ b/ext/standard/php_iptc.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_lcg.h b/ext/standard/php_lcg.h
index 3bdab4aab3..82141e6af2 100644
--- a/ext/standard/php_lcg.h
+++ b/ext/standard/php_lcg.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_link.h b/ext/standard/php_link.h
index ddc00429cf..1ca4acee25 100644
--- a/ext/standard/php_link.h
+++ b/ext/standard/php_link.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_mail.h b/ext/standard/php_mail.h
index 092dded660..925f58ebd5 100644
--- a/ext/standard/php_mail.h
+++ b/ext/standard/php_mail.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_math.h b/ext/standard/php_math.h
index 116acd9df5..8dec21acf3 100644
--- a/ext/standard/php_math.h
+++ b/ext/standard/php_math.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_metaphone.h b/ext/standard/php_metaphone.h
index 6af07bbbb0..14da9d8191 100644
--- a/ext/standard/php_metaphone.h
+++ b/ext/standard/php_metaphone.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_password.h b/ext/standard/php_password.h
index abc343d66e..a38af97626 100644
--- a/ext/standard/php_password.h
+++ b/ext/standard/php_password.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_rand.h b/ext/standard/php_rand.h
index e831f32b23..2928d98c5e 100644
--- a/ext/standard/php_rand.h
+++ b/ext/standard/php_rand.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_smart_str.h b/ext/standard/php_smart_str.h
index 2fef1d0bd0..d59258f091 100644
--- a/ext/standard/php_smart_str.h
+++ b/ext/standard/php_smart_str.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_smart_str_public.h b/ext/standard/php_smart_str_public.h
index ed36a7a6fe..b445dd7767 100644
--- a/ext/standard/php_smart_str_public.h
+++ b/ext/standard/php_smart_str_public.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_standard.h b/ext/standard/php_standard.h
index 3c7535da1f..d7476cb397 100644
--- a/ext/standard/php_standard.h
+++ b/ext/standard/php_standard.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_string.h b/ext/standard/php_string.h
index 65219f257a..2396d40461 100644
--- a/ext/standard/php_string.h
+++ b/ext/standard/php_string.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -156,7 +156,7 @@ PHPAPI char *php_strerror(int errnum);
# define php_mblen(ptr, len) 1
#else
# if defined(_REENTRANT) && defined(HAVE_MBRLEN) && defined(HAVE_MBSTATE_T)
-# define php_mblen(ptr, len) ((ptr) == NULL ? mbsinit(&BG(mblen_state)): (int)mbrlen(ptr, len, &BG(mblen_state)))
+# define php_mblen(ptr, len) ((ptr) == NULL ? memset(&BG(mblen_state), 0, sizeof(BG(mblen_state))): (int)mbrlen(ptr, len, &BG(mblen_state)))
# else
# define php_mblen(ptr, len) mblen(ptr, len)
# endif
diff --git a/ext/standard/php_type.h b/ext/standard/php_type.h
index e434ae05f4..8b71f87e5e 100644
--- a/ext/standard/php_type.h
+++ b/ext/standard/php_type.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_uuencode.h b/ext/standard/php_uuencode.h
index 28bcb09c3e..5b2b852606 100644
--- a/ext/standard/php_uuencode.h
+++ b/ext/standard/php_uuencode.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_var.h b/ext/standard/php_var.h
index afc5f178e4..48692e57c3 100644
--- a/ext/standard/php_var.h
+++ b/ext/standard/php_var.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/php_versioning.h b/ext/standard/php_versioning.h
index fcbedacc38..b3ea4f8f4d 100644
--- a/ext/standard/php_versioning.h
+++ b/ext/standard/php_versioning.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/proc_open.c b/ext/standard/proc_open.c
index d78ca9976b..f4c3b4738c 100644
--- a/ext/standard/proc_open.c
+++ b/ext/standard/proc_open.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -112,8 +112,17 @@ static php_process_env_t _php_array_to_envp(zval *environment, int is_persistent
zend_hash_get_current_data_ex(target_hash, (void **) &element, &pos) == SUCCESS;
zend_hash_move_forward_ex(target_hash, &pos)) {
- convert_to_string_ex(element);
- el_len = Z_STRLEN_PP(element);
+ if (Z_TYPE_PP(element) != IS_STRING) {
+ zval tmp;
+
+ MAKE_COPY_ZVAL(element, &tmp);
+ convert_to_string(&tmp);
+ el_len = Z_STRLEN(tmp);
+
+ zval_dtor(&tmp);
+ } else {
+ el_len = Z_STRLEN_PP(element);
+ }
if (el_len == 0) {
continue;
}
@@ -125,7 +134,7 @@ static php_process_env_t _php_array_to_envp(zval *environment, int is_persistent
if (string_length == 0) {
continue;
}
- sizeenv += string_length+1;
+ sizeenv += string_length;
break;
}
}
@@ -138,19 +147,26 @@ static php_process_env_t _php_array_to_envp(zval *environment, int is_persistent
for (zend_hash_internal_pointer_reset_ex(target_hash, &pos);
zend_hash_get_current_data_ex(target_hash, (void **) &element, &pos) == SUCCESS;
zend_hash_move_forward_ex(target_hash, &pos)) {
+ zval tmp;
- convert_to_string_ex(element);
- el_len = Z_STRLEN_PP(element);
+ if (Z_TYPE_PP(element) != IS_STRING) {
+ MAKE_COPY_ZVAL(element, &tmp);
+ convert_to_string(&tmp);
+ } else {
+ tmp = **element;
+ }
+
+ el_len = Z_STRLEN(tmp);
if (el_len == 0) {
- continue;
+ goto next_element;
}
- data = Z_STRVAL_PP(element);
+ data = Z_STRVAL(tmp);
switch (zend_hash_get_current_key_ex(target_hash, &string_key, &string_length, &num_key, 0, &pos)) {
case HASH_KEY_IS_STRING:
if (string_length == 0) {
- continue;
+ goto next_element;
}
l = string_length + el_len + 1;
@@ -175,6 +191,11 @@ static php_process_env_t _php_array_to_envp(zval *environment, int is_persistent
case HASH_KEY_NON_EXISTENT:
break;
}
+
+next_element:
+ if (Z_TYPE_PP(element) != IS_STRING) {
+ zval_dtor(&tmp);
+ }
}
assert((uint)(p - env.envp) <= sizeenv);
diff --git a/ext/standard/proc_open.h b/ext/standard/proc_open.h
index da1519b127..6708fded59 100644
--- a/ext/standard/proc_open.h
+++ b/ext/standard/proc_open.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/quot_print.c b/ext/standard/quot_print.c
index 0df127362f..7f54ce4d21 100644
--- a/ext/standard/quot_print.c
+++ b/ext/standard/quot_print.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/quot_print.h b/ext/standard/quot_print.h
index f621caf4b4..8be7faa388 100644
--- a/ext/standard/quot_print.h
+++ b/ext/standard/quot_print.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/rand.c b/ext/standard/rand.c
index 5f55a41f91..b0af30aa9d 100644
--- a/ext/standard/rand.c
+++ b/ext/standard/rand.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/scanf.c b/ext/standard/scanf.c
index 02e2c7173d..d092bbcfcf 100644
--- a/ext/standard/scanf.c
+++ b/ext/standard/scanf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/scanf.h b/ext/standard/scanf.h
index dbffca9bac..9d4acd4a8f 100644
--- a/ext/standard/scanf.h
+++ b/ext/standard/scanf.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/sha1.c b/ext/standard/sha1.c
index 4326db98a6..67e5d520f4 100644
--- a/ext/standard/sha1.c
+++ b/ext/standard/sha1.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/sha1.h b/ext/standard/sha1.h
index 450d457c6e..ea63a234cf 100644
--- a/ext/standard/sha1.h
+++ b/ext/standard/sha1.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/soundex.c b/ext/standard/soundex.c
index bb6818ecaa..cf915d4c1d 100644
--- a/ext/standard/soundex.c
+++ b/ext/standard/soundex.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/streamsfuncs.c b/ext/standard/streamsfuncs.c
index 0610ecfc49..b623447651 100644
--- a/ext/standard/streamsfuncs.c
+++ b/ext/standard/streamsfuncs.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/streamsfuncs.h b/ext/standard/streamsfuncs.h
index b662de5e4f..926cf2d5b5 100644
--- a/ext/standard/streamsfuncs.h
+++ b/ext/standard/streamsfuncs.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/string.c b/ext/standard/string.c
index b9d7427eb9..10d5ed976d 100644
--- a/ext/standard/string.c
+++ b/ext/standard/string.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1442,6 +1442,19 @@ PHPAPI void php_basename(const char *s, size_t len, char *suffix, size_t sufflen
state = 0;
cend = c;
}
+#if defined(PHP_WIN32) || defined(NETWARE)
+ /* Catch relative paths in c:file.txt style. They're not to confuse
+ with the NTFS streams. This part ensures also, that no drive
+ letter traversing happens. */
+ } else if ((*c == ':' && (c - comp == 1))) {
+ if (state == 0) {
+ comp = c;
+ state = 1;
+ } else {
+ cend = c;
+ state = 0;
+ }
+#endif
} else {
if (state == 0) {
comp = c;
@@ -5577,14 +5590,13 @@ PHP_FUNCTION(substr_compare)
int s1_len, s2_len;
long offset, len=0;
zend_bool cs=0;
- uint cmp_len;
if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "ssl|lb", &s1, &s1_len, &s2, &s2_len, &offset, &len, &cs) == FAILURE) {
RETURN_FALSE;
}
- if (ZEND_NUM_ARGS() >= 4 && len <= 0) {
- php_error_docref(NULL TSRMLS_CC, E_WARNING, "The length must be greater than zero");
+ if (ZEND_NUM_ARGS() >= 4 && len < 0) {
+ php_error_docref(NULL TSRMLS_CC, E_WARNING, "The length must be greater than or equal to zero");
RETURN_FALSE;
}
@@ -5598,12 +5610,10 @@ PHP_FUNCTION(substr_compare)
RETURN_FALSE;
}
- cmp_len = (uint) (len ? len : MAX(s2_len, (s1_len - offset)));
-
if (!cs) {
- RETURN_LONG(zend_binary_strncmp(s1 + offset, (s1_len - offset), s2, s2_len, cmp_len));
+ RETURN_LONG(zend_binary_strncmp(s1 + offset, (s1_len - offset), s2, s2_len, (uint)len));
} else {
- RETURN_LONG(zend_binary_strncasecmp_l(s1 + offset, (s1_len - offset), s2, s2_len, cmp_len));
+ RETURN_LONG(zend_binary_strncasecmp_l(s1 + offset, (s1_len - offset), s2, s2_len, (uint)len));
}
}
/* }}} */
diff --git a/ext/standard/syslog.c b/ext/standard/syslog.c
index ff98ab8572..acbffe49ad 100644
--- a/ext/standard/syslog.c
+++ b/ext/standard/syslog.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/tests/array/each.phpt b/ext/standard/tests/array/each.phpt
index 19ee728fd2..974808c08c 100644
--- a/ext/standard/tests/array/each.phpt
+++ b/ext/standard/tests/array/each.phpt
Binary files differ
diff --git a/ext/standard/tests/class_object/class_exists_variation_001.phpt b/ext/standard/tests/class_object/class_exists_variation_001.phpt
index 52a3584763..5f51b4bd93 100644
--- a/ext/standard/tests/class_object/class_exists_variation_001.phpt
+++ b/ext/standard/tests/class_object/class_exists_variation_001.phpt
@@ -100,15 +100,12 @@ In __autoload(12345)
bool(false)
Arg value -2345
-In __autoload(-2345)
bool(false)
Arg value 10.5
-In __autoload(10.5)
bool(false)
Arg value -10.5
-In __autoload(-10.5)
bool(false)
Arg value 101234567000
@@ -116,11 +113,9 @@ In __autoload(101234567000)
bool(false)
Arg value 1.07654321E-9
-In __autoload(1.07654321E-9)
bool(false)
Arg value 0.5
-In __autoload(0.5)
bool(false)
Error: 8 - Array to string conversion, %sclass_exists_variation_001.php(%d)
diff --git a/ext/standard/tests/class_object/trait_exists_variation_001.phpt b/ext/standard/tests/class_object/trait_exists_variation_001.phpt
index e7fa4afd1e..81df711cfa 100644
--- a/ext/standard/tests/class_object/trait_exists_variation_001.phpt
+++ b/ext/standard/tests/class_object/trait_exists_variation_001.phpt
@@ -100,15 +100,12 @@ In __autoload(12345)
bool(false)
Arg value -2345
-In __autoload(-2345)
bool(false)
Arg value 10.5
-In __autoload(10.5)
bool(false)
Arg value -10.5
-In __autoload(-10.5)
bool(false)
Arg value 101234567000
@@ -116,11 +113,9 @@ In __autoload(101234567000)
bool(false)
Arg value 1.07654321E-9
-In __autoload(1.07654321E-9)
bool(false)
Arg value 0.5
-In __autoload(0.5)
bool(false)
Error: 8 - Array to string conversion, %strait_exists_variation_001.php(%d)
diff --git a/ext/standard/tests/file/007_error.phpt b/ext/standard/tests/file/007_error.phpt
index a369c9d977..112beb3059 100644
--- a/ext/standard/tests/file/007_error.phpt
+++ b/ext/standard/tests/file/007_error.phpt
@@ -76,7 +76,7 @@ bool(false)
Warning: fopen() expects at least 2 parameters, 0 given in %s on line %d
bool(false)
-Warning: fclose(): 5 is not a valid stream resource in %s on line %d
+Warning: fclose(): %d is not a valid stream resource in %s on line %d
bool(false)
Warning: fclose() expects parameter 1 to be resource, string given in %s on line %d
@@ -85,7 +85,7 @@ bool(false)
Warning: fclose() expects exactly 1 parameter, 0 given in %s on line %d
bool(false)
-Warning: feof(): 5 is not a valid stream resource in %s on line %d
+Warning: feof(): %d is not a valid stream resource in %s on line %d
bool(false)
Warning: feof() expects parameter 1 to be resource, string given in %s on line %d
diff --git a/ext/standard/tests/file/basename_bug66395-win32.phpt b/ext/standard/tests/file/basename_bug66395-win32.phpt
new file mode 100644
index 0000000000..a9580dc09e
--- /dev/null
+++ b/ext/standard/tests/file/basename_bug66395-win32.phpt
@@ -0,0 +1,18 @@
+--TEST--
+basename bug #66395
+--SKIPIF--
+<?php if (substr(PHP_OS, 0, 3) != 'WIN') { die('skip Windows only basename tests'); } ?>
+--FILE--
+<?php
+echo basename("c:file.txt") . "\n";
+echo basename("d:subdir\\file.txt") . "\n";
+echo basename("y:file.txt", ".txt") . "\n";
+echo basename("notdriveletter:file.txt") . "\n";
+?>
+==DONE==
+--EXPECTF--
+file.txt
+file.txt
+file
+notdriveletter:file.txt
+==DONE==
diff --git a/ext/standard/tests/file/basename_bug66395_variation2-win32.phpt b/ext/standard/tests/file/basename_bug66395_variation2-win32.phpt
new file mode 100644
index 0000000000..0ebe996cd5
--- /dev/null
+++ b/ext/standard/tests/file/basename_bug66395_variation2-win32.phpt
@@ -0,0 +1,38 @@
+--TEST--
+basename bug #66395 check drive traversing and NTFS streams
+--SKIPIF--
+<?php if (substr(PHP_OS, 0, 3) != 'WIN') { die('skip Windows only basename tests'); } ?>
+--FILE--
+<?php
+echo basename("y:") . "\n";
+echo basename("y:/") . "\n";
+echo basename("notdriveletter:file.txt") . "\n";
+echo basename("a:\\b:c:d:hello.txt\\hcd:c.txt") . "\n";
+echo basename("a:b:c:d:hello.txt\\d:some.txt") . "\n";
+echo basename("a:b:c:d:hello\world\a.bmp\c:d:e:f.txt") . "\n";
+echo basename("a:\\b:\\c:d:hello\\world\\a.bmp\\d:e:f:g.txt") . "\n";
+echo basename("a:\\b:\\c:d:hello/world\\a.bmp\\d:\\e:\\f:g.txt") . "\n";
+echo basename("a:\\b:/c:d:hello\\world:somestream") . "\n";
+echo basename("a:\\b:\\c:d:hello\\world:some.stream") . "\n";
+echo basename("a:/b:\\c:d:hello\\world:some.stream:\$DATA") . "\n";
+echo basename("x:y:z:hello\world:my.stream:\$DATA") . "\n";
+echo basename("a:\\b:\\c:d:hello\\world:c:\$DATA") . "\n";
+echo basename("a:\\b:\\c:d:hello\\d:world:c:\$DATA") . "\n";
+?>
+==DONE==
+--EXPECTF--
+y
+y
+notdriveletter:file.txt
+hcd:c.txt
+some.txt
+f.txt
+g.txt
+g.txt
+world:somestream
+world:some.stream
+world:some.stream:$DATA
+world:my.stream:$DATA
+world:c:$DATA
+world:c:$DATA
+==DONE==
diff --git a/ext/standard/tests/file/bug66509.phpt b/ext/standard/tests/file/bug66509.phpt
new file mode 100644
index 0000000000..0e414f2321
--- /dev/null
+++ b/ext/standard/tests/file/bug66509.phpt
@@ -0,0 +1,15 @@
+--TEST--
+Bug #66509 (copy() showing $context parameter as required)
+--FILE--
+<?php
+
+$r = new \ReflectionFunction('copy');
+
+foreach($r->getParameters() as $p) {
+ var_dump($p->isOptional());
+}
+?>
+--EXPECT--
+bool(false)
+bool(false)
+bool(true)
diff --git a/ext/standard/tests/file/fgets_socket_variation1.phpt b/ext/standard/tests/file/fgets_socket_variation1.phpt
index 57944d8b56..429ad67d69 100644
--- a/ext/standard/tests/file/fgets_socket_variation1.phpt
+++ b/ext/standard/tests/file/fgets_socket_variation1.phpt
@@ -5,11 +5,17 @@ Dave Kelsey <d_kelsey@uk.ibm.com>
--FILE--
<?php
-/* Setup socket server */
-$server = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
/* Connect to it */
-$client = fsockopen('tcp://127.0.0.1:31337');
+$client = fsockopen("tcp://127.0.0.1:$port");
if (!$client) {
die("Unable to create socket");
diff --git a/ext/standard/tests/file/fgets_socket_variation2.phpt b/ext/standard/tests/file/fgets_socket_variation2.phpt
index 3500837133..da1f0b47ad 100644
--- a/ext/standard/tests/file/fgets_socket_variation2.phpt
+++ b/ext/standard/tests/file/fgets_socket_variation2.phpt
@@ -16,11 +16,17 @@ for ($i = 0; $i < 1000; $i++) {
}
fclose($fd);
-/* Setup socket server */
-$server = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
/* Connect to it */
-$client = fsockopen('tcp://127.0.0.1:31337');
+$client = fsockopen("tcp://127.0.0.1:$port");
if (!$client) {
die("Unable to create socket");
diff --git a/ext/standard/tests/file/fgetss_error.phpt b/ext/standard/tests/file/fgetss_error.phpt
index 3691e962e1..2b4ad68125 100644
--- a/ext/standard/tests/file/fgetss_error.phpt
+++ b/ext/standard/tests/file/fgetss_error.phpt
@@ -98,7 +98,7 @@ bool(false)
Warning: fgetss() expects parameter 1 to be resource, object given in %s on line %d
bool(false)
-- Testing fgetss() with closed/unset file handle --
-Warning: fgetss(): 5 is not a valid stream resource in %s on line %d
+Warning: fgetss(): %d is not a valid stream resource in %s on line %d
bool(false)
Warning: fgetss() expects parameter 1 to be resource, null given in %s on line %d
diff --git a/ext/standard/tests/file/file_put_contents_variation9.phpt b/ext/standard/tests/file/file_put_contents_variation9.phpt
index 7ad09c449d..79a42fe9b1 100644
--- a/ext/standard/tests/file/file_put_contents_variation9.phpt
+++ b/ext/standard/tests/file/file_put_contents_variation9.phpt
@@ -17,10 +17,10 @@ if(substr(PHP_OS, 0, 3) == "WIN")
echo "*** Testing file_put_contents() : usage variation ***\n";
-$filename = dirname(__FILE__).'/fileGetContentsVar9.tmp';
-$softlink = dirname(__FILE__).'/fileGetContentsVar9.SoftLink';
-$hardlink = dirname(__FILE__).'/fileGetContentsVar9.HardLink';
-$chainlink = dirname(__FILE__).'/fileGetContentsVar9.ChainLink';
+$filename = dirname(__FILE__).'/filePutContentsVar9.tmp';
+$softlink = dirname(__FILE__).'/filePutContentsVar9.SoftLink';
+$hardlink = dirname(__FILE__).'/filePutContentsVar9.HardLink';
+$chainlink = dirname(__FILE__).'/filePutContentsVar9.ChainLink';
// link files even though it original file doesn't exist yet
diff --git a/ext/standard/tests/file/fread_socket_variation1.phpt b/ext/standard/tests/file/fread_socket_variation1.phpt
index a615d2f414..d65565d3cc 100644
--- a/ext/standard/tests/file/fread_socket_variation1.phpt
+++ b/ext/standard/tests/file/fread_socket_variation1.phpt
@@ -3,13 +3,20 @@ Testing fread() on a TCP server socket
--FILE--
<?php
-$tcp_socket = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
-socket_set_timeout($tcp_socket, 0, 1000);
+socket_set_timeout($server, 0, 1000);
-var_dump(fread($tcp_socket, 1));
+var_dump(fread($server, 1));
-fclose($tcp_socket);
+fclose($server);
?>
--EXPECT--
diff --git a/ext/standard/tests/file/ftruncate_error.phpt b/ext/standard/tests/file/ftruncate_error.phpt
index a28095bc2d..254ad7688d 100644
--- a/ext/standard/tests/file/ftruncate_error.phpt
+++ b/ext/standard/tests/file/ftruncate_error.phpt
@@ -114,7 +114,7 @@ Warning: ftruncate() expects parameter 1 to be resource, object given in %s on l
bool(false)
-- Testing ftruncate() with closed/unset file handle --
-Warning: ftruncate(): 5 is not a valid stream resource in %s on line %d
+Warning: ftruncate(): %d is not a valid stream resource in %s on line %d
bool(false)
int(36)
diff --git a/ext/standard/tests/general_functions/bug41445_1.phpt b/ext/standard/tests/general_functions/bug41445_1.phpt
index e65e7afcc8..4698de436a 100644
--- a/ext/standard/tests/general_functions/bug41445_1.phpt
+++ b/ext/standard/tests/general_functions/bug41445_1.phpt
@@ -3,7 +3,7 @@ Bug #41445 (parse_ini_file() function parses octal numbers in section names) - 2
--FILE--
<?php
-$file = dirname(__FILE__)."/bug41445.ini";
+$file = dirname(__FILE__)."/bug41445_1.ini";
$data = <<<DATA
[2454.33]
diff --git a/ext/standard/tests/general_functions/bug66094.phpt b/ext/standard/tests/general_functions/bug66094.phpt
new file mode 100644
index 0000000000..8b33a4f4c3
--- /dev/null
+++ b/ext/standard/tests/general_functions/bug66094.phpt
@@ -0,0 +1,12 @@
+--TEST--
+Bug #66094 (unregister_tick_function tries to cast a Closure to a string)
+--FILE--
+<?php
+declare(ticks=1);
+register_tick_function($closure = function () { echo "Tick!\n"; });
+unregister_tick_function($closure);
+echo "done";
+?>
+--EXPECTF--
+Tick!
+done
diff --git a/ext/standard/tests/general_functions/floatval.phpt b/ext/standard/tests/general_functions/floatval.phpt
index b427bda7d5..9b7a3281e4 100644
--- a/ext/standard/tests/general_functions/floatval.phpt
+++ b/ext/standard/tests/general_functions/floatval.phpt
@@ -157,8 +157,8 @@ float(-5000000)
*** Testing floatval() on non floating types ***
float(-2147483648)
float(2147483648)
-float(5)
-float(6)
+float(%d)
+float(%d)
float(0)
float(1)
float(-1300)
@@ -175,8 +175,8 @@ float(0)
*** Testing doubleval() on non floating types ***
float(-2147483648)
float(2147483648)
-float(5)
-float(6)
+float(%d)
+float(%d)
float(0)
float(1)
float(-1300)
diff --git a/ext/standard/tests/general_functions/gettype_settype_basic.phpt b/ext/standard/tests/general_functions/gettype_settype_basic.phpt
index d6fb0d495b..d1fd4095be 100644
--- a/ext/standard/tests/general_functions/gettype_settype_basic.phpt
+++ b/ext/standard/tests/general_functions/gettype_settype_basic.phpt
@@ -232,11 +232,11 @@ int(0)
string(7) "integer"
-- Iteration 12 --
bool(true)
-int(5)
+int(%d)
string(7) "integer"
-- Iteration 13 --
bool(true)
-int(6)
+int(%d)
string(7) "integer"
-- Iteration 14 --
8: Object of class point could not be converted to int
@@ -291,11 +291,11 @@ int(0)
string(7) "integer"
-- Iteration 12 --
bool(true)
-int(5)
+int(%d)
string(7) "integer"
-- Iteration 13 --
bool(true)
-int(6)
+int(%d)
string(7) "integer"
-- Iteration 14 --
8: Object of class point could not be converted to int
@@ -350,11 +350,11 @@ float(0)
string(6) "double"
-- Iteration 12 --
bool(true)
-float(5)
+float(%d)
string(6) "double"
-- Iteration 13 --
bool(true)
-float(6)
+float(%d)
string(6) "double"
-- Iteration 14 --
8: Object of class point could not be converted to double
@@ -409,11 +409,11 @@ float(0)
string(6) "double"
-- Iteration 12 --
bool(true)
-float(5)
+float(%d)
string(6) "double"
-- Iteration 13 --
bool(true)
-float(6)
+float(%d)
string(6) "double"
-- Iteration 14 --
8: Object of class point could not be converted to double
@@ -610,12 +610,12 @@ string(6) "string"
-- Iteration 12 --
2: settype(): Cannot convert to resource type
bool(false)
-resource(5) of type (stream)
+resource(%d) of type (stream)
string(8) "resource"
-- Iteration 13 --
2: settype(): Cannot convert to resource type
bool(false)
-resource(6) of type (stream)
+resource(%d) of type (stream)
string(8) "resource"
-- Iteration 14 --
2: settype(): Cannot convert to resource type
@@ -716,14 +716,14 @@ string(5) "array"
bool(true)
array(1) {
[0]=>
- resource(5) of type (stream)
+ resource(%d) of type (stream)
}
string(5) "array"
-- Iteration 13 --
bool(true)
array(1) {
[0]=>
- resource(6) of type (stream)
+ resource(%d) of type (stream)
}
string(5) "array"
-- Iteration 14 --
@@ -824,14 +824,14 @@ string(6) "object"
bool(true)
object(stdClass)#2 (1) {
["scalar"]=>
- resource(5) of type (stream)
+ resource(%d) of type (stream)
}
string(6) "object"
-- Iteration 13 --
bool(true)
object(stdClass)#2 (1) {
["scalar"]=>
- resource(6) of type (stream)
+ resource(%d) of type (stream)
}
string(6) "object"
-- Iteration 14 --
@@ -893,11 +893,11 @@ string(6) "string"
string(6) "string"
-- Iteration 12 --
bool(true)
-string(14) "Resource id #5"
+string(14) "Resource id #%d"
string(6) "string"
-- Iteration 13 --
bool(true)
-string(14) "Resource id #6"
+string(14) "Resource id #%d"
string(6) "string"
-- Iteration 14 --
bool(true)
diff --git a/ext/standard/tests/general_functions/print_r.phpt b/ext/standard/tests/general_functions/print_r.phpt
index 81a523ad0b..19e71fbfd7 100644
--- a/ext/standard/tests/general_functions/print_r.phpt
+++ b/ext/standard/tests/general_functions/print_r.phpt
@@ -1484,13 +1484,13 @@ object_class Object
*** Testing print_r() on resources ***
-- Iteration 1 --
-Resource id #5
-Resource id #5
-Resource id #5
+Resource id #%d
+Resource id #%d
+Resource id #%d
-- Iteration 2 --
-Resource id #6
-Resource id #6
-Resource id #6
+Resource id #%d
+Resource id #%d
+Resource id #%d
*** Testing print_r() on different combinations of scalar
and non-scalar variables ***
diff --git a/ext/standard/tests/general_functions/strval.phpt b/ext/standard/tests/general_functions/strval.phpt
index b92be41ef4..372ac6701e 100644
--- a/ext/standard/tests/general_functions/strval.phpt
+++ b/ext/standard/tests/general_functions/strval.phpt
@@ -279,9 +279,9 @@ string(0) ""
-- Iteration 1 --
string(6) "Object"
-- Iteration 2 --
-string(14) "Resource id #5"
+string(14) "Resource id #%d"
-- Iteration 3 --
-string(14) "Resource id #6"
+string(14) "Resource id #%d"
-- Iteration 4 --
Notice: Array to string conversion in %sstrval.php on line %d
diff --git a/ext/standard/tests/general_functions/type.phpt b/ext/standard/tests/general_functions/type.phpt
index 98eccbbda7..51654b1859 100644
--- a/ext/standard/tests/general_functions/type.phpt
+++ b/ext/standard/tests/general_functions/type.phpt
@@ -105,9 +105,9 @@ int(0)
bool(true)
int(0)
bool(true)
-int(5)
+int(%d)
bool(true)
-int(6)
+int(%d)
string(54) "Object of class stdClass could not be converted to int"
bool(true)
int(%d)
@@ -128,9 +128,9 @@ float(0)
bool(true)
float(0)
bool(true)
-float(5)
+float(%d)
bool(true)
-float(6)
+float(%d)
string(57) "Object of class stdClass could not be converted to double"
bool(true)
float(%d)
diff --git a/ext/standard/tests/general_functions/var_dump.phpt b/ext/standard/tests/general_functions/var_dump.phpt
index 09e9f3b99e..c47227141b 100644
--- a/ext/standard/tests/general_functions/var_dump.phpt
+++ b/ext/standard/tests/general_functions/var_dump.phpt
@@ -844,9 +844,9 @@ object(object_class)#13 (8) {
*** Testing var_dump() on resources ***
-- Iteration 1 --
-resource(5) of type (stream)
+resource(%d) of type (stream)
-- Iteration 2 --
-resource(6) of type (stream)
+resource(%d) of type (stream)
*** Testing var_dump() on different combinations of scalar
and non-scalar variables ***
@@ -1227,9 +1227,9 @@ array(4) {
}
array(2) {
[0]=>
- resource(5) of type (stream)
+ resource(%d) of type (stream)
[1]=>
- resource(6) of type (stream)
+ resource(%d) of type (stream)
}
array(9) {
[0]=>
diff --git a/ext/standard/tests/general_functions/var_export-locale.phpt b/ext/standard/tests/general_functions/var_export-locale.phpt
index 3cbebe9c72..b6f87c431c 100644
--- a/ext/standard/tests/general_functions/var_export-locale.phpt
+++ b/ext/standard/tests/general_functions/var_export-locale.phpt
@@ -1,7 +1,7 @@
--TEST--
Test var_export() function with locale
--INI--
-precision=14
+serialize_precision=17
--SKIPIF--
<?php
if (!setlocale(LC_ALL, "german", "de","de_DE","de_DE.ISO8859-1","de_DE.ISO_8859-1","de_DE.UTF-8")) {
diff --git a/ext/standard/tests/general_functions/var_export_basic3.phpt b/ext/standard/tests/general_functions/var_export_basic3.phpt
index 9e27d90425..58c0448167 100644
--- a/ext/standard/tests/general_functions/var_export_basic3.phpt
+++ b/ext/standard/tests/general_functions/var_export_basic3.phpt
@@ -1,7 +1,7 @@
--TEST--
Test var_export() function with valid float values
--INI--
-precision=14
+serialize_precision=17
--FILE--
<?php
/* Prototype : mixed var_export(mixed var [, bool return])
diff --git a/ext/standard/tests/general_functions/var_export_basic5.phpt b/ext/standard/tests/general_functions/var_export_basic5.phpt
index 1512fa8377..dacb355323 100644
--- a/ext/standard/tests/general_functions/var_export_basic5.phpt
+++ b/ext/standard/tests/general_functions/var_export_basic5.phpt
@@ -1,5 +1,7 @@
--TEST--
Test var_export() function with valid arrays
+--INI--
+serialize_precision=17
--FILE--
<?php
/* Prototype : mixed var_export(mixed var [, bool return])
diff --git a/ext/standard/tests/mail/bug51604.phpt b/ext/standard/tests/mail/bug51604.phpt
index a657021025..988849c4e1 100644
--- a/ext/standard/tests/mail/bug51604.phpt
+++ b/ext/standard/tests/mail/bug51604.phpt
@@ -11,7 +11,7 @@ if(substr(PHP_OS, 0, 3) == "WIN")
--FILE--
<?php
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
$additional_headers = "KHeaders\n\n\n\n\n";
@@ -27,7 +27,7 @@ unlink($outFile);
===DONE===
--EXPECT--
bool(true)
-To: user@company.com
+To: user@example.com
Subject: Test Subject
KHeaders
diff --git a/ext/standard/tests/mail/bug66535.phpt b/ext/standard/tests/mail/bug66535.phpt
new file mode 100644
index 0000000000..db1f449cb6
--- /dev/null
+++ b/ext/standard/tests/mail/bug66535.phpt
@@ -0,0 +1,43 @@
+--TEST--
+Bug #66535: Extra newline if add_x_header and no additional headers are used
+--INI--
+sendmail_path=tee mailBasic.out >/dev/null
+mail.add_x_header = On
+--SKIPIF--
+<?php
+if(substr(PHP_OS, 0, 3) == "WIN")
+ die("skip Won't run on Windows");
+?>
+--FILE--
+<?php
+/* Prototype : int mail(string to, string subject, string message [, string additional_headers [, string additional_parameters]])
+ * Description: Send an email message
+ * Source code: ext/standard/mail.c
+ * Alias to functions:
+ */
+
+echo "*** Testing mail() : send email without additional headers ***\n";
+
+// Initialise all required variables
+$to = 'user@company.com';
+$subject = 'Test Subject';
+$message = 'A Message';
+
+$outFile = "mailBasic.out";
+@unlink($outFile);
+
+var_dump( mail($to, $subject, $message) );
+echo file_get_contents($outFile);
+unlink($outFile);
+
+?>
+===DONE===
+--EXPECTF--
+*** Testing mail() : send email without additional headers ***
+bool(true)
+To: user@company.com
+Subject: Test Subject
+X-PHP-Originating-Script: %d:bug66535.php
+
+A Message
+===DONE===
diff --git a/ext/standard/tests/mail/mail_basic.phpt b/ext/standard/tests/mail/mail_basic.phpt
index fecb50f32c..70f32df40f 100644
--- a/ext/standard/tests/mail/mail_basic.phpt
+++ b/ext/standard/tests/mail/mail_basic.phpt
@@ -20,7 +20,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
$additional_headers = 'KHeaders';
@@ -45,7 +45,7 @@ unlink($outFile);
*** Testing mail() : basic functionality ***
-- All Mail Content Parameters --
bool(true)
-To: user@company.com
+To: user@example.com
Subject: Test Subject
KHeaders
@@ -53,7 +53,7 @@ A Message
-- Mandatory Parameters --
bool(true)
-To: user@company.com
+To: user@example.com
Subject: Test Subject
A Message
diff --git a/ext/standard/tests/mail/mail_basic2.phpt b/ext/standard/tests/mail/mail_basic2.phpt
index 8967d18c4f..60ad009190 100644
--- a/ext/standard/tests/mail/mail_basic2.phpt
+++ b/ext/standard/tests/mail/mail_basic2.phpt
@@ -20,7 +20,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
$additional_headers = 'KHeaders';
@@ -40,7 +40,7 @@ unlink($outFile);
*** Testing mail() : basic functionality ***
-- extra parameters --
bool(true)
-%w1%wTo: user@company.com
+%w1%wTo: user@example.com
%w2%wSubject: Test Subject
%w3%wKHeaders
%w4%w
diff --git a/ext/standard/tests/mail/mail_basic3.phpt b/ext/standard/tests/mail/mail_basic3.phpt
index 58eae0379e..3e648e5cac 100644
--- a/ext/standard/tests/mail/mail_basic3.phpt
+++ b/ext/standard/tests/mail/mail_basic3.phpt
@@ -19,7 +19,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
diff --git a/ext/standard/tests/mail/mail_basic4.phpt b/ext/standard/tests/mail/mail_basic4.phpt
index 9ecc886aec..de2407a740 100644
--- a/ext/standard/tests/mail/mail_basic4.phpt
+++ b/ext/standard/tests/mail/mail_basic4.phpt
@@ -19,7 +19,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
diff --git a/ext/standard/tests/mail/mail_basic5.phpt b/ext/standard/tests/mail/mail_basic5.phpt
index 7e42ccb833..8d755ebb86 100644
--- a/ext/standard/tests/mail/mail_basic5.phpt
+++ b/ext/standard/tests/mail/mail_basic5.phpt
@@ -19,7 +19,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
diff --git a/ext/standard/tests/mail/mail_basic_alt1-win32.phpt b/ext/standard/tests/mail/mail_basic_alt1-win32.phpt
index 3c4dd88a5b..fc50498347 100644
--- a/ext/standard/tests/mail/mail_basic_alt1-win32.phpt
+++ b/ext/standard/tests/mail/mail_basic_alt1-win32.phpt
@@ -22,7 +22,7 @@ max_execution_time = 120
error_reporting(E_ALL & ~E_STRICT);
ini_set("SMTP", "localhost");
ini_set("smtp_port", 25);
-ini_set("sendmail_from", "user@company.com");
+ini_set("sendmail_from", "user@example.com");
echo "*** Testing mail() : basic functionality ***\n";
require_once(dirname(__FILE__).'/mail_include.inc');
diff --git a/ext/standard/tests/mail/mail_basic_alt2-win32.phpt b/ext/standard/tests/mail/mail_basic_alt2-win32.phpt
index d7bae62a0f..892d92391e 100644
--- a/ext/standard/tests/mail/mail_basic_alt2-win32.phpt
+++ b/ext/standard/tests/mail/mail_basic_alt2-win32.phpt
@@ -32,7 +32,7 @@ bool mail ( string \$to , string \$subject , string \$message [, string \$additi
Send an email message
HERE;
-$extra_headers = "from: user@company.com";
+$extra_headers = "from: user@example.com";
$res = mail($to, $subject, $message, $extra_headers);
diff --git a/ext/standard/tests/mail/mail_basic_alt3-win32.phpt b/ext/standard/tests/mail/mail_basic_alt3-win32.phpt
index 86b57eb813..1caa68c068 100644
--- a/ext/standard/tests/mail/mail_basic_alt3-win32.phpt
+++ b/ext/standard/tests/mail/mail_basic_alt3-win32.phpt
@@ -32,7 +32,7 @@ bool mail ( string \$to , string \$subject , string \$message [, string \$additi
Send an email message
HERE;
-$extra_headers = "FRom: user@company.com";
+$extra_headers = "FRom: user@example.com";
$res = mail($to, $subject, $message, $extra_headers);
diff --git a/ext/standard/tests/mail/mail_basic_alt4-win32.phpt b/ext/standard/tests/mail/mail_basic_alt4-win32.phpt
index f4a9d466bc..c8e45242e2 100644
--- a/ext/standard/tests/mail/mail_basic_alt4-win32.phpt
+++ b/ext/standard/tests/mail/mail_basic_alt4-win32.phpt
@@ -32,7 +32,7 @@ bool mail ( string \$to , string \$subject , string \$message [, string \$additi
Send an email message
HERE;
-$extra_headers = "from: user@company.com";
+$extra_headers = "from: user@example.com";
$extra_parameters = "addons"; // should be ignored
$res = mail($to, $subject, $message, $extra_headers, $extra_parameters);
diff --git a/ext/standard/tests/mail/mail_variation1.phpt b/ext/standard/tests/mail/mail_variation1.phpt
index bf37bf41e6..a8eb6bec79 100644
--- a/ext/standard/tests/mail/mail_variation1.phpt
+++ b/ext/standard/tests/mail/mail_variation1.phpt
@@ -18,7 +18,7 @@ if(substr(PHP_OS, 0, 3) == "WIN")
echo "*** Testing mail() : variation ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
var_dump( mail($to, $subject, $message) );
diff --git a/ext/standard/tests/mail/mail_variation2.phpt b/ext/standard/tests/mail/mail_variation2.phpt
index c16c2706a7..f0e44241b1 100644
--- a/ext/standard/tests/mail/mail_variation2.phpt
+++ b/ext/standard/tests/mail/mail_variation2.phpt
@@ -21,7 +21,7 @@ echo "*** Testing mail() : basic functionality ***\n";
// Initialise all required variables
-$to = 'user@company.com';
+$to = 'user@example.com';
$subject = 'Test Subject';
$message = 'A Message';
$outFile = "/tmp/php_test_mailVariation2.out";
@@ -36,7 +36,7 @@ unlink($outFile);
--EXPECTF--
*** Testing mail() : basic functionality ***
bool(true)
-%w1%wTo: user@company.com
+%w1%wTo: user@example.com
%w2%wSubject: Test Subject
%w3%w
%w4%wA Message
diff --git a/ext/standard/tests/mail/mail_variation_alt1-win32.phpt b/ext/standard/tests/mail/mail_variation_alt1-win32.phpt
index b81f3af9d2..dd7fd937e2 100644
--- a/ext/standard/tests/mail/mail_variation_alt1-win32.phpt
+++ b/ext/standard/tests/mail/mail_variation_alt1-win32.phpt
@@ -21,7 +21,7 @@ max_execution_time = 120
error_reporting(E_ALL & ~E_STRICT);
ini_set("SMTP", "localhost");
ini_set("smtp_port", 2525);
-ini_set("sendmail_from", "user@company.com");
+ini_set("sendmail_from", "user@example.com");
echo "*** Testing mail() : basic functionality ***\n";
require_once(dirname(__FILE__).'/mail_include.inc');
diff --git a/ext/standard/tests/mail/mail_variation_alt2-win32.phpt b/ext/standard/tests/mail/mail_variation_alt2-win32.phpt
index 6ae06bb202..817cc36af4 100644
--- a/ext/standard/tests/mail/mail_variation_alt2-win32.phpt
+++ b/ext/standard/tests/mail/mail_variation_alt2-win32.phpt
@@ -21,7 +21,7 @@ max_execution_time = 120
error_reporting(E_ALL & ~E_STRICT);
ini_set("SMTP", "localplace");
ini_set("smtp_port", 25);
-ini_set("sendmail_from", "user@company.com");
+ini_set("sendmail_from", "user@example.com");
echo "*** Testing mail() : basic functionality ***\n";
require_once(dirname(__FILE__).'/mail_include.inc');
diff --git a/ext/standard/tests/math/tan_basiclong_64bit.phpt b/ext/standard/tests/math/tan_basiclong_64bit.phpt
index 8ab083d500..3c8abe9d27 100644
--- a/ext/standard/tests/math/tan_basiclong_64bit.phpt
+++ b/ext/standard/tests/math/tan_basiclong_64bit.phpt
@@ -1,5 +1,7 @@
--TEST--
Test tan function : 64bit long tests
+--INI--
+precision=5
--SKIPIF--
<?php
if (PHP_INT_SIZE != 8) die("skip this test is for 64bit platform only");
@@ -28,33 +30,34 @@ foreach ($longVals as $longVal) {
===DONE===
--EXPECT--
--- testing: 9223372036854775807 ---
-float(84.739312968756)
+float(84.739)
--- testing: -9223372036854775808 ---
-float(-84.739312968756)
+float(-84.739)
--- testing: 2147483647 ---
-float(1.0523779637351)
+float(1.0524)
--- testing: -2147483648 ---
-float(4.0842894552986)
+float(4.0843)
--- testing: 9223372034707292160 ---
-float(-0.25738520049439)
+float(-0.25739)
--- testing: -9223372034707292160 ---
-float(0.25738520049439)
+float(0.25739)
--- testing: 2147483648 ---
-float(-4.0842894552986)
+float(-4.0843)
--- testing: -2147483649 ---
-float(0.34328416030117)
+float(0.34328)
--- testing: 4294967294 ---
-float(-19.579238091943)
+float(-19.579)
--- testing: 4294967295 ---
-float(-0.57225137018055)
+float(-0.57225)
--- testing: 4294967293 ---
-float(0.71667000824652)
+float(0.71667)
--- testing: 9223372036854775806 ---
-float(84.739312968756)
---- testing: 9.2233720368548E+18 ---
-float(84.739312968756)
+float(84.739)
+--- testing: 9.2234E+18 ---
+float(84.739)
--- testing: -9223372036854775807 ---
-float(-84.739312968756)
---- testing: -9.2233720368548E+18 ---
-float(-84.739312968756)
+float(-84.739)
+--- testing: -9.2234E+18 ---
+float(-84.739)
===DONE===
+
diff --git a/ext/standard/tests/network/fsockopen_basic.phpt b/ext/standard/tests/network/fsockopen_basic.phpt
index 3ec9366331..227762f899 100644
--- a/ext/standard/tests/network/fsockopen_basic.phpt
+++ b/ext/standard/tests/network/fsockopen_basic.phpt
@@ -11,12 +11,18 @@ Test fsockopen() function : basic functionality
echo "*** Testing fsockopen() : basic functionality ***\n";
echo "Open a server socket\n";
-$server = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
// Initialise all required variables
$hostname = 'tcp://127.0.0.1'; // loopback address
-$port = 31337;
$errno = null;
$errstr = null;
$timeout = 1.5;
diff --git a/ext/standard/tests/network/fsockopen_variation1.phpt b/ext/standard/tests/network/fsockopen_variation1.phpt
index 2e5f8d9ada..bb1b0f15c7 100644
--- a/ext/standard/tests/network/fsockopen_variation1.phpt
+++ b/ext/standard/tests/network/fsockopen_variation1.phpt
@@ -4,11 +4,17 @@ testing fsockopen without a protocol string
<?php
echo "Open a server socket\n";
-$server = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
echo "\nCalling fsockopen() without a protocol in the hostname string:\n";
$hostname = '127.0.0.1';
-$port = '31337';
$client = fsockopen($hostname, $port);
var_dump($client);
fclose($client);
diff --git a/ext/standard/tests/network/shutdown.phpt b/ext/standard/tests/network/shutdown.phpt
index f9ab66476f..1ce77fb80e 100644
--- a/ext/standard/tests/network/shutdown.phpt
+++ b/ext/standard/tests/network/shutdown.phpt
@@ -6,14 +6,22 @@ stream_socket_shutdown() test on IPv4 TCP Loopback
?>
--FILE--
<?php
- /* Setup socket server */
- $server = stream_socket_server('tcp://127.0.0.1:31337');
- if (!$server) {
+
+ for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+ }
+
+if (!$server) {
die('Unable to create AF_INET socket [server]');
}
/* Connect and send request 1 */
- $client1 = stream_socket_client('tcp://127.0.0.1:31337');
+ $client1 = stream_socket_client("tcp://127.0.0.1:$port");
if (!$client1) {
die('Unable to create AF_INET socket [client]');
}
@@ -22,7 +30,7 @@ stream_socket_shutdown() test on IPv4 TCP Loopback
@fwrite($client1, "Error 1\n");
/* Connect and send request 2 */
- $client2 = stream_socket_client('tcp://127.0.0.1:31337');
+ $client2 = stream_socket_client("tcp://127.0.0.1:$port");
if (!$client2) {
die('Unable to create AF_INET socket [client]');
}
diff --git a/ext/standard/tests/network/socket_get_status_basic.phpt b/ext/standard/tests/network/socket_get_status_basic.phpt
index f72662b166..46215f9838 100644
--- a/ext/standard/tests/network/socket_get_status_basic.phpt
+++ b/ext/standard/tests/network/socket_get_status_basic.phpt
@@ -3,9 +3,17 @@ Testing socket_get_status()
--FILE--
<?php
-$tcp_socket = stream_socket_server('tcp://127.0.0.1:31337');
-var_dump(socket_get_status($tcp_socket));
-fclose($tcp_socket);
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
+
+var_dump(socket_get_status($server));
+fclose($server);
?>
--EXPECTF--
diff --git a/ext/standard/tests/network/tcp4loop.phpt b/ext/standard/tests/network/tcp4loop.phpt
index afd955918e..a163cd9b35 100644
--- a/ext/standard/tests/network/tcp4loop.phpt
+++ b/ext/standard/tests/network/tcp4loop.phpt
@@ -2,14 +2,21 @@
Streams Based IPv4 TCP Loopback test
--FILE--
<?php # vim:ft=php:
- /* Setup socket server */
- $server = stream_socket_server('tcp://127.0.0.1:31337');
+
+ for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+ }
if (!$server) {
die('Unable to create AF_INET socket [server]');
}
/* Connect to it */
- $client = stream_socket_client('tcp://127.0.0.1:31337');
+ $client = stream_socket_client("tcp://127.0.0.1:$port");
if (!$client) {
die('Unable to create AF_INET socket [client]');
}
diff --git a/ext/standard/tests/network/tcp6loop.phpt b/ext/standard/tests/network/tcp6loop.phpt
index 3f28cd4437..30b1d7bcd2 100644
--- a/ext/standard/tests/network/tcp6loop.phpt
+++ b/ext/standard/tests/network/tcp6loop.phpt
@@ -10,14 +10,22 @@ Streams Based IPv6 TCP Loopback test
?>
--FILE--
<?php
- /* Setup socket server */
- $server = stream_socket_server('tcp://[::1]:31337');
+
+ for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://[::1]:$port");
+ if ($server) {
+ break;
+ }
+ }
+
if (!$server) {
die('Unable to create AF_INET6 socket [server]');
}
/* Connect to it */
- $client = stream_socket_client('tcp://[::1]:31337');
+ $client = stream_socket_client("tcp://[::1]:$port");
if (!$client) {
die('Unable to create AF_INET6 socket [client]');
}
diff --git a/ext/standard/tests/network/udp6loop.phpt b/ext/standard/tests/network/udp6loop.phpt
index 5fcf7a7f46..8241d80bac 100644
--- a/ext/standard/tests/network/udp6loop.phpt
+++ b/ext/standard/tests/network/udp6loop.phpt
@@ -16,14 +16,22 @@ Streams Based IPv6 UDP Loopback test
?>
--FILE--
<?php
- /* Setup socket server */
- $server = stream_socket_server('udp://[::1]:31337', $errno, $errstr, STREAM_SERVER_BIND);
+
+ for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("udp://[::1]:$port", $errno, $errstr, STREAM_SERVER_BIND);
+ if ($server) {
+ break;
+ }
+ }
+
if (!$server) {
die('Unable to create AF_INET6 socket [server]');
}
/* Connect to it */
- $client = stream_socket_client('udp://[::1]:31337');
+ $client = stream_socket_client("udp://[::1]:$port");
if (!$client) {
die('Unable to create AF_INET6 socket [client]');
}
diff --git a/ext/standard/tests/serialize/serialization_error_002.phpt b/ext/standard/tests/serialize/serialization_error_002.phpt
new file mode 100644
index 0000000000..70f35e4f3b
--- /dev/null
+++ b/ext/standard/tests/serialize/serialization_error_002.phpt
@@ -0,0 +1,52 @@
+--TEST--
+Test unserialize(): error is indistinguishable from deserialized boolean
+--FILE--
+<?php
+/* Prototype : proto string serialize(mixed variable)
+ * Description: Returns a string representation of variable (which can later be unserialized)
+ * Source code: ext/standard/var.c
+ * Alias to functions:
+ */
+/* Prototype : proto mixed unserialize(string variable_representation)
+ * Description: Takes a string representation of variable and recreates it
+ * Source code: ext/standard/var.c
+ * Alias to functions:
+ */
+
+echo "*** Testing unserialize() error/boolean distinction ***\n";
+
+$garbage = "obvious non-serialized data";
+$serialized_false = serialize(false);
+
+var_dump($serialized_false);
+
+$deserialized_garbage = unserialize($garbage);
+var_dump($deserialized_garbage);
+
+$deserialized_false = unserialize($serialized_false);
+var_dump($deserialized_false);
+
+echo "unserialize error and deserialized false are identical? " . (bool) ($deserialized_false == $deserialized_garbage) . "\n";
+
+// candidate safe idiom for determining whether data is serialized
+function isSerialized($str) {
+ return ($str == serialize(false) || @unserialize($str) !== false);
+}
+
+// Test unserialize error idiom
+var_dump(isSerialized($garbage));
+var_dump(isSerialized($serialized_false));
+
+echo "Done";
+?>
+--EXPECTF--
+*** Testing unserialize() error/boolean distinction ***
+string(4) "b:0;"
+
+Notice: unserialize(): Error at offset 0 of 27 bytes in %s%eserialization_error_002.php on line 20
+bool(false)
+bool(false)
+unserialize error and deserialized false are identical? 1
+bool(false)
+bool(true)
+Done
diff --git a/ext/standard/tests/streams/bug60602.phpt b/ext/standard/tests/streams/bug60602.phpt
new file mode 100644
index 0000000000..2c08ce87b7
--- /dev/null
+++ b/ext/standard/tests/streams/bug60602.phpt
@@ -0,0 +1,57 @@
+--TEST--
+Bug #60602 proc_open() modifies environment if it contains arrays
+--FILE--
+<?php
+
+$descs = array(
+ 0 => array('pipe', 'r'), // stdin
+ 1 => array('pipe', 'w'), // stdout
+ 2 => array('pipe', 'w'), // strerr
+);
+
+$environment = array('test' => array(1, 2, 3));
+
+$cmd = (substr(PHP_OS, 0, 3) == 'WIN') ? 'dir' : 'ls';
+$p = proc_open($cmd, $descs, $pipes, '.', $environment);
+
+if (is_resource($p)) {
+ $data = '';
+
+ while (1) {
+ $w = $e = NULL;
+ $n = stream_select($pipes, $w, $e, 300);
+
+ if ($n === false) {
+ echo "no streams \n";
+ break;
+ } else if ($n === 0) {
+ echo "process timed out\n";
+ proc_terminate($p, 9);
+ break;
+ } else if ($n > 0) {
+ $line = fread($pipes[1], 8192);
+ if (strlen($line) == 0) {
+ /* EOF */
+ break;
+ }
+ $data .= $line;
+ }
+ }
+ var_dump(strlen($data));
+
+ $ret = proc_close($p);
+ var_dump($ret);
+ var_dump(is_array($environment['test']));
+} else {
+ echo "no process\n";
+}
+?>
+==DONE==
+--EXPECTF--
+Notice: Array to string conversion in %s on line %d
+
+Notice: Array to string conversion in %s on line %d
+int(%d)
+int(0)
+bool(true)
+==DONE==
diff --git a/ext/standard/tests/streams/stream_set_timeout_error.phpt b/ext/standard/tests/streams/stream_set_timeout_error.phpt
index c1d4d1406f..814257dd93 100644
--- a/ext/standard/tests/streams/stream_set_timeout_error.phpt
+++ b/ext/standard/tests/streams/stream_set_timeout_error.phpt
@@ -13,10 +13,16 @@ echo "*** Testing stream_set_timeout() : error conditions ***\n";
//Test stream_set_timeout with one more than the expected number of arguments
echo "\n-- Testing stream_set_timeout() function with more than expected no. of arguments --\n";
-/* Setup socket server */
-$server = stream_socket_server('tcp://127.0.0.1:31337');
+for ($i=0; $i<100; $i++) {
+ $port = rand(10000, 65000);
+ /* Setup socket server */
+ $server = @stream_socket_server("tcp://127.0.0.1:$port");
+ if ($server) {
+ break;
+ }
+}
/* Connect to it */
-$client = fsockopen('tcp://127.0.0.1:31337');
+$client = fsockopen("tcp://127.0.0.1:$port");
$seconds = 10;
$microseconds = 10;
diff --git a/ext/standard/tests/strings/bug33605.phpt b/ext/standard/tests/strings/bug33605.phpt
index f0c49eb18f..7ba38f94f5 100644
--- a/ext/standard/tests/strings/bug33605.phpt
+++ b/ext/standard/tests/strings/bug33605.phpt
@@ -2,10 +2,10 @@
Bug #33605 (substr_compare crashes)
--FILE--
<?php
-$res = substr_compare("aa", "a", -99999999, 0, 0);
+$res = substr_compare("aa", "a", -99999999, -1, 0);
var_dump($res);
?>
--EXPECTF--
-Warning: substr_compare(): The length must be greater than zero in %s on line %d
+Warning: substr_compare(): The length must be greater than or equal to zero in %s on line %d
bool(false)
diff --git a/ext/standard/tests/strings/bug65947.phpt b/ext/standard/tests/strings/bug65947.phpt
new file mode 100644
index 0000000000..956aa6049a
--- /dev/null
+++ b/ext/standard/tests/strings/bug65947.phpt
@@ -0,0 +1,17 @@
+--TEST--
+Bug #65947 (basename is no more working after fgetcsv in certain situation)
+--SKIPIF--
+<?php if (!PHP_ZTS) { print "skip only for zts build"; }
+--FILE--
+<?php
+$filename = 'test.toto';
+// é in ISO-8859-1
+$csv = base64_decode('6Q==');
+$adata = str_getcsv($csv,";");
+$b2 = basename($filename);
+if ($filename != $b2)
+ print "BUG";
+else
+ print "OKEY";
+--EXPECTF--
+OKEY
diff --git a/ext/standard/tests/strings/implode1.phpt b/ext/standard/tests/strings/implode1.phpt
index 3997c54b59..3720c06927 100644
--- a/ext/standard/tests/strings/implode1.phpt
+++ b/ext/standard/tests/strings/implode1.phpt
Binary files differ
diff --git a/ext/standard/tests/strings/substr_compare.phpt b/ext/standard/tests/strings/substr_compare.phpt
index c647506b53..84777711e6 100644
--- a/ext/standard/tests/strings/substr_compare.phpt
+++ b/ext/standard/tests/strings/substr_compare.phpt
@@ -10,9 +10,10 @@ var_dump(substr_compare("abcde", "bc", 1, 3));
var_dump(substr_compare("abcde", "cd", 1, 2));
var_dump(substr_compare("abcde", "abc", 5, 1));
var_dump(substr_compare("abcde", "abcdef", -10, 10));
-
+var_dump(substr_compare("abcde", "abc", 0, 0));
var_dump(substr_compare("abcde", -1, 0, NULL, new stdClass));
echo "Test\n";
+var_dump(substr_compare("abcde", "abc", 0, -1));
var_dump(substr_compare("abcde", "abc", -1, NULL, -5));
var_dump(substr_compare("abcde", -1, 0, "str", new stdClass));
@@ -28,13 +29,15 @@ int(-1)
Warning: substr_compare(): The start position cannot exceed initial string length in %s on line %d
bool(false)
int(-1)
+int(0)
Warning: substr_compare() expects parameter 5 to be boolean, object given in %s on line %d
bool(false)
Test
-Warning: substr_compare(): The length must be greater than zero in %s on line %d
+Warning: substr_compare(): The length must be greater than or equal to zero in %s on line %d
bool(false)
+int(0)
Warning: substr_compare() expects parameter 4 to be long, string given in %s on line %d
bool(false)
diff --git a/ext/standard/tests/strings/vfprintf_basic1.phpt b/ext/standard/tests/strings/vfprintf_basic1.phpt
index 3129d4fcca..84d8ad101d 100644
--- a/ext/standard/tests/strings/vfprintf_basic1.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic1.phpt
@@ -20,7 +20,7 @@ $arg3 = array("one","two","three");
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic1.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic2.phpt b/ext/standard/tests/strings/vfprintf_basic2.phpt
index b758caeecc..36d6577bbd 100644
--- a/ext/standard/tests/strings/vfprintf_basic2.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic2.phpt
@@ -23,7 +23,7 @@ $arg2 = array(111,222);
$arg3 = array(111,222,333);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic2.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic3.phpt b/ext/standard/tests/strings/vfprintf_basic3.phpt
index b675b3db88..565079dc60 100644
--- a/ext/standard/tests/strings/vfprintf_basic3.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic3.phpt
@@ -24,7 +24,7 @@ $arg2 = array(11.11,22.22);
$arg3 = array(11.11,22.22,33.33);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic3.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic4.phpt b/ext/standard/tests/strings/vfprintf_basic4.phpt
index 1595f034bb..e653f63306 100644
--- a/ext/standard/tests/strings/vfprintf_basic4.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic4.phpt
@@ -19,7 +19,7 @@ $arg2 = array(TRUE,FALSE);
$arg3 = array(TRUE,FALSE,TRUE);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic4.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic5.phpt b/ext/standard/tests/strings/vfprintf_basic5.phpt
index a080c9e6c4..84fbe33f1c 100644
--- a/ext/standard/tests/strings/vfprintf_basic5.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic5.phpt
@@ -19,7 +19,7 @@ $arg2 = array(65,66);
$arg3 = array(65,66,67);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic5.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic6.phpt b/ext/standard/tests/strings/vfprintf_basic6.phpt
index ed88a2832e..6c1bbf02a2 100644
--- a/ext/standard/tests/strings/vfprintf_basic6.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic6.phpt
@@ -20,7 +20,7 @@ $arg2 = array(1000,2000);
$arg3 = array(1000,2000,3000);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic6.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic7.phpt b/ext/standard/tests/strings/vfprintf_basic7.phpt
index 45544a39ec..f4c11edc15 100644
--- a/ext/standard/tests/strings/vfprintf_basic7.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic7.phpt
@@ -23,7 +23,7 @@ $arg2 = array(-1111,-1234567);
$arg3 = array(-1111,-1234567,-2345432);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic7.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic7_64bit.phpt b/ext/standard/tests/strings/vfprintf_basic7_64bit.phpt
index 77fae2c09b..14cd31ddd2 100644
--- a/ext/standard/tests/strings/vfprintf_basic7_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic7_64bit.phpt
@@ -23,7 +23,7 @@ $arg2 = array(-1111,-1234567);
$arg3 = array(-1111,-1234567,-2345432);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic7_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic8.phpt b/ext/standard/tests/strings/vfprintf_basic8.phpt
index 6fe2151542..bf7eb96ad5 100644
--- a/ext/standard/tests/strings/vfprintf_basic8.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic8.phpt
@@ -19,7 +19,7 @@ $arg2 = array(021,0347);
$arg3 = array(021,0347,05678);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic8.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_basic9.phpt b/ext/standard/tests/strings/vfprintf_basic9.phpt
index 8294c8482f..080e52bb64 100644
--- a/ext/standard/tests/strings/vfprintf_basic9.phpt
+++ b/ext/standard/tests/strings/vfprintf_basic9.phpt
@@ -24,7 +24,7 @@ $arg2 = array(11,132);
$arg3 = array(11,132,177);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_basic9.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation10.phpt b/ext/standard/tests/strings/vfprintf_variation10.phpt
index e2c066eff8..bb00e70389 100644
--- a/ext/standard/tests/strings/vfprintf_variation10.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation10.phpt
Binary files differ
diff --git a/ext/standard/tests/strings/vfprintf_variation11.phpt b/ext/standard/tests/strings/vfprintf_variation11.phpt
index 45f1f61fa6..4bc38851d2 100644
--- a/ext/standard/tests/strings/vfprintf_variation11.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation11.phpt
@@ -45,7 +45,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation11.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation11_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation11_64bit.phpt
index d6549846b5..a55297999e 100644
--- a/ext/standard/tests/strings/vfprintf_variation11_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation11_64bit.phpt
@@ -45,7 +45,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation11_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation12.phpt b/ext/standard/tests/strings/vfprintf_variation12.phpt
index e95fd5bb7f..f0fa354ea6 100644
--- a/ext/standard/tests/strings/vfprintf_variation12.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation12.phpt
@@ -68,7 +68,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation12.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation12_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation12_64bit.phpt
index a1e57bc42c..fe786d3f49 100644
--- a/ext/standard/tests/strings/vfprintf_variation12_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation12_64bit.phpt
@@ -68,7 +68,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation12_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation13.phpt b/ext/standard/tests/strings/vfprintf_variation13.phpt
index 245feb5a23..fd34242424 100644
--- a/ext/standard/tests/strings/vfprintf_variation13.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation13.phpt
@@ -45,7 +45,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation13.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation13_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation13_64bit.phpt
index bf6fcb5ec0..68baed8537 100644
--- a/ext/standard/tests/strings/vfprintf_variation13_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation13_64bit.phpt
@@ -45,7 +45,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation13_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation14.phpt b/ext/standard/tests/strings/vfprintf_variation14.phpt
index c714d89758..0173a27fb7 100644
--- a/ext/standard/tests/strings/vfprintf_variation14.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation14.phpt
@@ -68,7 +68,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation14.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation14_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation14_64bit.phpt
index 930ee3d03d..fb34befd3c 100644
--- a/ext/standard/tests/strings/vfprintf_variation14_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation14_64bit.phpt
@@ -68,7 +68,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation14_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation15.phpt b/ext/standard/tests/strings/vfprintf_variation15.phpt
index 95667b5a81..19e319a557 100644
--- a/ext/standard/tests/strings/vfprintf_variation15.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation15.phpt
@@ -38,7 +38,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation15.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation15_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation15_64bit.phpt
index d2e331c2d3..7bb0d150e0 100644
--- a/ext/standard/tests/strings/vfprintf_variation15_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation15_64bit.phpt
@@ -38,7 +38,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation15_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation16.phpt b/ext/standard/tests/strings/vfprintf_variation16.phpt
index 21630521b8..4995ab02a4 100644
--- a/ext/standard/tests/strings/vfprintf_variation16.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation16.phpt
@@ -61,7 +61,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation16.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation16_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation16_64bit.phpt
index 381e67c339..16d0624018 100644
--- a/ext/standard/tests/strings/vfprintf_variation16_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation16_64bit.phpt
@@ -61,7 +61,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation16_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation17.phpt b/ext/standard/tests/strings/vfprintf_variation17.phpt
index 871ae98d85..6c17b801f6 100644
--- a/ext/standard/tests/strings/vfprintf_variation17.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation17.phpt
@@ -34,7 +34,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation17.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation18.phpt b/ext/standard/tests/strings/vfprintf_variation18.phpt
index 76168621c3..5467753dc0 100644
--- a/ext/standard/tests/strings/vfprintf_variation18.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation18.phpt
@@ -57,7 +57,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation18.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation19.phpt b/ext/standard/tests/strings/vfprintf_variation19.phpt
index 7ee01a97e1..26c21e1e3c 100644
--- a/ext/standard/tests/strings/vfprintf_variation19.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation19.phpt
@@ -46,7 +46,7 @@ $args_array = array(
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation19.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation19_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation19_64bit.phpt
index 58810a811a..a56357cfdf 100644
--- a/ext/standard/tests/strings/vfprintf_variation19_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation19_64bit.phpt
@@ -46,7 +46,7 @@ $args_array = array(
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation19_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation20.phpt b/ext/standard/tests/strings/vfprintf_variation20.phpt
index cd348d8350..48fea341ed 100644
--- a/ext/standard/tests/strings/vfprintf_variation20.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation20.phpt
@@ -84,7 +84,7 @@ $values = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation20.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation21.phpt b/ext/standard/tests/strings/vfprintf_variation21.phpt
index 4dc9ed5666..09bf703957 100644
--- a/ext/standard/tests/strings/vfprintf_variation21.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation21.phpt
@@ -81,7 +81,7 @@ $values = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation21.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation3.phpt b/ext/standard/tests/strings/vfprintf_variation3.phpt
index 02535cefb6..1ae945990c 100644
--- a/ext/standard/tests/strings/vfprintf_variation3.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation3.phpt
@@ -45,7 +45,7 @@ $args_array = array(
// and with int values from the above $args_array array
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation3.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation4.phpt b/ext/standard/tests/strings/vfprintf_variation4.phpt
index 72ca9fe3b9..642f35c46a 100644
--- a/ext/standard/tests/strings/vfprintf_variation4.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation4.phpt
@@ -62,7 +62,7 @@ $args_array = array(
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation4.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation4_64bit.phpt b/ext/standard/tests/strings/vfprintf_variation4_64bit.phpt
index f7038ff76c..6bf814003a 100644
--- a/ext/standard/tests/strings/vfprintf_variation4_64bit.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation4_64bit.phpt
@@ -62,7 +62,7 @@ $args_array = array(
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation4_64bit.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation5.phpt b/ext/standard/tests/strings/vfprintf_variation5.phpt
index 4bac1ebe57..eb3646ca1f 100644
--- a/ext/standard/tests/strings/vfprintf_variation5.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation5.phpt
@@ -42,7 +42,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation5.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation6.phpt b/ext/standard/tests/strings/vfprintf_variation6.phpt
index 6b5425d5cf..b5b82bbc62 100644
--- a/ext/standard/tests/strings/vfprintf_variation6.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation6.phpt
@@ -57,7 +57,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation6.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation7.phpt b/ext/standard/tests/strings/vfprintf_variation7.phpt
index a206fd8691..ee836edc77 100644
--- a/ext/standard/tests/strings/vfprintf_variation7.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation7.phpt
Binary files differ
diff --git a/ext/standard/tests/strings/vfprintf_variation8.phpt b/ext/standard/tests/strings/vfprintf_variation8.phpt
index cda05c4d79..a72e260e09 100644
--- a/ext/standard/tests/strings/vfprintf_variation8.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation8.phpt
@@ -60,7 +60,7 @@ $args_array = array(
);
/* creating dumping file */
-$data_file = dirname(__FILE__) . '/dump.txt';
+$data_file = dirname(__FILE__) . '/vfprintf_variation8.txt';
if (!($fp = fopen($data_file, 'wt')))
return;
diff --git a/ext/standard/tests/strings/vfprintf_variation9.phpt b/ext/standard/tests/strings/vfprintf_variation9.phpt
index d10c8aed50..dd3093c8c9 100644
--- a/ext/standard/tests/strings/vfprintf_variation9.phpt
+++ b/ext/standard/tests/strings/vfprintf_variation9.phpt
Binary files differ
diff --git a/ext/standard/tests/time/strptime_basic.phpt b/ext/standard/tests/time/strptime_basic.phpt
index 194a78f82b..30e3e82cc7 100644
--- a/ext/standard/tests/time/strptime_basic.phpt
+++ b/ext/standard/tests/time/strptime_basic.phpt
@@ -24,7 +24,7 @@ $input = "10:00:00 AM July 2 1963";
$tstamp = strtotime($input);
$str = strftime("%r %B%e %Y %Z", $tstamp);
-var_dump(strptime($str, '%H:%M:%S %p %B %d %Y %Z'));
+var_dump(strptime($str, '%H:%M:%S %p %B %d %Y'));
$str = strftime("%T %D", $tstamp);
var_dump(strptime($str, '%H:%M:%S %m/%d/%y'));
@@ -55,7 +55,7 @@ array(9) {
["tm_yday"]=>
int(182)
["unparsed"]=>
- string(3) "GMT"
+ string(4) " GMT"
}
array(9) {
["tm_sec"]=>
diff --git a/ext/standard/tests/url/parse_url_basic_001.phpt b/ext/standard/tests/url/parse_url_basic_001.phpt
index 1edc32eaba..4c5b0944c6 100644
--- a/ext/standard/tests/url/parse_url_basic_001.phpt
+++ b/ext/standard/tests/url/parse_url_basic_001.phpt
@@ -743,6 +743,13 @@ echo "Done";
string(1) ":"
}
+--> http://::#: array(2) {
+ ["scheme"]=>
+ string(4) "http"
+ ["host"]=>
+ string(1) ":"
+}
+
--> x://::6.5: array(3) {
["scheme"]=>
string(1) "x"
@@ -856,6 +863,8 @@ echo "Done";
--> http://?: bool(false)
+--> http://#: bool(false)
+
--> http://?:: bool(false)
--> http://:?: bool(false)
@@ -863,4 +872,4 @@ echo "Done";
--> http://blah.com:123456: bool(false)
--> http://blah.com:abcdef: bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_002.phpt b/ext/standard/tests/url/parse_url_basic_002.phpt
index 464e977ffc..ed0f08a84f 100644
--- a/ext/standard/tests/url/parse_url_basic_002.phpt
+++ b/ext/standard/tests/url/parse_url_basic_002.phpt
@@ -96,6 +96,7 @@ echo "Done";
--> x:/blah.com : string(1) "x"
--> x://::abc/? : bool(false)
--> http://::? : string(4) "http"
+--> http://::# : string(4) "http"
--> x://::6.5 : string(1) "x"
--> http://?:/ : string(4) "http"
--> http://@?:/ : string(4) "http"
@@ -118,8 +119,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_003.phpt b/ext/standard/tests/url/parse_url_basic_003.phpt
index 57f182bfa3..a2bbfa6482 100644
--- a/ext/standard/tests/url/parse_url_basic_003.phpt
+++ b/ext/standard/tests/url/parse_url_basic_003.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : string(1) ":"
+--> http://::# : string(1) ":"
--> x://::6.5 : string(1) ":"
--> http://?:/ : string(1) "?"
--> http://@?:/ : string(1) "?"
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_004.phpt b/ext/standard/tests/url/parse_url_basic_004.phpt
index 6abf4ed453..839ebee554 100644
--- a/ext/standard/tests/url/parse_url_basic_004.phpt
+++ b/ext/standard/tests/url/parse_url_basic_004.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : int(6)
--> http://?:/ : NULL
--> http://@?:/ : NULL
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_005.phpt b/ext/standard/tests/url/parse_url_basic_005.phpt
index 3bcc89106d..c113461fe7 100644
--- a/ext/standard/tests/url/parse_url_basic_005.phpt
+++ b/ext/standard/tests/url/parse_url_basic_005.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : NULL
--> http://?:/ : NULL
--> http://@?:/ : string(0) ""
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_006.phpt b/ext/standard/tests/url/parse_url_basic_006.phpt
index 741a424a61..24de1cc233 100644
--- a/ext/standard/tests/url/parse_url_basic_006.phpt
+++ b/ext/standard/tests/url/parse_url_basic_006.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : NULL
--> http://?:/ : NULL
--> http://@?:/ : NULL
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_007.phpt b/ext/standard/tests/url/parse_url_basic_007.phpt
index bf8f98042e..d4006879f4 100644
--- a/ext/standard/tests/url/parse_url_basic_007.phpt
+++ b/ext/standard/tests/url/parse_url_basic_007.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : string(9) "/blah.com"
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : NULL
--> http://?:/ : string(1) "/"
--> http://@?:/ : string(1) "/"
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_008.phpt b/ext/standard/tests/url/parse_url_basic_008.phpt
index a61fd06943..b283829c46 100644
--- a/ext/standard/tests/url/parse_url_basic_008.phpt
+++ b/ext/standard/tests/url/parse_url_basic_008.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : NULL
--> http://?:/ : NULL
--> http://@?:/ : NULL
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/parse_url_basic_009.phpt b/ext/standard/tests/url/parse_url_basic_009.phpt
index 5302388f6f..a7d70f34da 100644
--- a/ext/standard/tests/url/parse_url_basic_009.phpt
+++ b/ext/standard/tests/url/parse_url_basic_009.phpt
@@ -95,6 +95,7 @@ echo "Done";
--> x:/blah.com : NULL
--> x://::abc/? : bool(false)
--> http://::? : NULL
+--> http://::# : NULL
--> x://::6.5 : NULL
--> http://?:/ : NULL
--> http://@?:/ : NULL
@@ -117,8 +118,9 @@ echo "Done";
--> http://@:/ : bool(false)
--> http://:/ : bool(false)
--> http://? : bool(false)
+--> http://# : bool(false)
--> http://?: : bool(false)
--> http://:? : bool(false)
--> http://blah.com:123456 : bool(false)
--> http://blah.com:abcdef : bool(false)
-Done \ No newline at end of file
+Done
diff --git a/ext/standard/tests/url/urls.inc b/ext/standard/tests/url/urls.inc
index 27521c8520..4192f4a869 100644
--- a/ext/standard/tests/url/urls.inc
+++ b/ext/standard/tests/url/urls.inc
@@ -75,6 +75,7 @@ $urls = array(
'x:/blah.com',
'x://::abc/?',
'http://::?',
+'http://::#',
'x://::6.5',
'http://?:/',
'http://@?:/',
@@ -99,6 +100,7 @@ $urls = array(
'http://@:/',
'http://:/',
'http://?',
+'http://#',
'http://?:',
'http://:?',
'http://blah.com:123456',
@@ -106,4 +108,4 @@ $urls = array(
);
-?> \ No newline at end of file
+?>
diff --git a/ext/standard/type.c b/ext/standard/type.c
index 5d93f66f5b..dcc8083e41 100644
--- a/ext/standard/type.c
+++ b/ext/standard/type.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/uniqid.c b/ext/standard/uniqid.c
index eac389c26c..a87bdb9c52 100644
--- a/ext/standard/uniqid.c
+++ b/ext/standard/uniqid.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/uniqid.h b/ext/standard/uniqid.h
index 1d0804051a..0ea57fa52a 100644
--- a/ext/standard/uniqid.h
+++ b/ext/standard/uniqid.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/url.c b/ext/standard/url.c
index 190b4665eb..e4eb9c48b9 100644
--- a/ext/standard/url.c
+++ b/ext/standard/url.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/url.h b/ext/standard/url.h
index 87e2efbc73..89b4b39cf9 100644
--- a/ext/standard/url.h
+++ b/ext/standard/url.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/url_scanner_ex.c b/ext/standard/url_scanner_ex.c
index 2c2dfda1b1..8a5409341b 100644
--- a/ext/standard/url_scanner_ex.c
+++ b/ext/standard/url_scanner_ex.c
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/url_scanner_ex.h b/ext/standard/url_scanner_ex.h
index 667c56c1ec..0a7925e245 100644
--- a/ext/standard/url_scanner_ex.h
+++ b/ext/standard/url_scanner_ex.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/user_filters.c b/ext/standard/user_filters.c
index 1e5c38a373..ef80f2b290 100644
--- a/ext/standard/user_filters.c
+++ b/ext/standard/user_filters.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/uuencode.c b/ext/standard/uuencode.c
index 76701ff24b..52e892ed9e 100644
--- a/ext/standard/uuencode.c
+++ b/ext/standard/uuencode.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/var.c b/ext/standard/var.c
index fb2a310f4c..d05f05527c 100644
--- a/ext/standard/var.c
+++ b/ext/standard/var.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/var_unserializer.c b/ext/standard/var_unserializer.c
index f7546428b1..004274d406 100644
--- a/ext/standard/var_unserializer.c
+++ b/ext/standard/var_unserializer.c
@@ -4,7 +4,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/standard/versioning.c b/ext/standard/versioning.c
index aadbcaf84a..9eb3829a08 100644
--- a/ext/standard/versioning.c
+++ b/ext/standard/versioning.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sybase_ct/config.w32 b/ext/sybase_ct/config.w32
index bf56bd1402..c773b623af 100644
--- a/ext/sybase_ct/config.w32
+++ b/ext/sybase_ct/config.w32
@@ -7,8 +7,11 @@ ARG_WITH("sybase-ct", "SYBASE_CT support", "no");
if (PHP_SYBASE_CT != "no") {
if (CHECK_HEADER_ADD_INCLUDE("ctpublic.h", "CFLAGS_SYBASE_CT", PHP_PHP_BUILD + "\\sybase\\include;" + PHP_SYBASE_CT) &&
- CHECK_LIB("libcs.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT) &&
- CHECK_LIB("libct.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT)) {
+ (!X64 && CHECK_LIB("libsybcs.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT) &&
+ CHECK_LIB("libsybct.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT) ||
+ X64 && CHECK_LIB("libsybcs64.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT) &&
+ CHECK_LIB("libsybct64.lib", "sybase_ct", PHP_PHP_BUILD + "\\sybase\\lib;" + PHP_SYBASE_CT))
+ ) {
EXTENSION('sybase_ct', 'php_sybase_ct.c');
AC_DEFINE('HAVE_SYBASE_CT', 1);
} else {
diff --git a/ext/sybase_ct/php_sybase_ct.c b/ext/sybase_ct/php_sybase_ct.c
index ee53d484cf..73db73e984 100644
--- a/ext/sybase_ct/php_sybase_ct.c
+++ b/ext/sybase_ct/php_sybase_ct.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sybase_ct/php_sybase_ct.h b/ext/sybase_ct/php_sybase_ct.h
index f2ac3d0460..8e4993e0ed 100644
--- a/ext/sybase_ct/php_sybase_ct.h
+++ b/ext/sybase_ct/php_sybase_ct.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvmsg/php_sysvmsg.h b/ext/sysvmsg/php_sysvmsg.h
index 86c8c1ec21..df8c4d4235 100644
--- a/ext/sysvmsg/php_sysvmsg.h
+++ b/ext/sysvmsg/php_sysvmsg.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvmsg/sysvmsg.c b/ext/sysvmsg/sysvmsg.c
index a57e25e6c3..adf1d2d6be 100644
--- a/ext/sysvmsg/sysvmsg.c
+++ b/ext/sysvmsg/sysvmsg.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvsem/php_sysvsem.h b/ext/sysvsem/php_sysvsem.h
index c4598f56f2..964c3d3de4 100644
--- a/ext/sysvsem/php_sysvsem.h
+++ b/ext/sysvsem/php_sysvsem.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvsem/sysvsem.c b/ext/sysvsem/sysvsem.c
index b6e5ccb7dc..c30def8ba5 100644
--- a/ext/sysvsem/sysvsem.c
+++ b/ext/sysvsem/sysvsem.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvshm/php_sysvshm.h b/ext/sysvshm/php_sysvshm.h
index 280b3e487c..ba8849d2c4 100644
--- a/ext/sysvshm/php_sysvshm.h
+++ b/ext/sysvshm/php_sysvshm.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/sysvshm/sysvshm.c b/ext/sysvshm/sysvshm.c
index 2d4f66aead..72ffe0b187 100644
--- a/ext/sysvshm/sysvshm.c
+++ b/ext/sysvshm/sysvshm.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tidy/php_tidy.h b/ext/tidy/php_tidy.h
index 94178039b1..efeba3baa9 100644
--- a/ext/tidy/php_tidy.h
+++ b/ext/tidy/php_tidy.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tidy/tidy.c b/ext/tidy/tidy.c
index c3b9d8c346..14aff36094 100644
--- a/ext/tidy/tidy.c
+++ b/ext/tidy/tidy.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tokenizer/php_tokenizer.h b/ext/tokenizer/php_tokenizer.h
index 761556a14b..1b5490d257 100644
--- a/ext/tokenizer/php_tokenizer.h
+++ b/ext/tokenizer/php_tokenizer.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tokenizer/tests/token_get_all_variation14.phpt b/ext/tokenizer/tests/token_get_all_variation14.phpt
index 5fc390e36c..52d29198c7 100644
--- a/ext/tokenizer/tests/token_get_all_variation14.phpt
+++ b/ext/tokenizer/tests/token_get_all_variation14.phpt
@@ -26,7 +26,7 @@ struct myStruct {
?>';
var_dump( token_get_all($source));
-// with invalid open tag for testing entire source to be unkown token
+// with invalid open tag for testing entire source to be unknown token
echo "-- with invlalid PHP open tag & valid tokens --\n";
$source = '<pli
echo "hello world"; ?>';
diff --git a/ext/tokenizer/tokenizer.c b/ext/tokenizer/tokenizer.c
index ee96e2eaa1..8e2aaab923 100644
--- a/ext/tokenizer/tokenizer.c
+++ b/ext/tokenizer/tokenizer.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tokenizer/tokenizer_data.c b/ext/tokenizer/tokenizer_data.c
index 57b29e1dd7..681c0dd9af 100644
--- a/ext/tokenizer/tokenizer_data.c
+++ b/ext/tokenizer/tokenizer_data.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/tokenizer/tokenizer_data_gen.sh b/ext/tokenizer/tokenizer_data_gen.sh
index 4ccbd2ac67..9a675c4f97 100755
--- a/ext/tokenizer/tokenizer_data_gen.sh
+++ b/ext/tokenizer/tokenizer_data_gen.sh
@@ -16,7 +16,7 @@ echo '/*
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/wddx/php_wddx.h b/ext/wddx/php_wddx.h
index 923816a40e..7e823f7c8f 100644
--- a/ext/wddx/php_wddx.h
+++ b/ext/wddx/php_wddx.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/wddx/php_wddx_api.h b/ext/wddx/php_wddx_api.h
index 1a0194535d..66a5134598 100644
--- a/ext/wddx/php_wddx_api.h
+++ b/ext/wddx/php_wddx_api.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/wddx/wddx.c b/ext/wddx/wddx.c
index afeca90489..bc0244e358 100644
--- a/ext/wddx/wddx.c
+++ b/ext/wddx/wddx.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xml/compat.c b/ext/xml/compat.c
index a4c66d259b..41f5d42012 100644
--- a/ext/xml/compat.c
+++ b/ext/xml/compat.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xml/expat_compat.h b/ext/xml/expat_compat.h
index 1c94e45fd3..dab9812122 100644
--- a/ext/xml/expat_compat.h
+++ b/ext/xml/expat_compat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xml/php_xml.h b/ext/xml/php_xml.h
index 7766834ea4..0fc25739c4 100644
--- a/ext/xml/php_xml.h
+++ b/ext/xml/php_xml.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xml/xml.c b/ext/xml/xml.c
index 1ef01c8864..a881d910b4 100644
--- a/ext/xml/xml.c
+++ b/ext/xml/xml.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlreader/php_xmlreader.c b/ext/xmlreader/php_xmlreader.c
index aae55c8b3e..ea7b5d6778 100644
--- a/ext/xmlreader/php_xmlreader.c
+++ b/ext/xmlreader/php_xmlreader.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlreader/php_xmlreader.h b/ext/xmlreader/php_xmlreader.h
index a163135d36..f559bd18d4 100644
--- a/ext/xmlreader/php_xmlreader.h
+++ b/ext/xmlreader/php_xmlreader.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlrpc/php_xmlrpc.h b/ext/xmlrpc/php_xmlrpc.h
index 00f902086c..286711b505 100644
--- a/ext/xmlrpc/php_xmlrpc.h
+++ b/ext/xmlrpc/php_xmlrpc.h
@@ -37,7 +37,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlrpc/xmlrpc-epi-php.c b/ext/xmlrpc/xmlrpc-epi-php.c
index b73cbcfe24..799b47b3ef 100644
--- a/ext/xmlrpc/xmlrpc-epi-php.c
+++ b/ext/xmlrpc/xmlrpc-epi-php.c
@@ -37,7 +37,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlwriter/php_xmlwriter.c b/ext/xmlwriter/php_xmlwriter.c
index 0a1439ced5..7bc35dabc4 100644
--- a/ext/xmlwriter/php_xmlwriter.c
+++ b/ext/xmlwriter/php_xmlwriter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xmlwriter/php_xmlwriter.h b/ext/xmlwriter/php_xmlwriter.h
index e21a5e3510..929b87ba08 100644
--- a/ext/xmlwriter/php_xmlwriter.h
+++ b/ext/xmlwriter/php_xmlwriter.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xsl/php_xsl.c b/ext/xsl/php_xsl.c
index 41e1b9fa23..3d63dd0642 100644
--- a/ext/xsl/php_xsl.c
+++ b/ext/xsl/php_xsl.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xsl/php_xsl.h b/ext/xsl/php_xsl.h
index e1a792e84b..a457856815 100644
--- a/ext/xsl/php_xsl.h
+++ b/ext/xsl/php_xsl.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xsl/tests/bug49634.phpt b/ext/xsl/tests/bug49634.phpt
new file mode 100644
index 0000000000..b009fd5fb8
--- /dev/null
+++ b/ext/xsl/tests/bug49634.phpt
@@ -0,0 +1,105 @@
+--TEST--
+bug #49634 (Segfault throwing an exception in a XSL registered function)
+--SKIPIF--
+<?php
+extension_loaded("xsl") or die("skip need ext/xsl");
+?>
+--FILE--
+<?php
+
+$sXml = <<<XML
+<?xml version="1.0" encoding="UTF-8" ?>
+<root>
+ test
+</root>
+XML;
+
+$cDIR = __DIR__;
+$sXsl = <<<XSL
+<xsl:stylesheet version="1.0"
+ xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
+ xmlns:ext="http://php.net/xsl"
+ xsl:extension-element-prefixes="ext"
+ exclude-result-prefixes="ext">
+ <xsl:output encoding="UTF-8" indent="yes" method="xml" />
+ <xsl:template match="/">
+ <xsl:value-of select="ext:function('testFunction', document('$cDIR/bug49634.xml')/root)"/>
+ </xsl:template>
+</xsl:stylesheet>
+XSL;
+
+function testFunction($a)
+{
+ throw new Exception('Test exception.');
+}
+
+$domXml = new DOMDocument;
+$domXml->loadXML($sXml);
+$domXsl = new DOMDocument;
+$domXsl->loadXML($sXsl);
+
+for ($i = 0; $i < 10; $i++)
+{
+ $xsltProcessor = new XSLTProcessor();
+ $xsltProcessor->registerPHPFunctions(array('testFunction'));
+ $xsltProcessor->importStyleSheet($domXsl);
+ try {
+ @$xsltProcessor->transformToDoc($domXml);
+ } catch (Exception $e) {
+ echo $e,"\n";
+ }
+}
+?>
+===DONE===
+--EXPECTF--
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+exception 'Exception' with message 'Test exception.' in %s:%d
+Stack trace:
+#0 [internal function]: testFunction(Array)
+#1 %s(%d): XSLTProcessor->transformToDoc(Object(DOMDocument))
+#2 {main}
+===DONE===
diff --git a/ext/xsl/tests/bug49634.xml b/ext/xsl/tests/bug49634.xml
new file mode 100644
index 0000000000..f3f286eafc
--- /dev/null
+++ b/ext/xsl/tests/bug49634.xml
@@ -0,0 +1 @@
+<root/>
diff --git a/ext/xsl/xsl_fe.h b/ext/xsl/xsl_fe.h
index ba9d49beb7..89726da724 100644
--- a/ext/xsl/xsl_fe.h
+++ b/ext/xsl/xsl_fe.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/xsl/xsltprocessor.c b/ext/xsl/xsltprocessor.c
index af11104a2e..67c90f501f 100644
--- a/ext/xsl/xsltprocessor.c
+++ b/ext/xsl/xsltprocessor.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -279,7 +279,10 @@ static void xsl_ext_function_php(xmlXPathParserContextPtr ctxt, int nargs, int t
node->type = XML_NAMESPACE_DECL;
node->parent = nsparent;
node->ns = curns;
+ } else {
+ node = xmlDocCopyNodeList(domintern->document->ptr, node);
}
+
child = php_dom_create_object(node, &ret, child, domintern TSRMLS_CC);
add_next_index_zval(args[i], child);
}
diff --git a/ext/zip/php_zip.c b/ext/zip/php_zip.c
index d3ec27bafe..05dd1ecc21 100644
--- a/ext/zip/php_zip.c
+++ b/ext/zip/php_zip.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1537,7 +1537,7 @@ static ZIPARCHIVE_METHOD(open)
RETURN_LONG((long)err);
}
ze_obj->filename = estrdup(resolved_path);
- ze_obj->filename_len = filename_len;
+ ze_obj->filename_len = strlen(resolved_path);
ze_obj->za = intern;
RETURN_TRUE;
}
diff --git a/ext/zip/php_zip.h b/ext/zip/php_zip.h
index 7dd9ff09d0..06571948f1 100644
--- a/ext/zip/php_zip.h
+++ b/ext/zip/php_zip.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/zlib/php_zlib.h b/ext/zlib/php_zlib.h
index 6b1d0cd80c..b8a778fef0 100644
--- a/ext/zlib/php_zlib.h
+++ b/ext/zlib/php_zlib.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/zlib/tests/gzeof_variation1.phpt b/ext/zlib/tests/gzeof_variation1.phpt
index 6d1e0401df..77a1eccb66 100644
--- a/ext/zlib/tests/gzeof_variation1.phpt
+++ b/ext/zlib/tests/gzeof_variation1.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = dirname(__FILE__)."/temp.txt.gz";
+$filename = dirname(__FILE__)."/gzeof_variation1.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
$length = 10;
diff --git a/ext/zlib/tests/gzfile_basic.phpt b/ext/zlib/tests/gzfile_basic.phpt
index 1fceea5b90..17055646d8 100644
--- a/ext/zlib/tests/gzfile_basic.phpt
+++ b/ext/zlib/tests/gzfile_basic.phpt
@@ -12,7 +12,7 @@ is a very common test
for all languages
EOT;
$dirname = 'gzfile_temp';
-$filename = $dirname.'/plainfile.txt.gz';
+$filename = $dirname.'/gzfile_basic.txt.gz';
mkdir($dirname);
$h = gzopen($filename, 'w');
gzwrite($h, $plaintxt);
@@ -36,4 +36,4 @@ array(3) {
[2]=>
string(17) "for all languages"
}
-===DONE=== \ No newline at end of file
+===DONE===
diff --git a/ext/zlib/tests/gzfile_basic2.phpt b/ext/zlib/tests/gzfile_basic2.phpt
index 9f31eb0f87..2bbf315a1a 100644
--- a/ext/zlib/tests/gzfile_basic2.phpt
+++ b/ext/zlib/tests/gzfile_basic2.phpt
@@ -12,7 +12,7 @@ is a very common test
for all languages
EOT;
$dirname = 'gzfile_temp';
-$filename = $dirname.'/plainfile.txt';
+$filename = $dirname.'/gzfile_basic2.txt';
mkdir($dirname);
$h = fopen($filename, 'w');
fwrite($h, $plaintxt);
@@ -36,4 +36,4 @@ array(3) {
[2]=>
string(17) "for all languages"
}
-===DONE=== \ No newline at end of file
+===DONE===
diff --git a/ext/zlib/tests/gzopen_basic2.phpt b/ext/zlib/tests/gzopen_basic2.phpt
index 5cc02cd182..90766b1817 100644
--- a/ext/zlib/tests/gzopen_basic2.phpt
+++ b/ext/zlib/tests/gzopen_basic2.phpt
@@ -18,7 +18,7 @@ echo "*** Testing gzopen() : basic functionality ***\n";
// Initialise all required variables
-$filename = "temp.txt.gz";
+$filename = "gzopen_basic2.txt.gz";
$modes = array('w', 'w+');
$data = "This was the information that was written";
diff --git a/ext/zlib/tests/gzputs_basic.phpt b/ext/zlib/tests/gzputs_basic.phpt
index 7566e74e72..6456e4b55f 100644
--- a/ext/zlib/tests/gzputs_basic.phpt
+++ b/ext/zlib/tests/gzputs_basic.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = dirname(__FILE__)."/temp.txt.gz";
+$filename = dirname(__FILE__)."/gzputs_basic.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
$length = 10;
diff --git a/ext/zlib/tests/gzread_variation1.phpt b/ext/zlib/tests/gzread_variation1.phpt
index 1f50d77126..966351e736 100644
--- a/ext/zlib/tests/gzread_variation1.phpt
+++ b/ext/zlib/tests/gzread_variation1.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = "temp.txt.gz";
+$filename = "gzread_variation1.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
var_dump(gzread($h, 100));
diff --git a/ext/zlib/tests/gzwrite_basic.phpt b/ext/zlib/tests/gzwrite_basic.phpt
index 0d7521625d..46553eedf1 100644
--- a/ext/zlib/tests/gzwrite_basic.phpt
+++ b/ext/zlib/tests/gzwrite_basic.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = "temp.txt.gz";
+$filename = "gzwrite_basic.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
$length = 10;
diff --git a/ext/zlib/tests/gzwrite_error.phpt b/ext/zlib/tests/gzwrite_error.phpt
index b84a1db0c8..b4ddbb2ec7 100644
--- a/ext/zlib/tests/gzwrite_error.phpt
+++ b/ext/zlib/tests/gzwrite_error.phpt
@@ -8,7 +8,7 @@ if (!extension_loaded("zlib")) {
?>
--FILE--
<?php
-$filename = "temp.txt.gz";
+$filename = "gzwrite_error.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
$length = 10;
diff --git a/ext/zlib/tests/gzwrite_error2.phpt b/ext/zlib/tests/gzwrite_error2.phpt
index 691275055d..5f2a4197b5 100644
--- a/ext/zlib/tests/gzwrite_error2.phpt
+++ b/ext/zlib/tests/gzwrite_error2.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = "temp.txt.gz";
+$filename = "gzwrite_error2.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written. ";
var_dump(gzwrite( $h, $str, 0 ) );
diff --git a/ext/zlib/tests/readgzfile_basic.phpt b/ext/zlib/tests/readgzfile_basic.phpt
index 2d180c1a56..5fd539e21c 100644
--- a/ext/zlib/tests/readgzfile_basic.phpt
+++ b/ext/zlib/tests/readgzfile_basic.phpt
@@ -13,7 +13,7 @@ for all languages
EOT;
$dirname = 'readgzfile_temp';
-$filename = $dirname.'/plainfile.txt.gz';
+$filename = $dirname.'/readgzfile_basic.txt.gz';
mkdir($dirname);
$h = gzopen($filename, 'w');
gzwrite($h, $plaintxt);
diff --git a/ext/zlib/tests/readgzfile_basic2.phpt b/ext/zlib/tests/readgzfile_basic2.phpt
index 99d216a55e..5402f960c2 100644
--- a/ext/zlib/tests/readgzfile_basic2.phpt
+++ b/ext/zlib/tests/readgzfile_basic2.phpt
@@ -13,7 +13,7 @@ for all languages
EOT;
$dirname = 'readgzfile_temp';
-$filename = $dirname.'/plainfile.txt';
+$filename = $dirname.'/readgzfile_basic2.txt';
mkdir($dirname);
$h = fopen($filename, 'w');
fwrite($h, $plaintxt);
diff --git a/ext/zlib/tests/zlib_wrapper_fflush_basic.phpt b/ext/zlib/tests/zlib_wrapper_fflush_basic.phpt
index 74ccc0dabb..de1318cfed 100644
--- a/ext/zlib/tests/zlib_wrapper_fflush_basic.phpt
+++ b/ext/zlib/tests/zlib_wrapper_fflush_basic.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
-$filename = "temp.txt.gz";
+$filename = "zlib_wrapper_fflush_basic.txt.gz";
$h = gzopen($filename, 'w');
$str = "Here is the string to be written.";
$length = 10;
diff --git a/ext/zlib/tests/zlib_wrapper_ftruncate_basic.phpt b/ext/zlib/tests/zlib_wrapper_ftruncate_basic.phpt
index 53b140ac56..348e24505c 100644
--- a/ext/zlib/tests/zlib_wrapper_ftruncate_basic.phpt
+++ b/ext/zlib/tests/zlib_wrapper_ftruncate_basic.phpt
@@ -9,7 +9,7 @@ if (!extension_loaded("zlib")) {
--FILE--
<?php
$f = dirname(__FILE__)."/004.txt.gz";
-$f2 = "temp.txt.gz";
+$f2 = "zlib_wrapper_ftruncate_basic.txt.gz";
copy($f, $f2);
$h = gzopen($f2, "r");
diff --git a/ext/zlib/zlib.c b/ext/zlib/zlib.c
index 1114bc8a65..705fb5dd5f 100644
--- a/ext/zlib/zlib.c
+++ b/ext/zlib/zlib.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/zlib/zlib_filter.c b/ext/zlib/zlib_filter.c
index 8ccd9e161c..9a59c3a855 100644
--- a/ext/zlib/zlib_filter.c
+++ b/ext/zlib/zlib_filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/ext/zlib/zlib_fopen_wrapper.c b/ext/zlib/zlib_fopen_wrapper.c
index 1b00eb8713..4807d67aa2 100644
--- a/ext/zlib/zlib_fopen_wrapper.c
+++ b/ext/zlib/zlib_fopen_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/SAPI.c b/main/SAPI.c
index dcb2da629a..6890db3e65 100644
--- a/main/SAPI.c
+++ b/main/SAPI.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -137,6 +137,7 @@ PHP_FUNCTION(header_register_callback)
efree(callback_name);
RETURN_FALSE;
}
+
efree(callback_name);
if (SG(callback_func)) {
@@ -144,10 +145,10 @@ PHP_FUNCTION(header_register_callback)
SG(fci_cache) = empty_fcall_info_cache;
}
- Z_ADDREF_P(callback_func);
-
SG(callback_func) = callback_func;
-
+
+ Z_ADDREF_P(SG(callback_func));
+
RETURN_TRUE;
}
/* }}} */
@@ -156,24 +157,30 @@ static void sapi_run_header_callback(TSRMLS_D)
{
int error;
zend_fcall_info fci;
+ char *callback_name = NULL;
+ char *callback_error = NULL;
zval *retval_ptr = NULL;
-
- fci.size = sizeof(fci);
- fci.function_table = EG(function_table);
- fci.object_ptr = NULL;
- fci.function_name = SG(callback_func);
- fci.retval_ptr_ptr = &retval_ptr;
- fci.param_count = 0;
- fci.params = NULL;
- fci.no_separation = 0;
- fci.symbol_table = NULL;
-
- error = zend_call_function(&fci, &SG(fci_cache) TSRMLS_CC);
- if (error == FAILURE) {
+
+ if (zend_fcall_info_init(SG(callback_func), 0, &fci, &SG(fci_cache), &callback_name, &callback_error TSRMLS_CC) == SUCCESS) {
+ fci.retval_ptr_ptr = &retval_ptr;
+
+ error = zend_call_function(&fci, &SG(fci_cache) TSRMLS_CC);
+ if (error == FAILURE) {
+ goto callback_failed;
+ } else if (retval_ptr) {
+ zval_ptr_dtor(&retval_ptr);
+ }
+ } else {
+callback_failed:
php_error_docref(NULL TSRMLS_CC, E_WARNING, "Could not call the sapi_header_callback");
- } else if (retval_ptr) {
- zval_ptr_dtor(&retval_ptr);
}
+
+ if (callback_name) {
+ efree(callback_name);
+ }
+ if (callback_error) {
+ efree(callback_error);
+ }
}
SAPI_API void sapi_handle_post(void *arg TSRMLS_DC)
diff --git a/main/SAPI.h b/main/SAPI.h
index 92b7329dbc..c86ef6735c 100644
--- a/main/SAPI.h
+++ b/main/SAPI.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/fopen_wrappers.c b/main/fopen_wrappers.c
index 9b8645a061..4f6c79da1d 100644
--- a/main/fopen_wrappers.c
+++ b/main/fopen_wrappers.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/fopen_wrappers.h b/main/fopen_wrappers.h
index ee96eef313..4dde0e35eb 100644
--- a/main/fopen_wrappers.h
+++ b/main/fopen_wrappers.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/getopt.c b/main/getopt.c
index 591c8c7778..a31a6c75d5 100644
--- a/main/getopt.c
+++ b/main/getopt.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/internal_functions_nw.c b/main/internal_functions_nw.c
index 07aec9a08e..86ba57d486 100644
--- a/main/internal_functions_nw.c
+++ b/main/internal_functions_nw.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/internal_functions_win32.c b/main/internal_functions_win32.c
index 06cd5b2a50..8b5518ca90 100644
--- a/main/internal_functions_win32.c
+++ b/main/internal_functions_win32.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/main.c b/main/main.c
index 5942b23f72..66e4b6e93f 100644
--- a/main/main.c
+++ b/main/main.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1929,6 +1929,23 @@ int php_register_extensions(zend_module_entry **ptr, int count TSRMLS_DC)
}
return SUCCESS;
}
+
+/* A very long time ago php_module_startup() was refactored in a way
+ * which broke calling it with more than one additional module.
+ * This alternative to php_register_extensions() works around that
+ * by walking the shallower structure.
+ *
+ * See algo: https://bugs.php.net/bug.php?id=63159
+ */
+static int php_register_extensions_bc(zend_module_entry *ptr, int count TSRMLS_DC)
+{
+ while (count--) {
+ if (zend_register_internal_module(ptr++ TSRMLS_CC) == NULL) {
+ return FAILURE;
+ }
+ }
+ return SUCCESS;
+}
/* }}} */
#if defined(PHP_WIN32) && _MSC_VER >= 1400
@@ -2199,7 +2216,7 @@ int php_module_startup(sapi_module_struct *sf, zend_module_entry *additional_mod
}
/* start additional PHP extensions */
- php_register_extensions(&additional_modules, num_additional_modules TSRMLS_CC);
+ php_register_extensions_bc(additional_modules, num_additional_modules TSRMLS_CC);
/* load and startup extensions compiled as shared objects (aka DLLs)
as requested by php.ini entries
diff --git a/main/network.c b/main/network.c
index 5c0404b239..fc2a94badd 100644
--- a/main/network.c
+++ b/main/network.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/output.c b/main/output.c
index 9324f059da..72092e9561 100644
--- a/main/output.c
+++ b/main/output.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php.h b/main/php.h
index 7c1f8fd0c7..eff66d00b8 100644
--- a/main/php.h
+++ b/main/php.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_compat.h b/main/php_compat.h
index 936dd5231f..20951ba427 100644
--- a/main/php_compat.h
+++ b/main/php_compat.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_content_types.c b/main/php_content_types.c
index c4433978ed..c36812f101 100644
--- a/main/php_content_types.c
+++ b/main/php_content_types.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_content_types.h b/main/php_content_types.h
index 7ceffff5c0..ed5346c843 100644
--- a/main/php_content_types.h
+++ b/main/php_content_types.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_getopt.h b/main/php_getopt.h
index a3f4c1420b..f536ac8a96 100644
--- a/main/php_getopt.h
+++ b/main/php_getopt.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_globals.h b/main/php_globals.h
index 256765d665..b65499f1b3 100644
--- a/main/php_globals.h
+++ b/main/php_globals.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_ini.c b/main/php_ini.c
index e9529a2d29..e20ba4ba73 100644
--- a/main/php_ini.c
+++ b/main/php_ini.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -630,63 +630,81 @@ int php_init_config(TSRMLS_D)
zend_llist scanned_ini_list;
zend_llist_element *element;
int l, total_l = 0;
+ char *bufpath, *debpath, *endpath;
+ int lenpath;
- if ((ndir = php_scandir(php_ini_scanned_path, &namelist, 0, php_alphasort)) > 0) {
- zend_llist_init(&scanned_ini_list, sizeof(char *), (llist_dtor_func_t) free_estring, 1);
- memset(&fh2, 0, sizeof(fh2));
+ zend_llist_init(&scanned_ini_list, sizeof(char *), (llist_dtor_func_t) free_estring, 1);
+ memset(&fh2, 0, sizeof(fh2));
- for (i = 0; i < ndir; i++) {
+ bufpath = estrdup(php_ini_scanned_path);
+ for (debpath = bufpath ; debpath ; debpath=endpath) {
+ endpath = strchr(debpath, DEFAULT_DIR_SEPARATOR);
+ if (endpath) {
+ *(endpath++) = 0;
+ }
+ if (!debpath[0]) {
+ /* empty string means default builtin value
+ to allow "/foo/phd.d:" or ":/foo/php.d" */
+ debpath = PHP_CONFIG_FILE_SCAN_DIR;
+ }
+ lenpath = strlen(debpath);
- /* check for any file with .ini extension */
- if (!(p = strrchr(namelist[i]->d_name, '.')) || (p && strcmp(p, ".ini"))) {
- free(namelist[i]);
- continue;
- }
- /* Reset active ini section */
- RESET_ACTIVE_INI_HASH();
+ if (lenpath > 0 && (ndir = php_scandir(debpath, &namelist, 0, php_alphasort)) > 0) {
- if (IS_SLASH(php_ini_scanned_path[php_ini_scanned_path_len - 1])) {
- snprintf(ini_file, MAXPATHLEN, "%s%s", php_ini_scanned_path, namelist[i]->d_name);
- } else {
- snprintf(ini_file, MAXPATHLEN, "%s%c%s", php_ini_scanned_path, DEFAULT_SLASH, namelist[i]->d_name);
- }
- if (VCWD_STAT(ini_file, &sb) == 0) {
- if (S_ISREG(sb.st_mode)) {
- if ((fh2.handle.fp = VCWD_FOPEN(ini_file, "r"))) {
- fh2.filename = ini_file;
- fh2.type = ZEND_HANDLE_FP;
-
- if (zend_parse_ini_file(&fh2, 1, ZEND_INI_SCANNER_NORMAL, (zend_ini_parser_cb_t) php_ini_parser_cb, &configuration_hash TSRMLS_CC) == SUCCESS) {
- /* Here, add it to the list of ini files read */
- l = strlen(ini_file);
- total_l += l + 2;
- p = estrndup(ini_file, l);
- zend_llist_add_element(&scanned_ini_list, &p);
+ for (i = 0; i < ndir; i++) {
+
+ /* check for any file with .ini extension */
+ if (!(p = strrchr(namelist[i]->d_name, '.')) || (p && strcmp(p, ".ini"))) {
+ free(namelist[i]);
+ continue;
+ }
+ /* Reset active ini section */
+ RESET_ACTIVE_INI_HASH();
+
+ if (IS_SLASH(debpath[lenpath - 1])) {
+ snprintf(ini_file, MAXPATHLEN, "%s%s", debpath, namelist[i]->d_name);
+ } else {
+ snprintf(ini_file, MAXPATHLEN, "%s%c%s", debpath, DEFAULT_SLASH, namelist[i]->d_name);
+ }
+ if (VCWD_STAT(ini_file, &sb) == 0) {
+ if (S_ISREG(sb.st_mode)) {
+ if ((fh2.handle.fp = VCWD_FOPEN(ini_file, "r"))) {
+ fh2.filename = ini_file;
+ fh2.type = ZEND_HANDLE_FP;
+
+ if (zend_parse_ini_file(&fh2, 1, ZEND_INI_SCANNER_NORMAL, (zend_ini_parser_cb_t) php_ini_parser_cb, &configuration_hash TSRMLS_CC) == SUCCESS) {
+ /* Here, add it to the list of ini files read */
+ l = strlen(ini_file);
+ total_l += l + 2;
+ p = estrndup(ini_file, l);
+ zend_llist_add_element(&scanned_ini_list, &p);
+ }
}
}
}
+ free(namelist[i]);
}
- free(namelist[i]);
+ free(namelist);
}
- free(namelist);
+ }
+ efree(bufpath);
- if (total_l) {
- int php_ini_scanned_files_len = (php_ini_scanned_files) ? strlen(php_ini_scanned_files) + 1 : 0;
- php_ini_scanned_files = (char *) realloc(php_ini_scanned_files, php_ini_scanned_files_len + total_l + 1);
- if (!php_ini_scanned_files_len) {
- *php_ini_scanned_files = '\0';
- }
- total_l += php_ini_scanned_files_len;
- for (element = scanned_ini_list.head; element; element = element->next) {
- if (php_ini_scanned_files_len) {
- strlcat(php_ini_scanned_files, ",\n", total_l);
- }
- strlcat(php_ini_scanned_files, *(char **)element->data, total_l);
- strlcat(php_ini_scanned_files, element->next ? ",\n" : "\n", total_l);
+ if (total_l) {
+ int php_ini_scanned_files_len = (php_ini_scanned_files) ? strlen(php_ini_scanned_files) + 1 : 0;
+ php_ini_scanned_files = (char *) realloc(php_ini_scanned_files, php_ini_scanned_files_len + total_l + 1);
+ if (!php_ini_scanned_files_len) {
+ *php_ini_scanned_files = '\0';
+ }
+ total_l += php_ini_scanned_files_len;
+ for (element = scanned_ini_list.head; element; element = element->next) {
+ if (php_ini_scanned_files_len) {
+ strlcat(php_ini_scanned_files, ",\n", total_l);
}
+ strlcat(php_ini_scanned_files, *(char **)element->data, total_l);
+ strlcat(php_ini_scanned_files, element->next ? ",\n" : "\n", total_l);
}
- zend_llist_destroy(&scanned_ini_list);
}
+ zend_llist_destroy(&scanned_ini_list);
} else {
/* Make sure an empty php_ini_scanned_path ends up as NULL */
php_ini_scanned_path = NULL;
diff --git a/main/php_ini.h b/main/php_ini.h
index 65c80f7593..4159e7591f 100644
--- a/main/php_ini.h
+++ b/main/php_ini.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_main.h b/main/php_main.h
index 68ae83700e..1325486bd9 100644
--- a/main/php_main.h
+++ b/main/php_main.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_memory_streams.h b/main/php_memory_streams.h
index 0f975cc72d..3c4c3280eb 100644
--- a/main/php_memory_streams.h
+++ b/main/php_memory_streams.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_network.h b/main/php_network.h
index c1535ee040..d69bba308a 100644
--- a/main/php_network.h
+++ b/main/php_network.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_open_temporary_file.c b/main/php_open_temporary_file.c
index 054d497be6..16b61b8ba7 100644
--- a/main/php_open_temporary_file.c
+++ b/main/php_open_temporary_file.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_open_temporary_file.h b/main/php_open_temporary_file.h
index 75ac0bb0fe..873bffcb0a 100644
--- a/main/php_open_temporary_file.h
+++ b/main/php_open_temporary_file.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_output.h b/main/php_output.h
index 833bddec38..0312e256f8 100644
--- a/main/php_output.h
+++ b/main/php_output.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_reentrancy.h b/main/php_reentrancy.h
index 50f2e209cd..2f2e99c0b4 100644
--- a/main/php_reentrancy.h
+++ b/main/php_reentrancy.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_scandir.c b/main/php_scandir.c
index 9f3042e0f1..36c0c648e1 100644
--- a/main/php_scandir.c
+++ b/main/php_scandir.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_scandir.h b/main/php_scandir.h
index ad68e8d518..90708c6872 100644
--- a/main/php_scandir.h
+++ b/main/php_scandir.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_sprintf.c b/main/php_sprintf.c
index 9df43a557d..e9f956f8dd 100644
--- a/main/php_sprintf.c
+++ b/main/php_sprintf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_streams.h b/main/php_streams.h
index 5acf942e43..b0ecff07ad 100644
--- a/main/php_streams.h
+++ b/main/php_streams.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_syslog.h b/main/php_syslog.h
index e070487825..f8280a8a50 100644
--- a/main/php_syslog.h
+++ b/main/php_syslog.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_ticks.c b/main/php_ticks.c
index 17ffb9c770..b07f925fab 100644
--- a/main/php_ticks.c
+++ b/main/php_ticks.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_ticks.h b/main/php_ticks.h
index cc966fa520..0f58adac6a 100644
--- a/main/php_ticks.h
+++ b/main/php_ticks.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_variables.c b/main/php_variables.c
index 7018eae57b..ddd9408bb7 100644
--- a/main/php_variables.c
+++ b/main/php_variables.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_variables.h b/main/php_variables.h
index 8f5e96aac3..37b2cf2a04 100644
--- a/main/php_variables.h
+++ b/main/php_variables.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/php_version.h b/main/php_version.h
index 2d98a3f807..34f51281fa 100644
--- a/main/php_version.h
+++ b/main/php_version.h
@@ -2,7 +2,7 @@
/* edit configure.in to change version number */
#define PHP_MAJOR_VERSION 5
#define PHP_MINOR_VERSION 5
-#define PHP_RELEASE_VERSION 6
+#define PHP_RELEASE_VERSION 11
#define PHP_EXTRA_VERSION "-dev"
-#define PHP_VERSION "5.5.6-dev"
-#define PHP_VERSION_ID 50506
+#define PHP_VERSION "5.5.11-dev"
+#define PHP_VERSION_ID 50511
diff --git a/main/reentrancy.c b/main/reentrancy.c
index 7f85224835..dd411f478b 100644
--- a/main/reentrancy.c
+++ b/main/reentrancy.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/rfc1867.c b/main/rfc1867.c
index 7c208c368c..ab1eb75e7d 100644
--- a/main/rfc1867.c
+++ b/main/rfc1867.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/rfc1867.h b/main/rfc1867.h
index 8a502c4b89..1d47165851 100644
--- a/main/rfc1867.h
+++ b/main/rfc1867.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/snprintf.c b/main/snprintf.c
index 4514bd6821..1c73dcdcb7 100644
--- a/main/snprintf.c
+++ b/main/snprintf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/snprintf.h b/main/snprintf.h
index f4ed4d234d..10f0e24fa5 100644
--- a/main/snprintf.h
+++ b/main/snprintf.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/spprintf.c b/main/spprintf.c
index 596e1ef456..5b16d51441 100644
--- a/main/spprintf.c
+++ b/main/spprintf.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/spprintf.h b/main/spprintf.h
index d9aa9533e5..813bbde01a 100644
--- a/main/spprintf.h
+++ b/main/spprintf.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/cast.c b/main/streams/cast.c
index bf96d3cf80..78073c6187 100644
--- a/main/streams/cast.c
+++ b/main/streams/cast.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/filter.c b/main/streams/filter.c
index 6de3a928fe..71599f0d12 100644
--- a/main/streams/filter.c
+++ b/main/streams/filter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/glob_wrapper.c b/main/streams/glob_wrapper.c
index 9c051a5921..e0a1561fc3 100644
--- a/main/streams/glob_wrapper.c
+++ b/main/streams/glob_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/memory.c b/main/streams/memory.c
index 328d3be399..e6d0baaa86 100644
--- a/main/streams/memory.c
+++ b/main/streams/memory.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/mmap.c b/main/streams/mmap.c
index 4f9388c6e7..050e95f285 100644
--- a/main/streams/mmap.c
+++ b/main/streams/mmap.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_context.h b/main/streams/php_stream_context.h
index 59fa604306..58b298b689 100644
--- a/main/streams/php_stream_context.h
+++ b/main/streams/php_stream_context.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_filter_api.h b/main/streams/php_stream_filter_api.h
index abb5906654..9d9894c1c5 100644
--- a/main/streams/php_stream_filter_api.h
+++ b/main/streams/php_stream_filter_api.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_glob_wrapper.h b/main/streams/php_stream_glob_wrapper.h
index 330e917bda..d0322f7190 100644
--- a/main/streams/php_stream_glob_wrapper.h
+++ b/main/streams/php_stream_glob_wrapper.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_mmap.h b/main/streams/php_stream_mmap.h
index 7895ac69d4..b3570be48c 100644
--- a/main/streams/php_stream_mmap.h
+++ b/main/streams/php_stream_mmap.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_plain_wrapper.h b/main/streams/php_stream_plain_wrapper.h
index d88b30c479..f27dde2e55 100644
--- a/main/streams/php_stream_plain_wrapper.h
+++ b/main/streams/php_stream_plain_wrapper.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_transport.h b/main/streams/php_stream_transport.h
index c2d911032e..072625b701 100644
--- a/main/streams/php_stream_transport.h
+++ b/main/streams/php_stream_transport.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_stream_userspace.h b/main/streams/php_stream_userspace.h
index 2830dd0d26..28985a5e1e 100644
--- a/main/streams/php_stream_userspace.h
+++ b/main/streams/php_stream_userspace.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/php_streams_int.h b/main/streams/php_streams_int.h
index daae2b8893..489e18b26f 100644
--- a/main/streams/php_streams_int.h
+++ b/main/streams/php_streams_int.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/plain_wrapper.c b/main/streams/plain_wrapper.c
index 39df31a170..a50662b78e 100644
--- a/main/streams/plain_wrapper.c
+++ b/main/streams/plain_wrapper.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -78,11 +78,7 @@ PHPAPI int php_stream_parse_fopen_modes(const char *mode, int *open_flags)
/* unknown mode */
return FAILURE;
}
-#if defined(O_NONBLOCK)
- if (strchr(mode, 'n')) {
- flags |= O_NONBLOCK;
- }
-#endif
+
if (strchr(mode, '+')) {
flags |= O_RDWR;
} else if (flags) {
@@ -91,6 +87,12 @@ PHPAPI int php_stream_parse_fopen_modes(const char *mode, int *open_flags)
flags |= O_RDONLY;
}
+#if defined(O_NONBLOCK)
+ if (strchr(mode, 'n')) {
+ flags |= O_NONBLOCK;
+ }
+#endif
+
#if defined(_O_TEXT) && defined(O_BINARY)
if (strchr(mode, 't')) {
flags |= _O_TEXT;
diff --git a/main/streams/streams.c b/main/streams/streams.c
index 823b8859bf..c17570bbeb 100644
--- a/main/streams/streams.c
+++ b/main/streams/streams.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/transports.c b/main/streams/transports.c
index c24bf97ce6..1bf096efb2 100644
--- a/main/streams/transports.c
+++ b/main/streams/transports.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/userspace.c b/main/streams/userspace.c
index 69edbaafa9..b14efdd6a5 100644
--- a/main/streams/userspace.c
+++ b/main/streams/userspace.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/streams/xp_socket.c b/main/streams/xp_socket.c
index a9c050f267..5bbbd78fac 100644
--- a/main/streams/xp_socket.c
+++ b/main/streams/xp_socket.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -426,7 +426,7 @@ static int php_sockop_cast(php_stream *stream, int castas, void **ret TSRMLS_DC)
case PHP_STREAM_AS_FD:
case PHP_STREAM_AS_SOCKETD:
if (ret)
- *(int*)ret = sock->socket;
+ *(php_socket_t *)ret = sock->socket;
return SUCCESS;
default:
return FAILURE;
diff --git a/main/strlcat.c b/main/strlcat.c
index ca22839e86..b7aa06e8a2 100644
--- a/main/strlcat.c
+++ b/main/strlcat.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/strlcpy.c b/main/strlcpy.c
index 371faafd82..7738238bd5 100644
--- a/main/strlcpy.c
+++ b/main/strlcpy.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/win32_internal_function_disabled.h b/main/win32_internal_function_disabled.h
index 80fd8d1b82..7365262772 100644
--- a/main/win32_internal_function_disabled.h
+++ b/main/win32_internal_function_disabled.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/main/win95nt.h b/main/win95nt.h
index 2e944c2b0e..ce2b002f38 100644
--- a/main/win95nt.h
+++ b/main/win95nt.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/makedist b/makedist
index f5823d3925..1b47d7bd82 100755
--- a/makedist
+++ b/makedist
@@ -35,7 +35,7 @@ if test "${1}" = "1" -a "${2}" -lt "28"; then
fi
IFS="$old_IFS"
-if test "$PHPROOTx" == "x"; then
+if test "x$PHPROOT" == "x"; then
PHPROOT=git@git.php.net:php-src.git;
fi
diff --git a/netware/start.c b/netware/start.c
index 8651a6ccca..e0569b1b89 100644
--- a/netware/start.c
+++ b/netware/start.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/php.ini-development b/php.ini-development
index 2ef47a40a2..c125956e02 100644
--- a/php.ini-development
+++ b/php.ini-development
@@ -138,16 +138,6 @@
; Development Value: "GP"
; Production Value: "GP"
-; session.bug_compat_42
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-
-; session.bug_compat_warn
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-
; session.gc_divisor
; Default Value: 100
; Development Value: 1000
@@ -1488,31 +1478,6 @@ session.gc_maxlifetime = 1440
; setting session.gc_maxlifetime to 1440 (1440 seconds = 24 minutes):
; find /path/to/sessions -cmin +24 -type f | xargs rm
-; PHP 4.2 and less have an undocumented feature/bug that allows you to
-; to initialize a session variable in the global scope.
-; PHP 4.3 and later will warn you, if this feature is used.
-; You can disable the feature and the warning separately. At this time,
-; the warning is only displayed, if bug_compat_42 is enabled. This feature
-; introduces some serious security problems if not handled correctly. It's
-; recommended that you do not use this feature on production servers. But you
-; should enable this on development servers and enable the warning as well. If you
-; do not enable the feature on development servers, you won't be warned when it's
-; used and debugging errors caused by this can be difficult to track down.
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-; http://php.net/session.bug-compat-42
-session.bug_compat_42 = On
-
-; This setting controls whether or not you are warned by PHP when initializing a
-; session value into the global space. session.bug_compat_42 must be enabled before
-; these warnings can be issued by PHP. See the directive above for more information.
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-; http://php.net/session.bug-compat-warn
-session.bug_compat_warn = On
-
; Check HTTP Referer to invalidate externally stored URLs containing ids.
; HTTP_REFERER has to contain this substring for the session to be
; considered as valid.
diff --git a/php.ini-production b/php.ini-production
index c39de742db..c5cd462c04 100644
--- a/php.ini-production
+++ b/php.ini-production
@@ -138,16 +138,6 @@
; Development Value: "GP"
; Production Value: "GP"
-; session.bug_compat_42
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-
-; session.bug_compat_warn
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-
; session.gc_divisor
; Default Value: 100
; Development Value: 1000
@@ -1488,31 +1478,6 @@ session.gc_maxlifetime = 1440
; setting session.gc_maxlifetime to 1440 (1440 seconds = 24 minutes):
; find /path/to/sessions -cmin +24 -type f | xargs rm
-; PHP 4.2 and less have an undocumented feature/bug that allows you to
-; to initialize a session variable in the global scope.
-; PHP 4.3 and later will warn you, if this feature is used.
-; You can disable the feature and the warning separately. At this time,
-; the warning is only displayed, if bug_compat_42 is enabled. This feature
-; introduces some serious security problems if not handled correctly. It's
-; recommended that you do not use this feature on production servers. But you
-; should enable this on development servers and enable the warning as well. If you
-; do not enable the feature on development servers, you won't be warned when it's
-; used and debugging errors caused by this can be difficult to track down.
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-; http://php.net/session.bug-compat-42
-session.bug_compat_42 = Off
-
-; This setting controls whether or not you are warned by PHP when initializing a
-; session value into the global space. session.bug_compat_42 must be enabled before
-; these warnings can be issued by PHP. See the directive above for more information.
-; Default Value: On
-; Development Value: On
-; Production Value: Off
-; http://php.net/session.bug-compat-warn
-session.bug_compat_warn = Off
-
; Check HTTP Referer to invalidate externally stored URLs containing ids.
; HTTP_REFERER has to contain this substring for the session to be
; considered as valid.
diff --git a/run-tests.php b/run-tests.php
index 7eb445eeb8..305b48d933 100755
--- a/run-tests.php
+++ b/run-tests.php
@@ -241,6 +241,7 @@ $ini_overwrites = array(
'precision=14',
'memory_limit=128M',
'opcache.fast_shutdown=0',
+ 'opcache.file_update_protection=0',
);
function write_information($show_html)
@@ -580,7 +581,7 @@ if (isset($argc) && $argc > 1) {
if (!$valgrind_header) {
error("Valgrind returned no version info, cannot proceed.\nPlease check if Valgrind is installed.");
} else {
- $valgrind_version = preg_replace("/valgrind-([0-9])\.([0-9])\.([0-9]+)([.-\w]+)?(\s+)/", '$1$2$3', $valgrind_header, 1, $replace_count);
+ $valgrind_version = preg_replace("/valgrind-(\d)\.(\d)\.(\d+)([.\w_-]+)?(\s+)/", '$1$2$3', $valgrind_header, 1, $replace_count);
if ($replace_count != 1 || !is_numeric($valgrind_version)) {
error("Valgrind returned invalid version info (\"$valgrind_header\"), cannot proceed.");
}
@@ -1090,6 +1091,7 @@ function system_with_timeout($commandline, $env = null, $stdin = null)
fwrite($pipes[0], $stdin);
}
fclose($pipes[0]);
+ unset($pipes[0]);
$timeout = $leak_check ? 300 : (isset($env['TEST_TIMEOUT']) ? $env['TEST_TIMEOUT'] : 60);
diff --git a/sapi/aolserver/aolserver.c b/sapi/aolserver/aolserver.c
index 3dcbc8d211..a89b98e57a 100644
--- a/sapi/aolserver/aolserver.c
+++ b/sapi/aolserver/aolserver.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/libpre.c b/sapi/apache/libpre.c
index 35b47cf5df..ca10e34cdd 100644
--- a/sapi/apache/libpre.c
+++ b/sapi/apache/libpre.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/mod_php5.c b/sapi/apache/mod_php5.c
index 8361f7f410..a1e5a70e89 100644
--- a/sapi/apache/mod_php5.c
+++ b/sapi/apache/mod_php5.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/mod_php5.h b/sapi/apache/mod_php5.h
index bdbdd478dd..3bc7857380 100644
--- a/sapi/apache/mod_php5.h
+++ b/sapi/apache/mod_php5.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/php_apache.c b/sapi/apache/php_apache.c
index 3745197439..43a4c90efe 100644
--- a/sapi/apache/php_apache.c
+++ b/sapi/apache/php_apache.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/php_apache_http.h b/sapi/apache/php_apache_http.h
index 12788d304d..a18e5dbac2 100644
--- a/sapi/apache/php_apache_http.h
+++ b/sapi/apache/php_apache_http.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache/sapi_apache.c b/sapi/apache/sapi_apache.c
index 88c99855c6..f19586da1f 100644
--- a/sapi/apache/sapi_apache.c
+++ b/sapi/apache/sapi_apache.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2filter/apache_config.c b/sapi/apache2filter/apache_config.c
index 333c7b8cf2..7c50b9e6a8 100644
--- a/sapi/apache2filter/apache_config.c
+++ b/sapi/apache2filter/apache_config.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2filter/php_apache.h b/sapi/apache2filter/php_apache.h
index 4ee3c0aa90..47fe98b5fd 100644
--- a/sapi/apache2filter/php_apache.h
+++ b/sapi/apache2filter/php_apache.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2filter/php_functions.c b/sapi/apache2filter/php_functions.c
index e96ceda3f1..f1ae9c974b 100644
--- a/sapi/apache2filter/php_functions.c
+++ b/sapi/apache2filter/php_functions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2filter/sapi_apache2.c b/sapi/apache2filter/sapi_apache2.c
index 8ce490ea43..da920f818c 100644
--- a/sapi/apache2filter/sapi_apache2.c
+++ b/sapi/apache2filter/sapi_apache2.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2handler/apache_config.c b/sapi/apache2handler/apache_config.c
index 2b519393d7..76d3ee2264 100644
--- a/sapi/apache2handler/apache_config.c
+++ b/sapi/apache2handler/apache_config.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2handler/mod_php5.c b/sapi/apache2handler/mod_php5.c
index 56ef1bca44..4a01ebfd5f 100644
--- a/sapi/apache2handler/mod_php5.c
+++ b/sapi/apache2handler/mod_php5.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2handler/php_apache.h b/sapi/apache2handler/php_apache.h
index 8bc46089d7..34846048b0 100644
--- a/sapi/apache2handler/php_apache.h
+++ b/sapi/apache2handler/php_apache.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2handler/php_functions.c b/sapi/apache2handler/php_functions.c
index 1f79a538f4..2c57300926 100644
--- a/sapi/apache2handler/php_functions.c
+++ b/sapi/apache2handler/php_functions.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache2handler/sapi_apache2.c b/sapi/apache2handler/sapi_apache2.c
index b7f95e0c12..d2b3a327ff 100644
--- a/sapi/apache2handler/sapi_apache2.c
+++ b/sapi/apache2handler/sapi_apache2.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache_hooks/mod_php5.c b/sapi/apache_hooks/mod_php5.c
index 66adb482ed..a069e324c1 100644
--- a/sapi/apache_hooks/mod_php5.c
+++ b/sapi/apache_hooks/mod_php5.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache_hooks/mod_php5.h b/sapi/apache_hooks/mod_php5.h
index 86a5863ab9..3db828ec83 100644
--- a/sapi/apache_hooks/mod_php5.h
+++ b/sapi/apache_hooks/mod_php5.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache_hooks/php_apache.c b/sapi/apache_hooks/php_apache.c
index dde6d88773..6531ca20ee 100644
--- a/sapi/apache_hooks/php_apache.c
+++ b/sapi/apache_hooks/php_apache.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/apache_hooks/sapi_apache.c b/sapi/apache_hooks/sapi_apache.c
index a9c9d674e0..9ed93aea6d 100644
--- a/sapi/apache_hooks/sapi_apache.c
+++ b/sapi/apache_hooks/sapi_apache.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/caudium/caudium.c b/sapi/caudium/caudium.c
index d3b834fe93..e707f3576e 100644
--- a/sapi/caudium/caudium.c
+++ b/sapi/caudium/caudium.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cgi/cgi_main.c b/sapi/cgi/cgi_main.c
index 4c78fcafec..b1e12f7324 100644
--- a/sapi/cgi/cgi_main.c
+++ b/sapi/cgi/cgi_main.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1688,8 +1688,8 @@ static void add_response_header(sapi_header_struct *h, zval *return_value TSRMLS
PHP_FUNCTION(apache_response_headers) /* {{{ */
{
- if (ZEND_NUM_ARGS() > 0) {
- WRONG_PARAM_COUNT;
+ if (zend_parse_parameters_none() == FAILURE) {
+ return;
}
if (!&SG(sapi_headers).headers) {
@@ -2223,9 +2223,9 @@ consult the installation file that came with this distribution, or visit \n\
SG(request_info).no_headers = 1;
}
#if ZEND_DEBUG
- php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#else
- php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#endif
php_request_shutdown((void *) 0);
fcgi_shutdown();
diff --git a/sapi/cgi/fastcgi.c b/sapi/cgi/fastcgi.c
index 72977b6330..8ddc2e4577 100644
--- a/sapi/cgi/fastcgi.c
+++ b/sapi/cgi/fastcgi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cgi/fastcgi.h b/sapi/cgi/fastcgi.h
index f1f464dc05..702f51df6b 100644
--- a/sapi/cgi/fastcgi.h
+++ b/sapi/cgi/fastcgi.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/cli.h b/sapi/cli/cli.h
index 7686522a20..dc85893a0b 100644
--- a/sapi/cli/cli.h
+++ b/sapi/cli/cli.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/php.1.in b/sapi/cli/php.1.in
index c113030d14..8672b3ba33 100644
--- a/sapi/cli/php.1.in
+++ b/sapi/cli/php.1.in
@@ -178,15 +178,6 @@ Parse and execute
.IR file
.TP
.PD 0
-.B \-\-global \fIname\fP
-.TP
-.PD 1
-.B \-g \fIname\fP
-Make variable
-.IR name
-global in script.
-.TP
-.PD 0
.B \-\-help
.TP
.PD 1
@@ -298,7 +289,7 @@ Specify the document root to be used by the built-in web server
Version number
.TP
.PD 0
-.B \-\-stripped
+.B \-\-strip
.TP
.PD 1
.B \-w
diff --git a/sapi/cli/php_cli.c b/sapi/cli/php_cli.c
index 9f3fc4b5b7..9daa382eec 100644
--- a/sapi/cli/php_cli.c
+++ b/sapi/cli/php_cli.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -693,7 +693,7 @@ static int do_cli(int argc, char **argv TSRMLS_DC) /* {{{ */
goto out;
case 'v': /* show php version & quit */
- php_printf("PHP %s (%s) (built: %s %s) %s\nCopyright (c) 1997-2013 The PHP Group\n%s",
+ php_printf("PHP %s (%s) (built: %s %s) %s\nCopyright (c) 1997-2014 The PHP Group\n%s",
PHP_VERSION, cli_sapi_module.name, __DATE__, __TIME__,
#if ZEND_DEBUG && defined(HAVE_GCOV)
"(DEBUG GCOV)",
diff --git a/sapi/cli/php_cli_process_title.c b/sapi/cli/php_cli_process_title.c
index c50c412b1f..dec5613670 100644
--- a/sapi/cli/php_cli_process_title.c
+++ b/sapi/cli/php_cli_process_title.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/php_cli_process_title.h b/sapi/cli/php_cli_process_title.h
index b4b0861a2a..bd44d99111 100644
--- a/sapi/cli/php_cli_process_title.h
+++ b/sapi/cli/php_cli_process_title.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/php_cli_server.c b/sapi/cli/php_cli_server.c
index 1315a62b87..a993d65bc6 100644
--- a/sapi/cli/php_cli_server.c
+++ b/sapi/cli/php_cli_server.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -133,6 +133,7 @@ typedef struct php_cli_server_request {
char *query_string;
size_t query_string_len;
HashTable headers;
+ HashTable headers_original_case;
char *content;
size_t content_len;
const char *ext;
@@ -275,6 +276,42 @@ static php_cli_server_ext_mime_type_pair mime_type_map[] = {
{ "webm", "video/webm" },
{ "ogv", "video/ogg" },
{ "ogg", "audio/ogg" },
+ { "3gp", "video/3gpp" }, /* This is standard video format used for MMS in phones */
+ { "apk", "application/vnd.android.package-archive" },
+ { "avi", "video/x-msvideo" },
+ { "bmp", "image/x-ms-bmp" },
+ { "csv", "text/comma-separated-values" },
+ { "doc", "application/msword" },
+ { "docx", "application/msword" },
+ { "flac", "audio/flac" },
+ { "gz", "application/x-gzip" },
+ { "gzip", "application/x-gzip" },
+ { "ics", "text/calendar" },
+ { "kml", "application/vnd.google-earth.kml+xml" },
+ { "kmz", "application/vnd.google-earth.kmz" },
+ { "m4a", "audio/mp4" },
+ { "mp3", "audio/mpeg" },
+ { "mp4", "video/mp4" },
+ { "mpg", "video/mpeg" },
+ { "mpeg", "video/mpeg" },
+ { "mov", "video/quicktime" },
+ { "odp", "application/vnd.oasis.opendocument.presentation" },
+ { "ods", "application/vnd.oasis.opendocument.spreadsheet" },
+ { "odt", "application/vnd.oasis.opendocument.text" },
+ { "oga", "audio/ogg" },
+ { "pdf", "application/pdf" },
+ { "pptx", "application/vnd.ms-powerpoint" },
+ { "pps", "application/vnd.ms-powerpoint" },
+ { "qt", "video/quicktime" },
+ { "swf", "application/x-shockwave-flash" },
+ { "tar", "application/x-tar" },
+ { "text", "text/plain" },
+ { "tif", "image/tiff" },
+ { "wav", "audio/wav" },
+ { "wmv", "video/x-ms-wmv" },
+ { "xls", "application/vnd.ms-excel" },
+ { "xlsx", "application/vnd.ms-excel" },
+ { "zip", "application/x-zip-compressed" },
{ NULL, NULL }
};
@@ -435,6 +472,75 @@ static const char *get_mime_type(const char *ext, size_t ext_len) /* {{{ */
return NULL;
} /* }}} */
+PHP_FUNCTION(apache_request_headers) /* {{{ */
+{
+ php_cli_server_client *client;
+ HashTable *headers;
+ char *key;
+ uint key_len;
+ char **value_pointer;
+ HashPosition pos;
+
+ if (zend_parse_parameters_none() == FAILURE) {
+ return;
+ }
+
+ client = SG(server_context);
+ headers = &client->request.headers_original_case;
+
+ array_init_size(return_value, zend_hash_num_elements(headers));
+
+ zend_hash_internal_pointer_reset_ex(headers, &pos);
+ while (zend_hash_get_current_data_ex(headers, (void **)&value_pointer, &pos) == SUCCESS) {
+ zend_hash_get_current_key_ex(headers, &key, &key_len, NULL, 0, &pos);
+ add_assoc_string_ex(return_value, key, key_len, *value_pointer, 1);
+ zend_hash_move_forward_ex(headers, &pos);
+ }
+}
+/* }}} */
+
+static void add_response_header(sapi_header_struct *h, zval *return_value TSRMLS_DC) /* {{{ */
+{
+ char *s, *p;
+ int len;
+ ALLOCA_FLAG(use_heap)
+
+ if (h->header_len > 0) {
+ p = strchr(h->header, ':');
+ len = p - h->header;
+ if (p && (len > 0)) {
+ while (len > 0 && (h->header[len-1] == ' ' || h->header[len-1] == '\t')) {
+ len--;
+ }
+ if (len) {
+ s = do_alloca(len + 1, use_heap);
+ memcpy(s, h->header, len);
+ s[len] = 0;
+ do {
+ p++;
+ } while (*p == ' ' || *p == '\t');
+ add_assoc_stringl_ex(return_value, s, len+1, p, h->header_len - (p - h->header), 1);
+ free_alloca(s, use_heap);
+ }
+ }
+ }
+}
+/* }}} */
+
+PHP_FUNCTION(apache_response_headers) /* {{{ */
+{
+ if (zend_parse_parameters_none() == FAILURE) {
+ return;
+ }
+
+ if (!&SG(sapi_headers).headers) {
+ RETURN_FALSE;
+ }
+ array_init(return_value);
+ zend_llist_apply_with_argument(&SG(sapi_headers).headers, (llist_apply_with_arg_func_t)add_response_header, return_value TSRMLS_CC);
+}
+/* }}} */
+
/* {{{ cli_server module
*/
@@ -479,9 +585,15 @@ zend_module_entry cli_server_module_entry = {
};
/* }}} */
+ZEND_BEGIN_ARG_INFO(arginfo_no_args, 0)
+ZEND_END_ARG_INFO()
+
const zend_function_entry server_additional_functions[] = {
PHP_FE(cli_set_process_title, arginfo_cli_set_process_title)
PHP_FE(cli_get_process_title, arginfo_cli_get_process_title)
+ PHP_FE(apache_request_headers, arginfo_no_args)
+ PHP_FE(apache_response_headers, arginfo_no_args)
+ PHP_FALIAS(getallheaders, apache_request_headers, arginfo_no_args)
{NULL, NULL, NULL}
};
@@ -1300,6 +1412,7 @@ static int php_cli_server_request_ctor(php_cli_server_request *req) /* {{{ */
req->query_string = NULL;
req->query_string_len = 0;
zend_hash_init(&req->headers, 0, NULL, (void(*)(void*))char_ptr_dtor_p, 1);
+ zend_hash_init(&req->headers_original_case, 0, NULL, NULL, 1);
req->content = NULL;
req->content_len = 0;
req->ext = NULL;
@@ -1325,6 +1438,7 @@ static void php_cli_server_request_dtor(php_cli_server_request *req) /* {{{ */
pefree(req->query_string, 1);
}
zend_hash_destroy(&req->headers);
+ zend_hash_destroy(&req->headers_original_case);
if (req->content) {
pefree(req->content, 1);
}
@@ -1569,6 +1683,7 @@ static int php_cli_server_client_read_request_on_header_value(php_http_parser *p
{
char *header_name = zend_str_tolower_dup(client->current_header_name, client->current_header_name_len);
zend_hash_add(&client->request.headers, header_name, client->current_header_name_len + 1, &value, sizeof(char *), NULL);
+ zend_hash_add(&client->request.headers_original_case, client->current_header_name, client->current_header_name_len + 1, &value, sizeof(char *), NULL);
efree(header_name);
}
diff --git a/sapi/cli/php_cli_server.h b/sapi/cli/php_cli_server.h
index 9a29626c7f..a8d7f46e7c 100644
--- a/sapi/cli/php_cli_server.h
+++ b/sapi/cli/php_cli_server.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/ps_title.c b/sapi/cli/ps_title.c
index 6f3bdb862d..53cd5fc9a0 100644
--- a/sapi/cli/ps_title.c
+++ b/sapi/cli/ps_title.c
@@ -4,7 +4,7 @@
* PostgreSQL Database Management System (formerly known as Postgres, then as
* Postgres95)
*
- * Portions Copyright (c) 1996-2013, The PostgreSQL Global Development Group
+ * Portions Copyright (c) 1996-2014, The PostgreSQL Global Development Group
*
* Portions Copyright (c) 1994, The Regents of the University of California
*
diff --git a/sapi/cli/ps_title.h b/sapi/cli/ps_title.h
index 5623653e48..09650fed08 100644
--- a/sapi/cli/ps_title.h
+++ b/sapi/cli/ps_title.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/cli/tests/php_cli_server_019.phpt b/sapi/cli/tests/php_cli_server_019.phpt
new file mode 100644
index 0000000000..2b983e5c0a
--- /dev/null
+++ b/sapi/cli/tests/php_cli_server_019.phpt
@@ -0,0 +1,68 @@
+--TEST--
+Implement Req #65917 (getallheaders() is not supported by the built-in web server)
+--SKIPIF--
+<?php
+include "skipif.inc";
+?>
+--FILE--
+<?php
+include "php_cli_server.inc";
+php_cli_server_start(<<<'PHP'
+header('Bar-Foo: Foo');
+var_dump(getallheaders());
+var_dump(apache_request_headers());
+var_dump(apache_response_headers());
+PHP
+);
+
+list($host, $port) = explode(':', PHP_CLI_SERVER_ADDRESS);
+$port = intval($port)?:80;
+
+$fp = fsockopen($host, $port, $errno, $errstr, 0.5);
+if (!$fp) {
+ die("connect failed");
+}
+
+if(fwrite($fp, <<<HEADER
+GET / HTTP/1.1
+Host: {$host}
+Foo-Bar: Bar
+
+
+HEADER
+)) {
+ while (!feof($fp)) {
+ echo fgets($fp);
+ }
+}
+
+fclose($fp);
+?>
+--EXPECTF--
+HTTP/1.1 200 OK
+Host: %s
+Connection: close
+X-Powered-By: %s
+Bar-Foo: Foo
+Content-type: text/html
+
+array(2) {
+ ["Host"]=>
+ string(9) "localhost"
+ ["Foo-Bar"]=>
+ string(3) "Bar"
+}
+array(2) {
+ ["Host"]=>
+ string(9) "localhost"
+ ["Foo-Bar"]=>
+ string(3) "Bar"
+}
+array(3) {
+ ["X-Powered-By"]=>
+ string(%d) "P%s"
+ ["Bar-Foo"]=>
+ string(3) "Foo"
+ ["Content-type"]=>
+ string(9) "text/html"
+}
diff --git a/sapi/continuity/capi.c b/sapi/continuity/capi.c
index 26762a5a96..953991474d 100644
--- a/sapi/continuity/capi.c
+++ b/sapi/continuity/capi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/embed/php_embed.c b/sapi/embed/php_embed.c
index 414b4dbb02..dad54de1ae 100644
--- a/sapi/embed/php_embed.c
+++ b/sapi/embed/php_embed.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/embed/php_embed.h b/sapi/embed/php_embed.h
index ad5f4bc476..84c0e36336 100644
--- a/sapi/embed/php_embed.h
+++ b/sapi/embed/php_embed.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/devpoll.c b/sapi/fpm/fpm/events/devpoll.c
index 223d0729c8..3fa7cd4545 100644
--- a/sapi/fpm/fpm/events/devpoll.c
+++ b/sapi/fpm/fpm/events/devpoll.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/devpoll.h b/sapi/fpm/fpm/events/devpoll.h
index f9bc4af194..2753cb5abe 100644
--- a/sapi/fpm/fpm/events/devpoll.h
+++ b/sapi/fpm/fpm/events/devpoll.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/epoll.c b/sapi/fpm/fpm/events/epoll.c
index c9c7f1fd6d..2857ea2a09 100644
--- a/sapi/fpm/fpm/events/epoll.c
+++ b/sapi/fpm/fpm/events/epoll.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/epoll.h b/sapi/fpm/fpm/events/epoll.h
index abc5a21b10..f89e59a5f5 100644
--- a/sapi/fpm/fpm/events/epoll.h
+++ b/sapi/fpm/fpm/events/epoll.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/kqueue.c b/sapi/fpm/fpm/events/kqueue.c
index 7ce0760691..9fde33842b 100644
--- a/sapi/fpm/fpm/events/kqueue.c
+++ b/sapi/fpm/fpm/events/kqueue.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/kqueue.h b/sapi/fpm/fpm/events/kqueue.h
index 2642acaae5..16f8046529 100644
--- a/sapi/fpm/fpm/events/kqueue.h
+++ b/sapi/fpm/fpm/events/kqueue.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/poll.c b/sapi/fpm/fpm/events/poll.c
index 185eceb1a9..d49661413c 100644
--- a/sapi/fpm/fpm/events/poll.c
+++ b/sapi/fpm/fpm/events/poll.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/poll.h b/sapi/fpm/fpm/events/poll.h
index d55319214c..4a05755d07 100644
--- a/sapi/fpm/fpm/events/poll.h
+++ b/sapi/fpm/fpm/events/poll.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/port.c b/sapi/fpm/fpm/events/port.c
index 3cbf092cbc..0e6a880554 100644
--- a/sapi/fpm/fpm/events/port.c
+++ b/sapi/fpm/fpm/events/port.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/port.h b/sapi/fpm/fpm/events/port.h
index 666a157d23..f127b8cdad 100644
--- a/sapi/fpm/fpm/events/port.h
+++ b/sapi/fpm/fpm/events/port.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/select.c b/sapi/fpm/fpm/events/select.c
index e3af067d86..cf3331c04b 100644
--- a/sapi/fpm/fpm/events/select.c
+++ b/sapi/fpm/fpm/events/select.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/events/select.h b/sapi/fpm/fpm/events/select.h
index db52503fc1..74f7be2bc1 100644
--- a/sapi/fpm/fpm/events/select.h
+++ b/sapi/fpm/fpm/events/select.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/fastcgi.c b/sapi/fpm/fpm/fastcgi.c
index ec579eadf6..d77b6f8ca7 100644
--- a/sapi/fpm/fpm/fastcgi.c
+++ b/sapi/fpm/fpm/fastcgi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/fastcgi.h b/sapi/fpm/fpm/fastcgi.h
index ee786752e8..34f9eef9da 100644
--- a/sapi/fpm/fpm/fastcgi.h
+++ b/sapi/fpm/fpm/fastcgi.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/fpm/fpm/fpm_conf.c b/sapi/fpm/fpm/fpm_conf.c
index cd5fc34d0f..688c640250 100644
--- a/sapi/fpm/fpm/fpm_conf.c
+++ b/sapi/fpm/fpm/fpm_conf.c
@@ -148,6 +148,7 @@ static struct ini_value_parser_s ini_fpm_pool_options[] = {
{ "chroot", &fpm_conf_set_string, WPO(chroot) },
{ "chdir", &fpm_conf_set_string, WPO(chdir) },
{ "catch_workers_output", &fpm_conf_set_boolean, WPO(catch_workers_output) },
+ { "clear_env", &fpm_conf_set_boolean, WPO(clear_env) },
{ "security.limit_extensions", &fpm_conf_set_string, WPO(security_limit_extensions) },
{ 0, 0, 0 }
};
@@ -603,6 +604,7 @@ static void *fpm_worker_pool_config_alloc() /* {{{ */
wp->config->listen_backlog = FPM_BACKLOG_DEFAULT;
wp->config->pm_process_idle_timeout = 10; /* 10s by default */
wp->config->process_priority = 64; /* 64 means unset */
+ wp->config->clear_env = 1;
if (!fpm_worker_all_pools) {
fpm_worker_all_pools = wp;
@@ -1600,6 +1602,7 @@ static void fpm_conf_dump() /* {{{ */
zlog(ZLOG_NOTICE, "\tchroot = %s", STR2STR(wp->config->chroot));
zlog(ZLOG_NOTICE, "\tchdir = %s", STR2STR(wp->config->chdir));
zlog(ZLOG_NOTICE, "\tcatch_workers_output = %s", BOOL2STR(wp->config->catch_workers_output));
+ zlog(ZLOG_NOTICE, "\tclear_env = %s", BOOL2STR(wp->config->clear_env));
zlog(ZLOG_NOTICE, "\tsecurity.limit_extensions = %s", wp->config->security_limit_extensions);
for (kv = wp->config->env; kv; kv = kv->next) {
diff --git a/sapi/fpm/fpm/fpm_conf.h b/sapi/fpm/fpm/fpm_conf.h
index efd65dc6d9..19bd7ff1f8 100644
--- a/sapi/fpm/fpm/fpm_conf.h
+++ b/sapi/fpm/fpm/fpm_conf.h
@@ -83,6 +83,7 @@ struct fpm_worker_pool_config_s {
char *chroot;
char *chdir;
int catch_workers_output;
+ int clear_env;
char *security_limit_extensions;
struct key_value_s *env;
struct key_value_s *php_admin_values;
diff --git a/sapi/fpm/fpm/fpm_env.c b/sapi/fpm/fpm/fpm_env.c
index 6b64fedfec..2ff0bdc0e4 100644
--- a/sapi/fpm/fpm/fpm_env.c
+++ b/sapi/fpm/fpm/fpm_env.c
@@ -143,7 +143,9 @@ int fpm_env_init_child(struct fpm_worker_pool_s *wp) /* {{{ */
fpm_env_setproctitle(title);
efree(title);
- clearenv();
+ if (wp->config->clear_env) {
+ clearenv();
+ }
for (kv = wp->config->env; kv; kv = kv->next) {
setenv(kv->key, kv->value, 1);
diff --git a/sapi/fpm/fpm/fpm_main.c b/sapi/fpm/fpm/fpm_main.c
index 043e0e00a4..e8793259b4 100644
--- a/sapi/fpm/fpm/fpm_main.c
+++ b/sapi/fpm/fpm/fpm_main.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1721,9 +1721,9 @@ int main(int argc, char *argv[])
SG(request_info).no_headers = 1;
#if ZEND_DEBUG
- php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#else
- php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#endif
php_request_shutdown((void *) 0);
fcgi_shutdown();
diff --git a/sapi/fpm/php-fpm.conf.in b/sapi/fpm/php-fpm.conf.in
index 9002a2933b..ab03736beb 100644
--- a/sapi/fpm/php-fpm.conf.in
+++ b/sapi/fpm/php-fpm.conf.in
@@ -475,6 +475,15 @@ pm.max_spare_servers = 3
; Default Value: no
;catch_workers_output = yes
+; Clear environment in FPM workers
+; Prevents arbitrary environment variables from reaching FPM worker processes
+; by clearing the environment in workers before env vars specified in this
+; pool configuration are added.
+; Setting to "no" will make all environment variables available to PHP code
+; via getenv(), $_ENV and $_SERVER.
+; Default Value: yes
+;clear_env = no
+
; Limits the extensions of the main script FPM will allow to parse. This can
; prevent configuration mistakes on the web server side. You should only limit
; FPM to .php extensions to prevent malicious users to use other extensions to
diff --git a/sapi/isapi/php5isapi.c b/sapi/isapi/php5isapi.c
index 002ad2ae3e..d83c81ad9e 100644
--- a/sapi/isapi/php5isapi.c
+++ b/sapi/isapi/php5isapi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/litespeed/lsapi_main.c b/sapi/litespeed/lsapi_main.c
index 19364c66e0..52c39f1b6c 100644
--- a/sapi/litespeed/lsapi_main.c
+++ b/sapi/litespeed/lsapi_main.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -547,9 +547,9 @@ static int cli_main( int argc, char * argv[] )
case 'v':
if (php_request_startup(TSRMLS_C) != FAILURE) {
#if ZEND_DEBUG
- php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s) (DEBUG)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#else
- php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
#endif
#ifdef PHP_OUTPUT_NEWAPI
php_output_end_all(TSRMLS_C);
diff --git a/sapi/litespeed/lsapidef.h b/sapi/litespeed/lsapidef.h
index c8940a930e..3bdadac1d1 100644
--- a/sapi/litespeed/lsapidef.h
+++ b/sapi/litespeed/lsapidef.h
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/litespeed/lsapilib.c b/sapi/litespeed/lsapilib.c
index 3a13000e11..24b5a7e559 100644
--- a/sapi/litespeed/lsapilib.c
+++ b/sapi/litespeed/lsapilib.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/litespeed/lsapilib.h b/sapi/litespeed/lsapilib.h
index 538a170b44..9d6255b327 100644
--- a/sapi/litespeed/lsapilib.h
+++ b/sapi/litespeed/lsapilib.h
@@ -3,7 +3,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/milter/php_milter.c b/sapi/milter/php_milter.c
index 6856c07bb6..432fd806c2 100644
--- a/sapi/milter/php_milter.c
+++ b/sapi/milter/php_milter.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
@@ -1109,7 +1109,7 @@ int main(int argc, char *argv[])
}
SG(headers_sent) = 1;
SG(request_info).no_headers = 1;
- php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2013 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
+ php_printf("PHP %s (%s) (built: %s %s)\nCopyright (c) 1997-2014 The PHP Group\n%s", PHP_VERSION, sapi_module.name, __DATE__, __TIME__, get_zend_version());
php_output_teardown();
exit(1);
break;
diff --git a/sapi/nsapi/nsapi.c b/sapi/nsapi/nsapi.c
index 1e6a680c91..ec3137ca51 100644
--- a/sapi/nsapi/nsapi.c
+++ b/sapi/nsapi/nsapi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/phttpd/php_phttpd.h b/sapi/phttpd/php_phttpd.h
index 49089cffbf..92409ac905 100644
--- a/sapi/phttpd/php_phttpd.h
+++ b/sapi/phttpd/php_phttpd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/phttpd/phttpd.c b/sapi/phttpd/phttpd.c
index c2e917202f..60fc48ba35 100644
--- a/sapi/phttpd/phttpd.c
+++ b/sapi/phttpd/phttpd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/pi3web/pi3web_sapi.c b/sapi/pi3web/pi3web_sapi.c
index 64eb2a6c99..4bc08e5382 100644
--- a/sapi/pi3web/pi3web_sapi.c
+++ b/sapi/pi3web/pi3web_sapi.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/roxen/roxen.c b/sapi/roxen/roxen.c
index c897ef62be..b3a64345ea 100644
--- a/sapi/roxen/roxen.c
+++ b/sapi/roxen/roxen.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/thttpd/php_thttpd.h b/sapi/thttpd/php_thttpd.h
index 40d63d27b1..75e79b4054 100644
--- a/sapi/thttpd/php_thttpd.h
+++ b/sapi/thttpd/php_thttpd.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/thttpd/thttpd.c b/sapi/thttpd/thttpd.c
index 548bcda170..843e4a62fb 100644
--- a/sapi/thttpd/thttpd.c
+++ b/sapi/thttpd/thttpd.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/tux/php_tux.c b/sapi/tux/php_tux.c
index 968dd9eb91..55d911f8ab 100644
--- a/sapi/tux/php_tux.c
+++ b/sapi/tux/php_tux.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/webjames/php_webjames.h b/sapi/webjames/php_webjames.h
index f9903d1647..dcb6cdb911 100644
--- a/sapi/webjames/php_webjames.h
+++ b/sapi/webjames/php_webjames.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/sapi/webjames/webjames.c b/sapi/webjames/webjames.c
index 9237ac7dd3..264f910af4 100644
--- a/sapi/webjames/webjames.c
+++ b/sapi/webjames/webjames.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/tests/classes/autoload_021.phpt b/tests/classes/autoload_021.phpt
new file mode 100644
index 0000000000..13562b4000
--- /dev/null
+++ b/tests/classes/autoload_021.phpt
@@ -0,0 +1,13 @@
+--TEST--
+Validation of class names in the autoload process
+--FILE--
+<?php
+function __autoload($name) {
+ echo "$name\n";
+}
+$a = "../BUG";
+$x = new $a;
+echo "BUG\n";
+?>
+--EXPECTF--
+Fatal error: Class '../BUG' not found in %sautoload_021.php on line 6
diff --git a/tests/classes/bug65768.phpt b/tests/classes/bug65768.phpt
new file mode 100644
index 0000000000..17ec93cf24
--- /dev/null
+++ b/tests/classes/bug65768.phpt
@@ -0,0 +1,36 @@
+--TEST--
+Bug #65768: date_diff accepts only DateTime instance even though docs say about DateTimeInterface
+--INI--
+date.timezone=Europe/London
+--FILE--
+<?php
+
+$dt1 = new DateTime("2010-10-20");
+$dti1 = new DateTimeImmutable("2010-10-25");
+$dti2 = new DateTimeImmutable("2010-10-28");
+
+$diff1 = $dt1->diff($dti1);
+echo $diff1->y, " ", $diff1->m, " ", $diff1->d, " ",
+ $diff1->h, " ", $diff1->i, " ", $diff1->s, "\n";
+
+$diff2 = $dti1->diff($dti2);
+echo $diff2->y, " ", $diff2->m, " ", $diff2->d, " ",
+ $diff2->h, " ", $diff2->i, " ", $diff2->s, "\n";
+
+$diff3 = date_diff($dt1, $dti2);
+echo $diff3->y, " ", $diff3->m, " ", $diff3->d, " ",
+ $diff3->h, " ", $diff3->i, " ", $diff3->s, "\n";
+
+class cdt1 extends DateTime implements DateTimeInterface {}
+
+class cdt2 extends DateTimeImmutable implements DateTimeInterface {}
+
+class cdt3 implements DateTimeInterface {}
+
+?>
+--EXPECTF--
+0 0 5 0 0 0
+0 0 3 0 0 0
+0 0 8 0 0 0
+
+Fatal error: DateTimeInterface can't be implemented by user classes in %sbug65768.php on line %d
diff --git a/tests/lang/bug24640.phpt b/tests/lang/bug24640.phpt
index e41d0201b7..d02889101e 100644
--- a/tests/lang/bug24640.phpt
+++ b/tests/lang/bug24640.phpt
@@ -2,6 +2,7 @@
Bug #24640 (var_export and var_dump can't output large float)
--INI--
precision=12
+serialize_precision=17
--FILE--
<?php
function test($v)
diff --git a/tests/lang/operators/bitwiseShiftLeft_variationStr.phpt b/tests/lang/operators/bitwiseShiftLeft_variationStr.phpt
index b1bc437b0f..e13fc3bc1b 100644
--- a/tests/lang/operators/bitwiseShiftLeft_variationStr.phpt
+++ b/tests/lang/operators/bitwiseShiftLeft_variationStr.phpt
@@ -1,421 +1,421 @@
---TEST--
-Test << operator : various numbers as strings
---SKIPIF--
-<?php
-if (PHP_INT_SIZE != 4) die("skip this test is for 32bit platform only");
-?>
---FILE--
-<?php
-
-$strVals = array(
- "0","65","-44", "1.2", "-7.7", "abc", "123abc", "123e5", "123e5xyz", " 123abc", "123 abc", "123abc ", "3.4a",
- "a5.9"
-);
-
-error_reporting(E_ERROR);
-
-foreach ($strVals as $strVal) {
- foreach($strVals as $otherVal) {
- echo "--- testing: '$strVal' << '$otherVal' ---\n";
- var_dump(bin2hex($strVal<<$otherVal));
- }
-}
-
-
-?>
-===DONE===
---EXPECT--
---- testing: '0' << '0' ---
-string(2) "30"
---- testing: '0' << '65' ---
-string(2) "30"
---- testing: '0' << '-44' ---
-string(2) "30"
---- testing: '0' << '1.2' ---
-string(2) "30"
---- testing: '0' << '-7.7' ---
-string(2) "30"
---- testing: '0' << 'abc' ---
-string(2) "30"
---- testing: '0' << '123abc' ---
-string(2) "30"
---- testing: '0' << '123e5' ---
-string(2) "30"
---- testing: '0' << '123e5xyz' ---
-string(2) "30"
---- testing: '0' << ' 123abc' ---
-string(2) "30"
---- testing: '0' << '123 abc' ---
-string(2) "30"
---- testing: '0' << '123abc ' ---
-string(2) "30"
---- testing: '0' << '3.4a' ---
-string(2) "30"
---- testing: '0' << 'a5.9' ---
-string(2) "30"
---- testing: '65' << '0' ---
-string(4) "3635"
---- testing: '65' << '65' ---
-string(6) "313330"
---- testing: '65' << '-44' ---
-string(16) "3638313537343430"
---- testing: '65' << '1.2' ---
-string(6) "313330"
---- testing: '65' << '-7.7' ---
-string(22) "2d32313133393239323136"
---- testing: '65' << 'abc' ---
-string(4) "3635"
---- testing: '65' << '123abc' ---
-string(18) "313334323137373238"
---- testing: '65' << '123e5' ---
-string(18) "313334323137373238"
---- testing: '65' << '123e5xyz' ---
-string(18) "313334323137373238"
---- testing: '65' << ' 123abc' ---
-string(18) "313334323137373238"
---- testing: '65' << '123 abc' ---
-string(18) "313334323137373238"
---- testing: '65' << '123abc ' ---
-string(18) "313334323137373238"
---- testing: '65' << '3.4a' ---
-string(6) "353230"
---- testing: '65' << 'a5.9' ---
-string(4) "3635"
---- testing: '-44' << '0' ---
-string(6) "2d3434"
---- testing: '-44' << '65' ---
-string(6) "2d3838"
---- testing: '-44' << '-44' ---
-string(18) "2d3436313337333434"
---- testing: '-44' << '1.2' ---
-string(6) "2d3838"
---- testing: '-44' << '-7.7' ---
-string(22) "2d31343736333935303038"
---- testing: '-44' << 'abc' ---
-string(6) "2d3434"
---- testing: '-44' << '123abc' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << '123e5' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << '123e5xyz' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << ' 123abc' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << '123 abc' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << '123abc ' ---
-string(22) "2d31363130363132373336"
---- testing: '-44' << '3.4a' ---
-string(8) "2d333532"
---- testing: '-44' << 'a5.9' ---
-string(6) "2d3434"
---- testing: '1.2' << '0' ---
-string(2) "31"
---- testing: '1.2' << '65' ---
-string(2) "32"
---- testing: '1.2' << '-44' ---
-string(14) "31303438353736"
---- testing: '1.2' << '1.2' ---
-string(2) "32"
---- testing: '1.2' << '-7.7' ---
-string(16) "3333353534343332"
---- testing: '1.2' << 'abc' ---
-string(2) "31"
---- testing: '1.2' << '123abc' ---
-string(18) "313334323137373238"
---- testing: '1.2' << '123e5' ---
-string(18) "313334323137373238"
---- testing: '1.2' << '123e5xyz' ---
-string(18) "313334323137373238"
---- testing: '1.2' << ' 123abc' ---
-string(18) "313334323137373238"
---- testing: '1.2' << '123 abc' ---
-string(18) "313334323137373238"
---- testing: '1.2' << '123abc ' ---
-string(18) "313334323137373238"
---- testing: '1.2' << '3.4a' ---
-string(2) "38"
---- testing: '1.2' << 'a5.9' ---
-string(2) "31"
---- testing: '-7.7' << '0' ---
-string(4) "2d37"
---- testing: '-7.7' << '65' ---
-string(6) "2d3134"
---- testing: '-7.7' << '-44' ---
-string(16) "2d37333430303332"
---- testing: '-7.7' << '1.2' ---
-string(6) "2d3134"
---- testing: '-7.7' << '-7.7' ---
-string(20) "2d323334383831303234"
---- testing: '-7.7' << 'abc' ---
-string(4) "2d37"
---- testing: '-7.7' << '123abc' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << '123e5' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << '123e5xyz' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << ' 123abc' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << '123 abc' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << '123abc ' ---
-string(20) "2d393339353234303936"
---- testing: '-7.7' << '3.4a' ---
-string(6) "2d3536"
---- testing: '-7.7' << 'a5.9' ---
-string(4) "2d37"
---- testing: 'abc' << '0' ---
-string(2) "30"
---- testing: 'abc' << '65' ---
-string(2) "30"
---- testing: 'abc' << '-44' ---
-string(2) "30"
---- testing: 'abc' << '1.2' ---
-string(2) "30"
---- testing: 'abc' << '-7.7' ---
-string(2) "30"
---- testing: 'abc' << 'abc' ---
-string(2) "30"
---- testing: 'abc' << '123abc' ---
-string(2) "30"
---- testing: 'abc' << '123e5' ---
-string(2) "30"
---- testing: 'abc' << '123e5xyz' ---
-string(2) "30"
---- testing: 'abc' << ' 123abc' ---
-string(2) "30"
---- testing: 'abc' << '123 abc' ---
-string(2) "30"
---- testing: 'abc' << '123abc ' ---
-string(2) "30"
---- testing: 'abc' << '3.4a' ---
-string(2) "30"
---- testing: 'abc' << 'a5.9' ---
-string(2) "30"
---- testing: '123abc' << '0' ---
-string(6) "313233"
---- testing: '123abc' << '65' ---
-string(6) "323436"
---- testing: '123abc' << '-44' ---
-string(18) "313238393734383438"
---- testing: '123abc' << '1.2' ---
-string(6) "323436"
---- testing: '123abc' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: '123abc' << 'abc' ---
-string(6) "313233"
---- testing: '123abc' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: '123abc' << '3.4a' ---
-string(6) "393834"
---- testing: '123abc' << 'a5.9' ---
-string(6) "313233"
---- testing: '123e5' << '0' ---
-string(6) "313233"
---- testing: '123e5' << '65' ---
-string(6) "323436"
---- testing: '123e5' << '-44' ---
-string(18) "313238393734383438"
---- testing: '123e5' << '1.2' ---
-string(6) "323436"
---- testing: '123e5' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: '123e5' << 'abc' ---
-string(6) "313233"
---- testing: '123e5' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: '123e5' << '3.4a' ---
-string(6) "393834"
---- testing: '123e5' << 'a5.9' ---
-string(6) "313233"
---- testing: '123e5xyz' << '0' ---
-string(6) "313233"
---- testing: '123e5xyz' << '65' ---
-string(6) "323436"
---- testing: '123e5xyz' << '-44' ---
-string(18) "313238393734383438"
---- testing: '123e5xyz' << '1.2' ---
-string(6) "323436"
---- testing: '123e5xyz' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: '123e5xyz' << 'abc' ---
-string(6) "313233"
---- testing: '123e5xyz' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: '123e5xyz' << '3.4a' ---
-string(6) "393834"
---- testing: '123e5xyz' << 'a5.9' ---
-string(6) "313233"
---- testing: ' 123abc' << '0' ---
-string(6) "313233"
---- testing: ' 123abc' << '65' ---
-string(6) "323436"
---- testing: ' 123abc' << '-44' ---
-string(18) "313238393734383438"
---- testing: ' 123abc' << '1.2' ---
-string(6) "323436"
---- testing: ' 123abc' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: ' 123abc' << 'abc' ---
-string(6) "313233"
---- testing: ' 123abc' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: ' 123abc' << '3.4a' ---
-string(6) "393834"
---- testing: ' 123abc' << 'a5.9' ---
-string(6) "313233"
---- testing: '123 abc' << '0' ---
-string(6) "313233"
---- testing: '123 abc' << '65' ---
-string(6) "323436"
---- testing: '123 abc' << '-44' ---
-string(18) "313238393734383438"
---- testing: '123 abc' << '1.2' ---
-string(6) "323436"
---- testing: '123 abc' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: '123 abc' << 'abc' ---
-string(6) "313233"
---- testing: '123 abc' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: '123 abc' << '3.4a' ---
-string(6) "393834"
---- testing: '123 abc' << 'a5.9' ---
-string(6) "313233"
---- testing: '123abc ' << '0' ---
-string(6) "313233"
---- testing: '123abc ' << '65' ---
-string(6) "323436"
---- testing: '123abc ' << '-44' ---
-string(18) "313238393734383438"
---- testing: '123abc ' << '1.2' ---
-string(6) "323436"
---- testing: '123abc ' << '-7.7' ---
-string(20) "2d313637373732313630"
---- testing: '123abc ' << 'abc' ---
-string(6) "313233"
---- testing: '123abc ' << '123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << '123e5' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << '123e5xyz' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << ' 123abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << '123 abc' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << '123abc ' ---
-string(20) "2d363731303838363430"
---- testing: '123abc ' << '3.4a' ---
-string(6) "393834"
---- testing: '123abc ' << 'a5.9' ---
-string(6) "313233"
---- testing: '3.4a' << '0' ---
-string(2) "33"
---- testing: '3.4a' << '65' ---
-string(2) "36"
---- testing: '3.4a' << '-44' ---
-string(14) "33313435373238"
---- testing: '3.4a' << '1.2' ---
-string(2) "36"
---- testing: '3.4a' << '-7.7' ---
-string(18) "313030363633323936"
---- testing: '3.4a' << 'abc' ---
-string(2) "33"
---- testing: '3.4a' << '123abc' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << '123e5' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << '123e5xyz' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << ' 123abc' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << '123 abc' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << '123abc ' ---
-string(18) "343032363533313834"
---- testing: '3.4a' << '3.4a' ---
-string(4) "3234"
---- testing: '3.4a' << 'a5.9' ---
-string(2) "33"
---- testing: 'a5.9' << '0' ---
-string(2) "30"
---- testing: 'a5.9' << '65' ---
-string(2) "30"
---- testing: 'a5.9' << '-44' ---
-string(2) "30"
---- testing: 'a5.9' << '1.2' ---
-string(2) "30"
---- testing: 'a5.9' << '-7.7' ---
-string(2) "30"
---- testing: 'a5.9' << 'abc' ---
-string(2) "30"
---- testing: 'a5.9' << '123abc' ---
-string(2) "30"
---- testing: 'a5.9' << '123e5' ---
-string(2) "30"
---- testing: 'a5.9' << '123e5xyz' ---
-string(2) "30"
---- testing: 'a5.9' << ' 123abc' ---
-string(2) "30"
---- testing: 'a5.9' << '123 abc' ---
-string(2) "30"
---- testing: 'a5.9' << '123abc ' ---
-string(2) "30"
---- testing: 'a5.9' << '3.4a' ---
-string(2) "30"
---- testing: 'a5.9' << 'a5.9' ---
-string(2) "30"
-===DONE===
-
+--TEST--
+Test << operator : various numbers as strings
+--SKIPIF--
+<?php
+if (PHP_INT_SIZE != 4) die("skip this test is for 32bit platform only");
+if ((65<<65)==0) die("skip this test is for Intel only");
+?>
+--FILE--
+<?php
+
+$strVals = array(
+ "0","65","-44", "1.2", "-7.7", "abc", "123abc", "123e5", "123e5xyz", " 123abc", "123 abc", "123abc ", "3.4a",
+ "a5.9"
+);
+
+error_reporting(E_ERROR);
+
+foreach ($strVals as $strVal) {
+ foreach($strVals as $otherVal) {
+ echo "--- testing: '$strVal' << '$otherVal' ---\n";
+ var_dump(bin2hex($strVal<<$otherVal));
+ }
+}
+
+?>
+===DONE===
+--EXPECT--
+--- testing: '0' << '0' ---
+string(2) "30"
+--- testing: '0' << '65' ---
+string(2) "30"
+--- testing: '0' << '-44' ---
+string(2) "30"
+--- testing: '0' << '1.2' ---
+string(2) "30"
+--- testing: '0' << '-7.7' ---
+string(2) "30"
+--- testing: '0' << 'abc' ---
+string(2) "30"
+--- testing: '0' << '123abc' ---
+string(2) "30"
+--- testing: '0' << '123e5' ---
+string(2) "30"
+--- testing: '0' << '123e5xyz' ---
+string(2) "30"
+--- testing: '0' << ' 123abc' ---
+string(2) "30"
+--- testing: '0' << '123 abc' ---
+string(2) "30"
+--- testing: '0' << '123abc ' ---
+string(2) "30"
+--- testing: '0' << '3.4a' ---
+string(2) "30"
+--- testing: '0' << 'a5.9' ---
+string(2) "30"
+--- testing: '65' << '0' ---
+string(4) "3635"
+--- testing: '65' << '65' ---
+string(6) "313330"
+--- testing: '65' << '-44' ---
+string(16) "3638313537343430"
+--- testing: '65' << '1.2' ---
+string(6) "313330"
+--- testing: '65' << '-7.7' ---
+string(22) "2d32313133393239323136"
+--- testing: '65' << 'abc' ---
+string(4) "3635"
+--- testing: '65' << '123abc' ---
+string(18) "313334323137373238"
+--- testing: '65' << '123e5' ---
+string(18) "313334323137373238"
+--- testing: '65' << '123e5xyz' ---
+string(18) "313334323137373238"
+--- testing: '65' << ' 123abc' ---
+string(18) "313334323137373238"
+--- testing: '65' << '123 abc' ---
+string(18) "313334323137373238"
+--- testing: '65' << '123abc ' ---
+string(18) "313334323137373238"
+--- testing: '65' << '3.4a' ---
+string(6) "353230"
+--- testing: '65' << 'a5.9' ---
+string(4) "3635"
+--- testing: '-44' << '0' ---
+string(6) "2d3434"
+--- testing: '-44' << '65' ---
+string(6) "2d3838"
+--- testing: '-44' << '-44' ---
+string(18) "2d3436313337333434"
+--- testing: '-44' << '1.2' ---
+string(6) "2d3838"
+--- testing: '-44' << '-7.7' ---
+string(22) "2d31343736333935303038"
+--- testing: '-44' << 'abc' ---
+string(6) "2d3434"
+--- testing: '-44' << '123abc' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << '123e5' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << '123e5xyz' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << ' 123abc' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << '123 abc' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << '123abc ' ---
+string(22) "2d31363130363132373336"
+--- testing: '-44' << '3.4a' ---
+string(8) "2d333532"
+--- testing: '-44' << 'a5.9' ---
+string(6) "2d3434"
+--- testing: '1.2' << '0' ---
+string(2) "31"
+--- testing: '1.2' << '65' ---
+string(2) "32"
+--- testing: '1.2' << '-44' ---
+string(14) "31303438353736"
+--- testing: '1.2' << '1.2' ---
+string(2) "32"
+--- testing: '1.2' << '-7.7' ---
+string(16) "3333353534343332"
+--- testing: '1.2' << 'abc' ---
+string(2) "31"
+--- testing: '1.2' << '123abc' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << '123e5' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << '123e5xyz' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << ' 123abc' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << '123 abc' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << '123abc ' ---
+string(18) "313334323137373238"
+--- testing: '1.2' << '3.4a' ---
+string(2) "38"
+--- testing: '1.2' << 'a5.9' ---
+string(2) "31"
+--- testing: '-7.7' << '0' ---
+string(4) "2d37"
+--- testing: '-7.7' << '65' ---
+string(6) "2d3134"
+--- testing: '-7.7' << '-44' ---
+string(16) "2d37333430303332"
+--- testing: '-7.7' << '1.2' ---
+string(6) "2d3134"
+--- testing: '-7.7' << '-7.7' ---
+string(20) "2d323334383831303234"
+--- testing: '-7.7' << 'abc' ---
+string(4) "2d37"
+--- testing: '-7.7' << '123abc' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << '123e5' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << '123e5xyz' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << ' 123abc' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << '123 abc' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << '123abc ' ---
+string(20) "2d393339353234303936"
+--- testing: '-7.7' << '3.4a' ---
+string(6) "2d3536"
+--- testing: '-7.7' << 'a5.9' ---
+string(4) "2d37"
+--- testing: 'abc' << '0' ---
+string(2) "30"
+--- testing: 'abc' << '65' ---
+string(2) "30"
+--- testing: 'abc' << '-44' ---
+string(2) "30"
+--- testing: 'abc' << '1.2' ---
+string(2) "30"
+--- testing: 'abc' << '-7.7' ---
+string(2) "30"
+--- testing: 'abc' << 'abc' ---
+string(2) "30"
+--- testing: 'abc' << '123abc' ---
+string(2) "30"
+--- testing: 'abc' << '123e5' ---
+string(2) "30"
+--- testing: 'abc' << '123e5xyz' ---
+string(2) "30"
+--- testing: 'abc' << ' 123abc' ---
+string(2) "30"
+--- testing: 'abc' << '123 abc' ---
+string(2) "30"
+--- testing: 'abc' << '123abc ' ---
+string(2) "30"
+--- testing: 'abc' << '3.4a' ---
+string(2) "30"
+--- testing: 'abc' << 'a5.9' ---
+string(2) "30"
+--- testing: '123abc' << '0' ---
+string(6) "313233"
+--- testing: '123abc' << '65' ---
+string(6) "323436"
+--- testing: '123abc' << '-44' ---
+string(18) "313238393734383438"
+--- testing: '123abc' << '1.2' ---
+string(6) "323436"
+--- testing: '123abc' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: '123abc' << 'abc' ---
+string(6) "313233"
+--- testing: '123abc' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc' << '3.4a' ---
+string(6) "393834"
+--- testing: '123abc' << 'a5.9' ---
+string(6) "313233"
+--- testing: '123e5' << '0' ---
+string(6) "313233"
+--- testing: '123e5' << '65' ---
+string(6) "323436"
+--- testing: '123e5' << '-44' ---
+string(18) "313238393734383438"
+--- testing: '123e5' << '1.2' ---
+string(6) "323436"
+--- testing: '123e5' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: '123e5' << 'abc' ---
+string(6) "313233"
+--- testing: '123e5' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5' << '3.4a' ---
+string(6) "393834"
+--- testing: '123e5' << 'a5.9' ---
+string(6) "313233"
+--- testing: '123e5xyz' << '0' ---
+string(6) "313233"
+--- testing: '123e5xyz' << '65' ---
+string(6) "323436"
+--- testing: '123e5xyz' << '-44' ---
+string(18) "313238393734383438"
+--- testing: '123e5xyz' << '1.2' ---
+string(6) "323436"
+--- testing: '123e5xyz' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: '123e5xyz' << 'abc' ---
+string(6) "313233"
+--- testing: '123e5xyz' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: '123e5xyz' << '3.4a' ---
+string(6) "393834"
+--- testing: '123e5xyz' << 'a5.9' ---
+string(6) "313233"
+--- testing: ' 123abc' << '0' ---
+string(6) "313233"
+--- testing: ' 123abc' << '65' ---
+string(6) "323436"
+--- testing: ' 123abc' << '-44' ---
+string(18) "313238393734383438"
+--- testing: ' 123abc' << '1.2' ---
+string(6) "323436"
+--- testing: ' 123abc' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: ' 123abc' << 'abc' ---
+string(6) "313233"
+--- testing: ' 123abc' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: ' 123abc' << '3.4a' ---
+string(6) "393834"
+--- testing: ' 123abc' << 'a5.9' ---
+string(6) "313233"
+--- testing: '123 abc' << '0' ---
+string(6) "313233"
+--- testing: '123 abc' << '65' ---
+string(6) "323436"
+--- testing: '123 abc' << '-44' ---
+string(18) "313238393734383438"
+--- testing: '123 abc' << '1.2' ---
+string(6) "323436"
+--- testing: '123 abc' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: '123 abc' << 'abc' ---
+string(6) "313233"
+--- testing: '123 abc' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: '123 abc' << '3.4a' ---
+string(6) "393834"
+--- testing: '123 abc' << 'a5.9' ---
+string(6) "313233"
+--- testing: '123abc ' << '0' ---
+string(6) "313233"
+--- testing: '123abc ' << '65' ---
+string(6) "323436"
+--- testing: '123abc ' << '-44' ---
+string(18) "313238393734383438"
+--- testing: '123abc ' << '1.2' ---
+string(6) "323436"
+--- testing: '123abc ' << '-7.7' ---
+string(20) "2d313637373732313630"
+--- testing: '123abc ' << 'abc' ---
+string(6) "313233"
+--- testing: '123abc ' << '123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << '123e5' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << '123e5xyz' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << ' 123abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << '123 abc' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << '123abc ' ---
+string(20) "2d363731303838363430"
+--- testing: '123abc ' << '3.4a' ---
+string(6) "393834"
+--- testing: '123abc ' << 'a5.9' ---
+string(6) "313233"
+--- testing: '3.4a' << '0' ---
+string(2) "33"
+--- testing: '3.4a' << '65' ---
+string(2) "36"
+--- testing: '3.4a' << '-44' ---
+string(14) "33313435373238"
+--- testing: '3.4a' << '1.2' ---
+string(2) "36"
+--- testing: '3.4a' << '-7.7' ---
+string(18) "313030363633323936"
+--- testing: '3.4a' << 'abc' ---
+string(2) "33"
+--- testing: '3.4a' << '123abc' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << '123e5' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << '123e5xyz' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << ' 123abc' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << '123 abc' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << '123abc ' ---
+string(18) "343032363533313834"
+--- testing: '3.4a' << '3.4a' ---
+string(4) "3234"
+--- testing: '3.4a' << 'a5.9' ---
+string(2) "33"
+--- testing: 'a5.9' << '0' ---
+string(2) "30"
+--- testing: 'a5.9' << '65' ---
+string(2) "30"
+--- testing: 'a5.9' << '-44' ---
+string(2) "30"
+--- testing: 'a5.9' << '1.2' ---
+string(2) "30"
+--- testing: 'a5.9' << '-7.7' ---
+string(2) "30"
+--- testing: 'a5.9' << 'abc' ---
+string(2) "30"
+--- testing: 'a5.9' << '123abc' ---
+string(2) "30"
+--- testing: 'a5.9' << '123e5' ---
+string(2) "30"
+--- testing: 'a5.9' << '123e5xyz' ---
+string(2) "30"
+--- testing: 'a5.9' << ' 123abc' ---
+string(2) "30"
+--- testing: 'a5.9' << '123 abc' ---
+string(2) "30"
+--- testing: 'a5.9' << '123abc ' ---
+string(2) "30"
+--- testing: 'a5.9' << '3.4a' ---
+string(2) "30"
+--- testing: 'a5.9' << 'a5.9' ---
+string(2) "30"
+===DONE===
+
diff --git a/tests/lang/operators/bitwiseShiftLeft_variationStr2.phpt b/tests/lang/operators/bitwiseShiftLeft_variationStr2.phpt
new file mode 100644
index 0000000000..09949c56b0
--- /dev/null
+++ b/tests/lang/operators/bitwiseShiftLeft_variationStr2.phpt
@@ -0,0 +1,18 @@
+--TEST--
+Test << operator : numbers as strings, simple
+--FILE--
+<?php
+
+error_reporting(E_ERROR);
+
+var_dump("12" << "0");
+var_dump("34" << "1");
+var_dump("56" << "2");
+
+?>
+===DONE===
+--EXPECT--
+int(12)
+int(68)
+int(224)
+===DONE===
diff --git a/tests/lang/operators/bitwiseShiftRight_variationStr.phpt b/tests/lang/operators/bitwiseShiftRight_variationStr.phpt
index 9518d42cdc..ad53fea9d1 100644
--- a/tests/lang/operators/bitwiseShiftRight_variationStr.phpt
+++ b/tests/lang/operators/bitwiseShiftRight_variationStr.phpt
@@ -1,26 +1,30 @@
---TEST--
-Test >> operator : various numbers as strings
---FILE--
-<?php
-
-$strVals = array(
- "0","65","-44", "1.2", "-7.7", "abc", "123abc", "123e5", "123e5xyz", " 123abc", "123 abc", "123abc ", "3.4a",
- "a5.9"
-);
-
-error_reporting(E_ERROR);
-
-foreach ($strVals as $strVal) {
- foreach($strVals as $otherVal) {
- echo "--- testing: '$strVal' >> '$otherVal' ---\n";
- var_dump(bin2hex($strVal>>$otherVal));
- }
-}
-
-
-?>
-===DONE===
---EXPECT--
+--TEST--
+Test >> operator : various numbers as strings
+--SKIPIF--
+<?php
+if ((65<<65)==0) die("skip this test is for Intel only");
+?>
+--FILE--
+<?php
+
+$strVals = array(
+ "0","65","-44", "1.2", "-7.7", "abc", "123abc", "123e5", "123e5xyz", " 123abc", "123 abc", "123abc ", "3.4a",
+ "a5.9"
+);
+
+error_reporting(E_ERROR);
+
+foreach ($strVals as $strVal) {
+ foreach($strVals as $otherVal) {
+ echo "--- testing: '$strVal' >> '$otherVal' ---\n";
+ var_dump(bin2hex($strVal>>$otherVal));
+ }
+}
+
+
+?>
+===DONE===
+--EXPECT--
--- testing: '0' >> '0' ---
string(2) "30"
--- testing: '0' >> '65' ---
@@ -412,5 +416,5 @@ string(2) "30"
--- testing: 'a5.9' >> '3.4a' ---
string(2) "30"
--- testing: 'a5.9' >> 'a5.9' ---
-string(2) "30"
-===DONE===
+string(2) "30"
+===DONE===
diff --git a/tests/lang/operators/bitwiseShiftRight_variationStr2.phpt b/tests/lang/operators/bitwiseShiftRight_variationStr2.phpt
new file mode 100644
index 0000000000..db90e1b338
--- /dev/null
+++ b/tests/lang/operators/bitwiseShiftRight_variationStr2.phpt
@@ -0,0 +1,18 @@
+--TEST--
+Test >> operator : numbers as strings, simple
+--FILE--
+<?php
+
+error_reporting(E_ERROR);
+
+var_dump("12" >> "0");
+var_dump("34" >> "1");
+var_dump("56" >> "2");
+
+?>
+===DONE===
+--EXPECT--
+int(12)
+int(17)
+int(14)
+===DONE===
diff --git a/tests/security/open_basedir_linkinfo.phpt b/tests/security/open_basedir_linkinfo.phpt
index f8be45305e..55cf2c2f4b 100644
--- a/tests/security/open_basedir_linkinfo.phpt
+++ b/tests/security/open_basedir_linkinfo.phpt
@@ -41,6 +41,7 @@ test_open_basedir_after("linkinfo");
?>
--CLEAN--
<?php
+chdir(__DIR__);
require_once "open_basedir.inc";
delete_directories();
?>
diff --git a/tests/security/open_basedir_readlink.phpt b/tests/security/open_basedir_readlink.phpt
index b102ee9d9c..33720bbf1b 100644
--- a/tests/security/open_basedir_readlink.phpt
+++ b/tests/security/open_basedir_readlink.phpt
@@ -37,6 +37,7 @@ test_open_basedir_after("readlink");
?>
--CLEAN--
<?php
+chdir(__DIR__);
require_once "open_basedir.inc";
delete_directories();
?>
diff --git a/tests/strings/001.phpt b/tests/strings/001.phpt
index 3bfd3dbc30..98ceceb350 100644
--- a/tests/strings/001.phpt
+++ b/tests/strings/001.phpt
@@ -177,9 +177,23 @@ if ($ss == "\$'") {
}
-echo "Testing uniqid: ";
+echo "Testing uniqid(true): ";
+$str = "prefix";
+$ui1 = uniqid($str, true);
+$ui2 = uniqid($str, true);
+
+$len = 29;
+
+if (strlen($ui1) == strlen($ui2) && strlen($ui1) == $len && $ui1 != $ui2) {
+ echo("passed\n");
+} else {
+ echo("failed!\n");
+}
+
+echo "Testing uniqid(false): ";
$str = "prefix";
$ui1 = uniqid($str);
+usleep( 1 );
$ui2 = uniqid($str);
$len = strncasecmp(PHP_OS, 'CYGWIN', 6) ? 19 : 29;
@@ -207,4 +221,5 @@ Testing ufirst: passed
Testing strtr: passed
Testing addslashes: passed
Testing stripslashes: passed
-Testing uniqid: passed
+Testing uniqid(true): passed
+Testing uniqid(false): passed
diff --git a/win32/build/config.w32 b/win32/build/config.w32
index 3401205c8f..849a9372f7 100644
--- a/win32/build/config.w32
+++ b/win32/build/config.w32
@@ -357,7 +357,7 @@ ADD_SOURCES("Zend", "zend_language_parser.c zend_language_scanner.c \
zend_ini_parser.c zend_ini_scanner.c zend_alloc.c zend_compile.c \
zend_constants.c zend_dynamic_array.c zend_exceptions.c \
zend_execute_API.c zend_highlight.c \
- zend_llist.c zend_opcode.c zend_operators.c zend_ptr_stack.c \
+ zend_llist.c zend_vm_opcodes.c zend_opcode.c zend_operators.c zend_ptr_stack.c \
zend_stack.c zend_variables.c zend.c zend_API.c zend_extensions.c \
zend_hash.c zend_list.c zend_indent.c zend_builtin_functions.c \
zend_sprintf.c zend_ini.c zend_qsort.c zend_multibyte.c zend_ts_hash.c \
diff --git a/win32/build/deplister.c b/win32/build/deplister.c
index 8da65ba302..31f1f07e67 100644
--- a/win32/build/deplister.c
+++ b/win32/build/deplister.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/build/libs_version.txt b/win32/build/libs_version.txt
index 44420ddec8..964a2c735f 100644
--- a/win32/build/libs_version.txt
+++ b/win32/build/libs_version.txt
@@ -3,14 +3,14 @@ cclient-2007f
freetype-2.4.10
icu-51.2
jpeglib-9
-libcurl-7.30.0
+libcurl-7.35.0
libiconv-1.14
libmcrypt-2.5.8
libmpir-2.6.0
libpng-1.5.14
libpq-9.2.2
-libssh2-1.4.2
+libssh2-1.4.3
libtidy-20090406
libxslt-1.1.27
libxml-2.9.1
-openssl-1.0.1e
+openssl-1.0.1f
diff --git a/win32/globals.c b/win32/globals.c
index b381cc1237..0f88e4cc63 100644
--- a/win32/globals.c
+++ b/win32/globals.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/grp.h b/win32/grp.h
index a3fb97b205..899d3ac0cd 100644
--- a/win32/grp.h
+++ b/win32/grp.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/php_win32_globals.h b/win32/php_win32_globals.h
index b2b07f68e1..6bf9ba5b71 100644
--- a/win32/php_win32_globals.h
+++ b/win32/php_win32_globals.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/select.c b/win32/select.c
index 92af4be7b8..8e44636945 100644
--- a/win32/select.c
+++ b/win32/select.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/select.h b/win32/select.h
index 7cff1f303e..a8d8496295 100644
--- a/win32/select.h
+++ b/win32/select.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/sockets.c b/win32/sockets.c
index c8fddd6e52..8b3898bb3c 100644
--- a/win32/sockets.c
+++ b/win32/sockets.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/sockets.h b/win32/sockets.h
index f0b9f27484..78a0d3a967 100644
--- a/win32/sockets.h
+++ b/win32/sockets.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/syslog.h b/win32/syslog.h
index e24737fe2f..06397d0f90 100644
--- a/win32/syslog.h
+++ b/win32/syslog.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/time.h b/win32/time.h
index f841a2b601..d5d86eb1ed 100644
--- a/win32/time.h
+++ b/win32/time.h
@@ -50,4 +50,6 @@ PHPAPI extern int setitimer(int which, const struct itimerval *value,
PHPAPI int nanosleep( const struct timespec * rqtp, struct timespec * rmtp );
+PHPAPI int usleep(unsigned int useconds);
+
#endif
diff --git a/win32/winutil.c b/win32/winutil.c
index 4afc28feca..22e2d45304 100644
--- a/win32/winutil.c
+++ b/win32/winutil.c
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |
diff --git a/win32/winutil.h b/win32/winutil.h
index 8cf07ec286..773063e5f6 100644
--- a/win32/winutil.h
+++ b/win32/winutil.h
@@ -2,7 +2,7 @@
+----------------------------------------------------------------------+
| PHP Version 5 |
+----------------------------------------------------------------------+
- | Copyright (c) 1997-2013 The PHP Group |
+ | Copyright (c) 1997-2014 The PHP Group |
+----------------------------------------------------------------------+
| This source file is subject to version 3.01 of the PHP license, |
| that is bundled with this package in the file LICENSE, and is |