1, about the return value, the PHP kernel uses a large number of macros to implement, we first look at a function
Php_function宏的定义(Zend/zend_API.h)
#define Php_function zend_function#define zend_function (name) zend_named_function (ZEND_FN (name)) #define ZEND_FN (name) zif_# #name # define Zend_named_function (name) void name (internal_function_parameters) #define internal_function_parameters int HT, zval *return_value, Zval **return_value_ptr,zval *this_ptr, int return_value_used tsrmls_dc//final void Zif_hello_world (int ht, zval *return_value, Zval **return_value_ptr, zval *this_ptr, int return_ Value_used tsrmls_dc) {}
Parameter interpretation
internal_function_parameters
name and type |
Description |
Access Macros |
int ht |
Number of actual parameters passed by the user |
ZEND_NUM_ARGS() |
zval *return_value |
A pointer to a PHP variable that populates the return value to be passed to the user. The default value is IS_NULL . |
RETVAL_* ,RETURN_* |
zval **return_value_ptr |
When a reference is returned, PHP sets it as a pointer to the variable. Returning references is not recommended. |
|
zval *this_ptr |
If this is a method call, it points to $this the PHP variable that holds the object. |
getThis() |
int return_value_used |
Flag indicating whether the return value will be used by the caller. Caller. |
|
A function entry can contain a pointer to the structure of a parameter information. It is not necessary to provide this information unless you intend to accept the parameter reference or return a reference, and provide the information that is accessed by the PHP reflection API. Parameters can be passed directly as function arguments, or through a stack
2. Macros for return values
a)RETURN_BOOL(0); //返回bool值
#define Retval_bool (b) Zval_bool (return_value, b) #define Return_bool (b) {retval_bool (b); return;} #define Zval_bool (z, b) do { Zval *__z = (z); Z_lval_p (__z) = ((b)! = 0); Z_type_p (__z) = Is_bool; } while (0)
So expand this return_bool (0), and the final operation that returns the value in the function is
Do { Zval *__z = (return_value); Z_lval_p (__z) = ((0) = 0); Define the Return_value value z_type_p (__z) = Is_bool;//define Return_value type}while (0)
b) RETURN_STRING("hello world", 1);
After expansion
Do { const char *__s = ("Hello World"); Zval *__z = return_value; Z_strlen_p (__z) = STRLEN (__s);//define Length z_strval_p (__z) = (1?estrndup (__s, Z_strlen_p (__z)):(char*) __s);//define values, The Estrndup function implements the copy of the string z_type_p (__z) = is_string;} while (0)
c) Return_long (100);
After expansion
Zval *__z = Return_value; Z_lval_p (__z) = +; Z_type_p (__z) = Is_long;
d) Return array
Array_init (Return_value);//Initialize the Return_value array, and you can return an empty one after this operation is completed
e) Return Object
Object_init (Return_value);//Initialize Return_value to object, this operation completes and returns an empty pair of image
other
#define ZVAL_FALSE (z) zval_bool (z, 0) #define ZVAL_TRUE (z) Zval_bool (z, 1) #define RETVAL_RESOURCE (L) zval_resource (Return_value, l) #define Retval_b OOL (b) Zval_bool (Return_value, b) #define RETVAL_NULL () Zval_null (return_value) #define Retval_long (L) Zval_long (Return_value, l) #define Retval_do Uble (d) zval_double (Return_value, D) #define Retval_string (S, duplicate) Zval_st RING (Return_value, S, duplicate) #define RETVAL_STRINGL (S, l, duplicate) Zval_stringl (Return_value, S, L, duplicate ) #define Retval_empty_string () zval_empty_string (return_value) #define RETVAL_ZVAL (Zv, copy, Dtor) Zval_zval (Return_value, Zv, copy, dtor) #define Retval_false Zval_bool (Return_valu E, 0) #define Retval_true Zval_bool (Return_value, 1) #define RETURN_RESOURCE (l) {R Etval_resource (l); Return } #define Return_bool (b) {retval_bool (b); RETURN;} #define Return_null () {retval_null (); RETURN;} #define Return_long (L) {Retval_long (l); RETURN;} #define Return_double (d) {retval_double (d); RETURN;} #define RETURN_STRING (S, duplicate) {retval_string (S, duplicate); RETURN;} #define RETURN_STRINGL (S, l, duplicate) {Retval_stringl (S, l, duplicate); RETURN;} #define Return_empty_string () {retval_empty_string (); RETURN;} #define RETURN_ZVAL (Zv, copy, dtor) {retval_zval (Zv, copy, dtor); RETURN;} #define RETURN_FALSE {retval_false; RETURN;} #define RETURN_TRUE {retval_true; RETURN;}
3, arrays, and operations of objects
Zval *arr; Make_std_zval (arr); Array_init (arr); $arr = Array (); Add_assoc_long (arr, "a", 10); $arr ["a"] = 10; Add_asoc_unset (arr, "a"); Unset (arr["a"]); Add_assoc_bool (arr, "B", 1); $arr ["b"] = True;add_assoc_resource (arr, "C", 10); $arr ["c"] = $resource; Add_assoc_double (arr, "D", 2.15); $arr ["d"] = 2.15;add_assoc_string (arr, "E", "Hello", 1); $arr ["e"] = "Hello"; the last parameter indicates whether the string value is copied Add_assoc_stringl (); Zval *sub; Make_std_zval (sub); Array_init (sub); Add_assoc_zval (arr, "F", sub); $arr ["f"] = $sub; Zval *arr; Make_std_zval (arr); Array_init (arr); $arr = Array (); Add_index_long (arr, 1, 10); $arr [1] = 10;add_index_unset (arr, 1); Unset ($arr [1]); Add_index_bool (arr, 2, 1); $arr [2] = True;add_index_resource (arr, 3, 10); $arr [3] = $resource; Add_index_double (arr, 4, 2.15); $arr [4] = 2.15;add_index_string (arr, 5, "Hello", 1); $arr [5] = "Hello"; the last parameter indicates whether the string value is copied Add_index_stringl (); Zval *sub; Make_std_zval (sub); Array_init (sub); Add_index_zval (arr, 6, sub); $arr [6] = $sub; Zval *arr; MakE_std_zval (arr); Array_init (arr); $arr = Array (); Add_next_index_long (arr, 10); $arr [] = 10;add_next_index_unset (arr); Unset ($arr []); Add_next_index_bool (arr, 1); $arr [] = True;add_next_index_resource (arr, 10); $arr [] = $resource; Add_next_index_double (arr, 2.15); $arr [] = 2.15;add_next_index_string (arr, "Hello", 1); $arr [] = "Hello"; the last parameter indicates whether the string value is copied Add_next_index_stringl (); Zval *sub; Make_std_zval (sub); Array_init (sub); Add_next_index_zval (arr, sub); $arr [] = $sub; Zval *obj; Make_std_zval (obj); object_init (obj);//$obj = new Stdclass;add_property_long (obj, "a", 10); $obj->a = 10;add_property_unset (obj, "a"); unset ($obj->a); Add_property_bool (obj, "B", 1); $obj->b = True;add_property_resource (obj, "C", 10); $obj->c = $resource; add_property_double (obj, "D", 2.15); $obj->d = 2.15;add_property_string (obj, "e", "Hello", 1);//$obj->e = "Hello"; The last parameter indicates whether the string value is copied Add_property_stringl (); Zval *sub; Make_std_zval (sub); Object_init (sub); $sub = new STDCLASS;ADD_PROperty_zval (obj, "f", sub); $obj->f = $sub;
Some actions for macros
#define Z_LVAL (Zval) (zval). Value.lval #define Z_bval (Zval) ((Zend_bool) (zval). Value.lval) #define Z_DVAL (Zval) (zval). Value.dval #define Z_strval (zval) (zval). Value.str.val #define Z_strlen (zval) (zval). Value.str.len #define Z_ar Rval (Zval) (zval). value.ht #define Z_objval (zval) (zval). Value.obj #define Z_obj_handle (zval) z_objval (zval). h Andle #define Z_OBJ_HT (zval) z_objval (zval) Handlers #define Z_OBJCE (Zval) zend_get_class_entry (& (Zval) TSR MLS_CC) #define Z_OBJPROP (Zval) z_obj_ht ((Zval))->get_properties (& (Zval) tsrmls_cc) #define Z_obj_handler ( Zval, HF) Z_obj_ht ((zval))->hf#define Z_resval (zval) (zval). Value.lval #define Z_OBJDEBUG (zval,is_tmp) (Z_OBJ_HAND LER ((zval), get_debug_info)? Z_obj_handler ((zval), Get_debug_info) (& (Zval), &is_tmp tsrmls_cc):(Is_tmp=0,z_obj_handler ((zval), get_ Properties)? Z_objprop (zval): NULL)) #define Z_LVAL_P (zval_p) z_lval (*zval_p) #define Z_BVAL_P (zval_p) z_bval (*zval_p) #defi NE z_Dval_p (zval_p) z_dval (*zval_p) #define Z_STRVAL_P (zval_p) z_strval (*zval_p) #define Z_STRLEN_P (zval_p) Z_st Rlen (*zval_p) #define Z_ARRVAL_P (zval_p) z_arrval (*zval_p) #define Z_OBJPROP_P (zval_p) z_objprop (*zval_p) #define Z_ Objce_p (zval_p) z_objce (*zval_p) #define Z_RESVAL_P (zval_p) z_resval (*zval_p) #define Z_OBJVAL_P (zval_p) z_o Bjval (*zval_p) #define Z_OBJ_HANDLE_P (zval_p) z_obj_handle (*zval_p) #define Z_OBJ_HT_P (zval_p) z_obj_ht (*zval_p) # Define Z_OBJ_HANDLER_P (Zval_p, h) z_obj_handler (*zval_p, h) #define Z_OBJDEBUG_P (zval_p,is_tmp) z_objdebug (*zval_p,is _TMP) #define Z_LVAL_PP (ZVAL_PP) z_lval (**zval_pp) #define Z_BVAL_PP (ZVAL_PP) z_bval (**zval_pp) #define Z_DVAL_PP (Z VAL_PP) Z_dval (**zval_pp) #define Z_STRVAL_PP (ZVAL_PP) z_strval (**zval_pp) #define Z_STRLEN_PP (ZVAL_PP) Z_strlen ( **ZVAL_PP) #define Z_ARRVAL_PP (ZVAL_PP) z_arrval (**zval_pp) #define Z_OBJPROP_PP (ZVAL_PP) Z_objprop (**ZVAL_PP) # Define Z_OBJCE_PP (ZVAL_PP) Z_objce (**ZVAL_PP) #define Z_RESVAL_PP (ZVAL_PP) z_resval (**zval_pp) #define Z_OBJVAL_PP (ZVAL_PP) z_objval (**zval_pp) #define Z _OBJ_HANDLE_PP (zval_p) z_obj_handle (**zval_p) #define Z_OBJ_HT_PP (zval_p) z_obj_ht (**zval_p) #define Z_obj_handler_ PP (zval_p, h) z_obj_handler (**zval_p, h) #define Z_OBJDEBUG_PP (zval_pp,is_tmp) z_objdebug (**zval_pp,is_tmp) #define Z_ TYPE (Zval) (zval). Type#define z_type_p (zval_p) z_type (*zval_p) #define Z_TYPE_PP (ZVAL_PP) z_type (**ZVAL_PP)
Functions in-depth PHP kernel