summaryrefslogtreecommitdiff
path: root/Zend/zend_API.c
diff options
context:
space:
mode:
authorNikita Popov <nikita.ppv@gmail.com>2021-01-12 10:15:13 +0100
committerNikita Popov <nikita.ppv@gmail.com>2021-01-12 10:15:13 +0100
commit45a4d07dd075af0737da6ecbb98aed705687fafc (patch)
tree7c91d0b6570accaa568a94affdf3ae25b0fa1bef /Zend/zend_API.c
parenta69da19c6ba3f2f6255f43eaab634deccefa2f57 (diff)
parent973138f39da192b3948b981b442401c30c8b80bc (diff)
downloadphp-git-45a4d07dd075af0737da6ecbb98aed705687fafc.tar.gz
Merge branch 'PHP-8.0'
* PHP-8.0: Add support for union types for internal functions
Diffstat (limited to 'Zend/zend_API.c')
-rw-r--r--Zend/zend_API.c36
1 files changed, 33 insertions, 3 deletions
diff --git a/Zend/zend_API.c b/Zend/zend_API.c
index 82c1d0496f..8a265e907c 100644
--- a/Zend/zend_API.c
+++ b/Zend/zend_API.c
@@ -2566,10 +2566,40 @@ ZEND_API zend_result zend_register_functions(zend_class_entry *scope, const zend
for (i = 0; i < num_args; i++) {
if (ZEND_TYPE_HAS_CLASS(new_arg_info[i].type)) {
ZEND_ASSERT(ZEND_TYPE_HAS_NAME(new_arg_info[i].type)
- && "Only simple classes are currently supported");
+ && "Should be stored as simple name");
const char *class_name = ZEND_TYPE_LITERAL_NAME(new_arg_info[i].type);
- ZEND_TYPE_SET_PTR(new_arg_info[i].type,
- zend_string_init_interned(class_name, strlen(class_name), 1));
+
+ size_t num_types = 1;
+ const char *p = class_name;
+ while ((p = strchr(p, '|'))) {
+ num_types++;
+ p++;
+ }
+
+ if (num_types == 1) {
+ /* Simple class type */
+ ZEND_TYPE_SET_PTR(new_arg_info[i].type,
+ zend_string_init_interned(class_name, strlen(class_name), 1));
+ } else {
+ /* Union type */
+ zend_type_list *list = malloc(ZEND_TYPE_LIST_SIZE(num_types));
+ list->num_types = num_types;
+ ZEND_TYPE_SET_LIST(new_arg_info[i].type, list);
+
+ const char *start = class_name;
+ uint32_t j = 0;
+ while (true) {
+ const char *end = strchr(start, '|');
+ zend_string *str =
+ zend_string_init(start, end ? end - start : strlen(start), 1);
+ list->types[j] = (zend_type) ZEND_TYPE_INIT_CLASS(str, 0, 0);
+ if (!end) {
+ break;
+ }
+ start = end + 1;
+ j++;
+ }
+ }
}
}
}