@@ -1785,26 +1785,34 @@ ZEND_API void object_properties_load(zend_object *object, const HashTable *prope
17851785}
17861786/* }}} */
17871787
1788+ static ZEND_COLD zend_never_inline void zend_cannot_instantiate_class (zend_class_entry * class_type ) {
1789+ if (class_type -> ce_flags & ZEND_ACC_INTERFACE ) {
1790+ zend_throw_error (NULL , "Cannot instantiate interface %s" , ZSTR_VAL (class_type -> name ));
1791+ } else if (class_type -> ce_flags & ZEND_ACC_TRAIT ) {
1792+ zend_throw_error (NULL , "Cannot instantiate trait %s" , ZSTR_VAL (class_type -> name ));
1793+ } else if (class_type -> ce_flags & ZEND_ACC_ENUM ) {
1794+ zend_throw_error (NULL , "Cannot instantiate enum %s" , ZSTR_VAL (class_type -> name ));
1795+ } else {
1796+ ZEND_ASSERT (class_type -> ce_flags & (ZEND_ACC_IMPLICIT_ABSTRACT_CLASS |ZEND_ACC_EXPLICIT_ABSTRACT_CLASS ));
1797+ zend_throw_error (NULL , "Cannot instantiate abstract class %s" , ZSTR_VAL (class_type -> name ));
1798+ }
1799+ }
1800+
17881801/* This function requires 'properties' to contain all props declared in the
17891802 * class and all props being public. If only a subset is given or the class
17901803 * has protected members then you need to merge the properties separately by
17911804 * calling zend_merge_properties(). */
1792- static zend_always_inline zend_result _object_and_properties_init (zval * arg , zend_class_entry * class_type , HashTable * properties ) /* {{{ */
1793- {
1794- if (UNEXPECTED (class_type -> ce_flags & ZEND_ACC_UNINSTANTIABLE )) {
1795- if (class_type -> ce_flags & ZEND_ACC_INTERFACE ) {
1796- zend_throw_error (NULL , "Cannot instantiate interface %s" , ZSTR_VAL (class_type -> name ));
1797- } else if (class_type -> ce_flags & ZEND_ACC_TRAIT ) {
1798- zend_throw_error (NULL , "Cannot instantiate trait %s" , ZSTR_VAL (class_type -> name ));
1799- } else if (class_type -> ce_flags & ZEND_ACC_ENUM ) {
1800- zend_throw_error (NULL , "Cannot instantiate enum %s" , ZSTR_VAL (class_type -> name ));
1801- } else {
1802- ZEND_ASSERT (class_type -> ce_flags & (ZEND_ACC_IMPLICIT_ABSTRACT_CLASS |ZEND_ACC_EXPLICIT_ABSTRACT_CLASS ));
1803- zend_throw_error (NULL , "Cannot instantiate abstract class %s" , ZSTR_VAL (class_type -> name ));
1805+ static zend_always_inline zend_result _object_and_properties_init (zval * arg , zend_class_entry * class_type , HashTable * properties , bool known_instantiable ) /* {{{ */
1806+ {
1807+ if (!known_instantiable ) {
1808+ if (UNEXPECTED (class_type -> ce_flags & ZEND_ACC_UNINSTANTIABLE )) {
1809+ zend_cannot_instantiate_class (class_type );
1810+ ZVAL_NULL (arg );
1811+ Z_OBJ_P (arg ) = NULL ;
1812+ return FAILURE ;
18041813 }
1805- ZVAL_NULL (arg );
1806- Z_OBJ_P (arg ) = NULL ;
1807- return FAILURE ;
1814+ } else {
1815+ ZEND_ASSERT ((class_type -> ce_flags & ZEND_ACC_UNINSTANTIABLE ) == 0 );
18081816 }
18091817
18101818 if (UNEXPECTED (!(class_type -> ce_flags & ZEND_ACC_CONSTANTS_UPDATED ))) {
@@ -1833,19 +1841,24 @@ static zend_always_inline zend_result _object_and_properties_init(zval *arg, zen
18331841
18341842ZEND_API zend_result object_and_properties_init (zval * arg , zend_class_entry * class_type , HashTable * properties ) /* {{{ */
18351843{
1836- return _object_and_properties_init (arg , class_type , properties );
1844+ return _object_and_properties_init (arg , class_type , properties , false );
18371845}
18381846/* }}} */
18391847
18401848ZEND_API zend_result object_init_ex (zval * arg , zend_class_entry * class_type ) /* {{{ */
18411849{
1842- return _object_and_properties_init (arg , class_type , NULL );
1850+ return _object_and_properties_init (arg , class_type , NULL , false );
18431851}
18441852/* }}} */
18451853
1854+ ZEND_API zend_result object_init_instantiable_class (zval * arg , zend_class_entry * class_type ) /* {{{ */
1855+ {
1856+ return _object_and_properties_init (arg , class_type , NULL , true);
1857+ }
1858+
18461859ZEND_API zend_result object_init_with_constructor (zval * arg , zend_class_entry * class_type , uint32_t param_count , zval * params , HashTable * named_params ) /* {{{ */
18471860{
1848- zend_result status = _object_and_properties_init (arg , class_type , NULL );
1861+ zend_result status = _object_and_properties_init (arg , class_type , NULL , false );
18491862 if (UNEXPECTED (status == FAILURE )) {
18501863 ZVAL_UNDEF (arg );
18511864 return FAILURE ;
0 commit comments