Skip to content

Commit

Permalink
implement semi-reserved words support for class|object members
Browse files Browse the repository at this point in the history
  • Loading branch information
marcioAlmada committed Feb 25, 2015
1 parent 52f5cb9 commit 2e11444
Show file tree
Hide file tree
Showing 7 changed files with 19,313 additions and 3,812 deletions.
45 changes: 45 additions & 0 deletions Zend/zend_compile.c
Expand Up @@ -1479,6 +1479,35 @@ uint32_t zend_get_class_fetch_type(zend_string *name) /* {{{ */
}
/* }}} */

uint32_t zend_check_reserved_method_name(zend_string *name) /* {{{ */
{
if (zend_string_equals_literal_ci(name, "static")) {
return ZEND_RESERVED_STATIC;
} else if (zend_string_equals_literal_ci(name, "public")) {
return ZEND_RESERVED_PUBLIC;
} else if (zend_string_equals_literal_ci(name, "private")) {
return ZEND_RESERVED_PRIVATE;
} else if (zend_string_equals_literal_ci(name, "protected")) {
return ZEND_RESERVED_PROTECTED;
} else if (zend_string_equals_literal_ci(name, "abstract")) {
return ZEND_RESERVED_ABSTRACT;
} else if (zend_string_equals_literal_ci(name, "final")) {
return ZEND_RESERVED_FINAL;
} else {
return ZEND_NOT_RESERVED;
}
}
/* }}} */

uint32_t zend_check_reserved_class_const_name(zend_string *name) /* {{{ */
{
if(zend_string_equals_literal_ci(name, "class")) {
return ZEND_RESERVED_CLASS;
}
return zend_check_reserved_method_name(name);
}
/* }}} */

ZEND_API zend_string *zend_get_compiled_variable_name(const zend_op_array *op_array, uint32_t var) /* {{{ */
{
return op_array->vars[EX_VAR_TO_NUM(var)];
Expand Down Expand Up @@ -4282,6 +4311,12 @@ void zend_compile_func_decl(znode *result, zend_ast *ast) /* {{{ */

if (is_method) {
zend_bool has_body = stmt_ast != NULL;

if(ZEND_NOT_RESERVED != zend_check_reserved_method_name(decl->name)) {
zend_error_noreturn(E_COMPILE_ERROR,
"Cannot use '%s' as class method name as it is reserved", decl->name->val);
}

zend_begin_method_decl(op_array, decl->name, has_body);
} else {
zend_begin_func_decl(result, op_array, decl);
Expand Down Expand Up @@ -4404,6 +4439,16 @@ void zend_compile_class_const_decl(zend_ast *ast) /* {{{ */
zend_const_expr_to_zval(&value_zv, value_ast);

name = zend_new_interned_string_safe(name);

uint32_t is_reserved = zend_check_reserved_class_const_name(name);
if(ZEND_RESERVED_CLASS == is_reserved) {
zend_error_noreturn( E_COMPILE_ERROR,
"Cannot redefine class constant %s::%s as it is reserved", ce->name->val, name->val);
} else if(ZEND_NOT_RESERVED != is_reserved) {
zend_error_noreturn(E_COMPILE_ERROR,
"Cannot use '%s' as class constant name as it is reserved", name->val);
}

if (zend_hash_add(&ce->constants_table, name, &value_zv) == NULL) {
zend_error_noreturn(E_COMPILE_ERROR, "Cannot redefine class constant %s::%s",
ce->name->val, name->val);
Expand Down
12 changes: 12 additions & 0 deletions Zend/zend_compile.h
Expand Up @@ -719,6 +719,8 @@ ZEND_API zend_bool zend_is_compiling(void);
ZEND_API char *zend_make_compiled_string_description(const char *name);
ZEND_API void zend_initialize_class_data(zend_class_entry *ce, zend_bool nullify_handlers);
uint32_t zend_get_class_fetch_type(zend_string *name);
uint32_t zend_check_reserved_method_name(zend_string *name);
uint32_t zend_check_reserved_class_const_name(zend_string *name);

typedef zend_bool (*zend_auto_global_callback)(zend_string *name);
typedef struct _zend_auto_global {
Expand Down Expand Up @@ -757,6 +759,16 @@ int zend_add_literal(zend_op_array *op_array, zval *zv);
#define ZEND_FETCH_CLASS_NO_AUTOLOAD 0x80
#define ZEND_FETCH_CLASS_SILENT 0x0100

/* reserved names */
#define ZEND_NOT_RESERVED 0
#define ZEND_RESERVED_STATIC 1
#define ZEND_RESERVED_ABSTRACT 2
#define ZEND_RESERVED_FINAL 3
#define ZEND_RESERVED_PRIVATE 4
#define ZEND_RESERVED_PROTECTED 5
#define ZEND_RESERVED_PUBLIC 6
#define ZEND_RESERVED_CLASS 7

/* variable parsing type (compile-time) */
#define ZEND_PARSED_MEMBER (1<<0)
#define ZEND_PARSED_METHOD_CALL (1<<1)
Expand Down

0 comments on commit 2e11444

Please sign in to comment.