]> granicus.if.org Git - php/commitdiff
refactor: class constants parsing
authormoliata <7127204+moliata@users.noreply.github.com>
Mon, 6 Jul 2020 16:23:27 +0000 (19:23 +0300)
committerNikita Popov <nikita.ppv@gmail.com>
Mon, 6 Jul 2020 16:34:41 +0000 (18:34 +0200)
As part of my work on typed class constants, I wanted to make a
separate pull request for unrelated changes.

These include:

 * Moving from ast->child[0]->attr to ast->attr
 * Making zend_ast_export_ex() export class constants' visibility
 * Extracting an additional zend_compile_class_const_group() function

Closes GH-5812.

Zend/tests/assert/expect_015.phpt
Zend/tests/attributes/012_ast_export.phpt
Zend/zend_ast.c
Zend/zend_compile.c
Zend/zend_language_parser.y

index 21ff636f92c8cd5323d3a3e97cc376adab29bc2f..3414f52e1b2e90b6dbecf6eeb9ae48ad3b836425 100644 (file)
@@ -164,8 +164,8 @@ Warning: assert(): assert(0 && ($a = function () {
 
 Warning: assert(): assert(0 && ($a = function &(array &$a, ?X $b = null) use($c, &$d): ?X {
     abstract class A extends B implements C, D {
-        const X = 12;
-        const Y = self::X, Z = 'aaa';
+        public const X = 12;
+        public const Y = self::X, Z = 'aaa';
         public $a = 1, $b;
         protected $c;
         private static $d = null;
index 47176b1b0d02d8043153b5d54c5dd9c4e01c3d4a..fe3539c8a9fb8b361995710558f7cb82e43fefa1 100644 (file)
@@ -29,7 +29,7 @@ Warning: assert(): assert(0 && ($a = <<A1(1, 2, 1 + 2)>> fn() => 1)) failed in %
 Warning: assert(): assert(0 && ($a = new <<A1>> class {
     <<A1>>
     <<A2>>
-    const FOO = 'foo';
+    public const FOO = 'foo';
     <<A2>>
     public $x;
     <<A3>>
index 5d7c98dad5b7ce1b23b8893b351832a51c249271..53c3be0de944d896e941fcc55bd19c95be04a053 100644 (file)
@@ -1381,6 +1381,16 @@ static ZEND_COLD void zend_ast_export_attributes(smart_str *str, zend_ast *ast,
        }
 }
 
+static ZEND_COLD void zend_ast_export_visibility(smart_str *str, uint32_t flags) {
+       if (flags & ZEND_ACC_PUBLIC) {
+               smart_str_appends(str, "public ");
+       } else if (flags & ZEND_ACC_PROTECTED) {
+               smart_str_appends(str, "protected ");
+       } else if (flags & ZEND_ACC_PRIVATE) {
+               smart_str_appends(str, "private ");
+       }
+}
+
 static ZEND_COLD void zend_ast_export_type(smart_str *str, zend_ast *ast, int indent) {
        if (ast->kind == ZEND_AST_TYPE_UNION) {
                zend_ast_list *list = zend_ast_get_list(ast);
@@ -1478,13 +1488,9 @@ tail_call:
                                zend_bool newlines = !(ast->kind == ZEND_AST_CLOSURE || ast->kind == ZEND_AST_ARROW_FUNC);
                                zend_ast_export_attributes(str, decl->child[4], indent, newlines);
                        }
-                       if (decl->flags & ZEND_ACC_PUBLIC) {
-                               smart_str_appends(str, "public ");
-                       } else if (decl->flags & ZEND_ACC_PROTECTED) {
-                               smart_str_appends(str, "protected ");
-                       } else if (decl->flags & ZEND_ACC_PRIVATE) {
-                               smart_str_appends(str, "private ");
-                       }
+
+                       zend_ast_export_visibility(str, decl->flags);
+
                        if (decl->flags & ZEND_ACC_STATIC) {
                                smart_str_appends(str, "static ");
                        }
@@ -1595,13 +1601,9 @@ simple_list:
                        if (ast->child[2]) {
                                zend_ast_export_attributes(str, ast->child[2], indent, 1);
                        }
-                       if (ast->attr & ZEND_ACC_PUBLIC) {
-                               smart_str_appends(str, "public ");
-                       } else if (ast->attr & ZEND_ACC_PROTECTED) {
-                               smart_str_appends(str, "protected ");
-                       } else if (ast->attr & ZEND_ACC_PRIVATE) {
-                               smart_str_appends(str, "private ");
-                       }
+
+                       zend_ast_export_visibility(str, ast->attr);
+
                        if (ast->attr & ZEND_ACC_STATIC) {
                                smart_str_appends(str, "static ");
                        }
@@ -1616,15 +1618,19 @@ simple_list:
                }
 
                case ZEND_AST_CONST_DECL:
-               case ZEND_AST_CLASS_CONST_DECL:
                        smart_str_appends(str, "const ");
                        goto simple_list;
                case ZEND_AST_CLASS_CONST_GROUP:
                        if (ast->child[1]) {
                                zend_ast_export_attributes(str, ast->child[1], indent, 1);
                        }
-                       zend_ast_export_ex(str, ast->child[0], 0, indent);
-                       break;
+
+                       zend_ast_export_visibility(str, ast->attr);
+                       smart_str_appends(str, "const ");
+
+                       ast = ast->child[0];
+
+                       goto simple_list;
                case ZEND_AST_NAME_LIST:
                        zend_ast_export_name_list(str, (zend_ast_list*)ast, indent);
                        break;
index 7ee7e8e9d32529303f001c4608d9536ba72a2bf2..ea5baf2a126b1d3d08c1f8c4a405ea67c53e76e7 100644 (file)
@@ -6613,18 +6613,18 @@ void zend_compile_prop_decl(zend_ast *ast, zend_ast *type_ast, uint32_t flags, z
 }
 /* }}} */
 
-void zend_compile_prop_group(zend_ast *list) /* {{{ */
+void zend_compile_prop_group(zend_ast *ast) /* {{{ */
 {
-       zend_ast *type_ast = list->child[0];
-       zend_ast *prop_ast = list->child[1];
-       zend_ast *attr_ast = list->child[2];
+       zend_ast *type_ast = ast->child[0];
+       zend_ast *prop_ast = ast->child[1];
+       zend_ast *attr_ast = ast->child[2];
 
        if (attr_ast && zend_ast_get_list(prop_ast)->children > 1) {
                zend_error_noreturn(E_COMPILE_ERROR, "Cannot apply attributes to a group of properties");
                return;
        }
 
-       zend_compile_prop_decl(prop_ast, type_ast, list->attr, attr_ast);
+       zend_compile_prop_decl(prop_ast, type_ast, ast->attr, attr_ast);
 }
 /* }}} */
 
@@ -6640,23 +6640,18 @@ static void zend_check_const_and_trait_alias_attr(uint32_t attr, const char* ent
 }
 /* }}} */
 
-void zend_compile_class_const_decl(zend_ast *ast, zend_ast *attr_ast) /* {{{ */
+void zend_compile_class_const_decl(zend_ast *ast, uint32_t flags, zend_ast *attr_ast) /* {{{ */
 {
        zend_ast_list *list = zend_ast_get_list(ast);
        zend_class_entry *ce = CG(active_class_entry);
-       uint32_t i;
+       uint32_t i, children = list->children;
 
        if ((ce->ce_flags & ZEND_ACC_TRAIT) != 0) {
                zend_error_noreturn(E_COMPILE_ERROR, "Traits cannot have constants");
                return;
        }
 
-       if (attr_ast && list->children > 1) {
-               zend_error_noreturn(E_COMPILE_ERROR, "Cannot apply attributes to a group of constants");
-               return;
-       }
-
-       for (i = 0; i < list->children; ++i) {
+       for (i = 0; i < children; ++i) {
                zend_class_constant *c;
                zend_ast *const_ast = list->child[i];
                zend_ast *name_ast = const_ast->child[0];
@@ -6666,12 +6661,12 @@ void zend_compile_class_const_decl(zend_ast *ast, zend_ast *attr_ast) /* {{{ */
                zend_string *doc_comment = doc_comment_ast ? zend_string_copy(zend_ast_get_str(doc_comment_ast)) : NULL;
                zval value_zv;
 
-               if (UNEXPECTED(ast->attr & (ZEND_ACC_STATIC|ZEND_ACC_ABSTRACT|ZEND_ACC_FINAL))) {
-                       zend_check_const_and_trait_alias_attr(ast->attr, "constant");
+               if (UNEXPECTED(flags & (ZEND_ACC_STATIC|ZEND_ACC_ABSTRACT|ZEND_ACC_FINAL))) {
+                       zend_check_const_and_trait_alias_attr(flags, "constant");
                }
 
                zend_const_expr_to_zval(&value_zv, value_ast);
-               c = zend_declare_class_constant_ex(ce, name, &value_zv, ast->attr, doc_comment);
+               c = zend_declare_class_constant_ex(ce, name, &value_zv, flags, doc_comment);
 
                if (attr_ast) {
                        zend_compile_attributes(&c->attributes, attr_ast, 0, ZEND_ATTRIBUTE_TARGET_CLASS_CONST);
@@ -6680,6 +6675,21 @@ void zend_compile_class_const_decl(zend_ast *ast, zend_ast *attr_ast) /* {{{ */
 }
 /* }}} */
 
+void zend_compile_class_const_group(zend_ast *ast) /* {{{ */
+{
+       zend_ast *const_ast = ast->child[0];
+       zend_ast *attr_ast = ast->child[1];
+
+       if (attr_ast && zend_ast_get_list(const_ast)->children > 1) {
+               zend_error_noreturn(E_COMPILE_ERROR, "Cannot apply attributes to a group of constants");
+
+               return;
+       }
+
+       zend_compile_class_const_decl(const_ast, ast->attr, attr_ast);
+}
+/* }}} */
+
 static void zend_compile_method_ref(zend_ast *ast, zend_trait_method_reference *method_ref) /* {{{ */
 {
        zend_ast *class_ast = ast->child[0];
@@ -8983,7 +8993,7 @@ void zend_compile_stmt(zend_ast *ast) /* {{{ */
                        zend_compile_prop_group(ast);
                        break;
                case ZEND_AST_CLASS_CONST_GROUP:
-                       zend_compile_class_const_decl(ast->child[0], ast->child[1]);
+                       zend_compile_class_const_group(ast);
                        break;
                case ZEND_AST_USE_TRAIT:
                        zend_compile_use_trait(ast);
index 88b159cc6e57717510f0e7db1540bc60c3e362c2..7827a178f6f5b5f9b97ee0b63aa755a2ceb14a39 100644 (file)
@@ -797,7 +797,8 @@ attributed_class_statement:
                        { $$ = zend_ast_create(ZEND_AST_PROP_GROUP, $2, $3, NULL);
                          $$->attr = $1; }
        |       method_modifiers T_CONST class_const_list ';'
-                       { $$ = zend_ast_create(ZEND_AST_CLASS_CONST_GROUP, $3, NULL); $3->attr = $1; }
+                       { $$ = zend_ast_create(ZEND_AST_CLASS_CONST_GROUP, $3, NULL);
+                         $$->attr = $1; }
        |       method_modifiers function returns_ref identifier backup_doc_comment '(' parameter_list ')'
                return_type backup_fn_flags method_body backup_fn_flags
                        { $$ = zend_ast_create_decl(ZEND_AST_METHOD, $3 | $1 | $12, $2, $5,