60
60
61
61
ZEND_DECLARE_MODULE_GLOBALS (ffi )
62
62
63
- typedef enum _zend_ffi_tag_kind {
64
- ZEND_FFI_TAG_ENUM ,
65
- ZEND_FFI_TAG_STRUCT ,
66
- ZEND_FFI_TAG_UNION
67
- } zend_ffi_tag_kind ;
68
-
69
63
static const char * zend_ffi_tag_kind_name [3 ] = {"enum" , "struct" , "union" };
70
64
71
-
72
- typedef struct _zend_ffi_tag {
73
- zend_ffi_tag_kind kind ;
74
- zend_ffi_type * type ;
75
- } zend_ffi_tag ;
76
-
77
65
#include "ffi_arginfo.h"
78
66
79
- typedef enum _zend_ffi_symbol_kind {
80
- ZEND_FFI_SYM_TYPE ,
81
- ZEND_FFI_SYM_CONST ,
82
- ZEND_FFI_SYM_VAR ,
83
- ZEND_FFI_SYM_FUNC
84
- } zend_ffi_symbol_kind ;
85
-
86
- typedef struct _zend_ffi_symbol {
87
- zend_ffi_symbol_kind kind ;
88
- bool is_const ;
89
- zend_ffi_type * type ;
90
- union {
91
- void * addr ;
92
- int64_t value ;
93
- };
94
- } zend_ffi_symbol ;
95
-
96
- typedef struct _zend_ffi_scope {
97
- HashTable * symbols ;
98
- HashTable * tags ;
99
- } zend_ffi_scope ;
100
-
101
67
typedef struct _zend_ffi {
102
68
zend_object std ;
103
69
DL_HANDLE lib ;
104
70
HashTable * symbols ;
105
71
HashTable * tags ;
106
- bool persistent ;
72
+ bool persistent ;
107
73
} zend_ffi ;
108
74
109
75
#define ZEND_FFI_TYPE_MAKE_OWNED (t ) \
@@ -128,7 +94,7 @@ static zend_internal_function zend_ffi_cast_fn;
128
94
static zend_internal_function zend_ffi_type_fn ;
129
95
130
96
/* forward declarations */
131
- //??? static void _zend_ffi_type_dtor(zend_ffi_type *type);
97
+ static void _zend_ffi_type_dtor (zend_ffi_type * type );
132
98
static void zend_ffi_finalize_type (zend_ffi_dcl * dcl );
133
99
static bool zend_ffi_is_same_type (zend_ffi_type * type1 , zend_ffi_type * type2 );
134
100
static zend_ffi_type * zend_ffi_remember_type (zend_ffi_type * type );
@@ -2205,7 +2171,7 @@ static zend_object *zend_ffi_new(zend_class_entry *class_type) /* {{{ */
2205
2171
}
2206
2172
/* }}} */
2207
2173
2208
- ZEND_API void _zend_ffi_type_dtor (zend_ffi_type * type ) /* {{{ */
2174
+ static void _zend_ffi_type_dtor (zend_ffi_type * type ) /* {{{ */
2209
2175
{
2210
2176
type = ZEND_FFI_TYPE (type );
2211
2177
@@ -2885,6 +2851,7 @@ ZEND_METHOD(FFI, cdef) /* {{{ */
2885
2851
DL_HANDLE handle = NULL ;
2886
2852
char * err ;
2887
2853
void * addr ;
2854
+ bool persistent = false;
2888
2855
2889
2856
ZEND_FFI_VALIDATE_API_RESTRICTION ();
2890
2857
ZEND_PARSE_PARAMETERS_START (0 , 2 )
@@ -2922,9 +2889,14 @@ ZEND_METHOD(FFI, cdef) /* {{{ */
2922
2889
FFI_G (tags ) = NULL ;
2923
2890
2924
2891
if (code && ZSTR_LEN (code )) {
2925
- if (zend_ffi_cache_cdef_get ) {
2926
- ffi = zend_ffi_cache_cdef_get (code );
2927
- if (ffi ) {
2892
+ if (zend_ffi_cache_scope_get ) {
2893
+ zend_ffi_scope * scope = zend_ffi_cache_scope_get (code );
2894
+ if (scope ) {
2895
+ ffi = (zend_ffi * )zend_ffi_new (zend_ffi_ce );
2896
+ ffi -> lib = handle ;
2897
+ ffi -> symbols = scope -> symbols ;
2898
+ ffi -> tags = scope -> tags ;
2899
+ ffi -> persistent = true;
2928
2900
RETURN_OBJ (& ffi -> std );
2929
2901
}
2930
2902
}
@@ -2971,16 +2943,37 @@ ZEND_METHOD(FFI, cdef) /* {{{ */
2971
2943
}
2972
2944
} ZEND_HASH_FOREACH_END ();
2973
2945
}
2946
+
2947
+ if (zend_ffi_cache_scope_add ) {
2948
+ zend_ffi_scope scope , * cached_scope ;
2949
+
2950
+ scope .symbols = FFI_G (symbols );
2951
+ scope .tags = FFI_G (tags );
2952
+ cached_scope = zend_ffi_cache_scope_add (code , & scope );
2953
+ if (cached_scope ) {
2954
+ if (FFI_G (symbols )) {
2955
+ zend_hash_destroy (FFI_G (symbols ));
2956
+ efree (FFI_G (symbols ));
2957
+ FFI_G (symbols ) = NULL ;
2958
+ }
2959
+ if (FFI_G (tags )) {
2960
+ zend_hash_destroy (FFI_G (tags ));
2961
+ efree (FFI_G (tags ));
2962
+ FFI_G (tags ) = NULL ;
2963
+ }
2964
+ FFI_G (symbols ) = cached_scope -> symbols ;
2965
+ FFI_G (tags ) = cached_scope -> tags ;
2966
+ persistent = true;
2967
+ }
2968
+ }
2969
+
2974
2970
}
2975
2971
2976
2972
ffi = (zend_ffi * )zend_ffi_new (zend_ffi_ce );
2977
2973
ffi -> lib = handle ;
2978
2974
ffi -> symbols = FFI_G (symbols );
2979
2975
ffi -> tags = FFI_G (tags );
2980
-
2981
- if (zend_ffi_cache_cdef_add ) {
2982
- ffi = zend_ffi_cache_cdef_add (code , ffi );
2983
- }
2976
+ ffi -> persistent = persistent ;
2984
2977
2985
2978
FFI_G (symbols ) = NULL ;
2986
2979
FFI_G (tags ) = NULL ;
@@ -3711,6 +3704,7 @@ ZEND_METHOD(FFI, new) /* {{{ */
3711
3704
3712
3705
if (type_def ) {
3713
3706
zend_ffi_dcl dcl = ZEND_FFI_ATTR_INIT ;
3707
+ zend_ffi_dcl * cached_dcl ;
3714
3708
3715
3709
if (!is_static_call ) {
3716
3710
zend_ffi * ffi = (zend_ffi * )Z_OBJ (EX (This ));
@@ -3726,8 +3720,8 @@ ZEND_METHOD(FFI, new) /* {{{ */
3726
3720
FFI_G (default_type_attr ) = 0 ;
3727
3721
3728
3722
if (zend_ffi_cache_type_get
3729
- && zend_ffi_cache_type_get ( type_def , & dcl ) == SUCCESS ) {
3730
- /* pass */
3723
+ && ( cached_dcl = zend_ffi_cache_type_get ( type_def )) ) {
3724
+ memcpy ( & dcl , cached_dcl , sizeof ( zend_ffi_dcl ));
3731
3725
} else if (zend_ffi_parse_type (ZSTR_VAL (type_def ), ZSTR_LEN (type_def ), & dcl ) == FAILURE ) {
3732
3726
zend_ffi_type_dtor (dcl .type );
3733
3727
if (clean_tags && FFI_G (tags )) {
@@ -3754,7 +3748,13 @@ ZEND_METHOD(FFI, new) /* {{{ */
3754
3748
FFI_G (tags ) = NULL ;
3755
3749
3756
3750
if (zend_ffi_cache_type_add ) {
3757
- zend_ffi_cache_type_add (type_def , & dcl );
3751
+ cached_dcl = zend_ffi_cache_type_add (type_def , & dcl );
3752
+ if (cached_dcl ) {
3753
+ if (ZEND_FFI_TYPE_IS_OWNED (dcl .type )) {
3754
+ _zend_ffi_type_dtor (dcl .type );
3755
+ }
3756
+ memcpy (& dcl , cached_dcl , sizeof (zend_ffi_dcl ));
3757
+ }
3758
3758
}
3759
3759
}
3760
3760
@@ -3868,6 +3868,7 @@ ZEND_METHOD(FFI, cast) /* {{{ */
3868
3868
3869
3869
if (type_def ) {
3870
3870
zend_ffi_dcl dcl = ZEND_FFI_ATTR_INIT ;
3871
+ zend_ffi_dcl * cached_dcl ;
3871
3872
3872
3873
if (!is_static_call ) {
3873
3874
zend_ffi * ffi = (zend_ffi * )Z_OBJ (EX (This ));
@@ -3883,8 +3884,8 @@ ZEND_METHOD(FFI, cast) /* {{{ */
3883
3884
FFI_G (default_type_attr ) = 0 ;
3884
3885
3885
3886
if (zend_ffi_cache_type_get
3886
- && zend_ffi_cache_type_get ( type_def , & dcl ) == SUCCESS ) {
3887
- /* pass */
3887
+ && ( cached_dcl = zend_ffi_cache_type_get ( type_def )) ) {
3888
+ memcpy ( & dcl , cached_dcl , sizeof ( zend_ffi_dcl ));
3888
3889
} else if (zend_ffi_parse_type (ZSTR_VAL (type_def ), ZSTR_LEN (type_def ), & dcl ) == FAILURE ) {
3889
3890
zend_ffi_type_dtor (dcl .type );
3890
3891
if (clean_tags && FFI_G (tags )) {
@@ -3911,7 +3912,13 @@ ZEND_METHOD(FFI, cast) /* {{{ */
3911
3912
FFI_G (tags ) = NULL ;
3912
3913
3913
3914
if (zend_ffi_cache_type_add ) {
3914
- zend_ffi_cache_type_add (type_def , & dcl );
3915
+ cached_dcl = zend_ffi_cache_type_add (type_def , & dcl );
3916
+ if (cached_dcl ) {
3917
+ if (ZEND_FFI_TYPE_IS_OWNED (dcl .type )) {
3918
+ _zend_ffi_type_dtor (dcl .type );
3919
+ }
3920
+ memcpy (& dcl , cached_dcl , sizeof (zend_ffi_dcl ));
3921
+ }
3915
3922
}
3916
3923
}
3917
3924
@@ -4033,6 +4040,7 @@ ZEND_METHOD(FFI, type) /* {{{ */
4033
4040
{
4034
4041
zend_ffi_ctype * ctype ;
4035
4042
zend_ffi_dcl dcl = ZEND_FFI_ATTR_INIT ;
4043
+ zend_ffi_dcl * cached_dcl ;
4036
4044
zend_string * type_def ;
4037
4045
bool is_static_call = Z_TYPE (EX (This )) != IS_OBJECT ;
4038
4046
@@ -4062,8 +4070,8 @@ ZEND_METHOD(FFI, type) /* {{{ */
4062
4070
FFI_G (default_type_attr ) = 0 ;
4063
4071
4064
4072
if (zend_ffi_cache_type_get
4065
- && zend_ffi_cache_type_get ( type_def , & dcl ) == SUCCESS ) {
4066
- /* pass */
4073
+ && ( cached_dcl = zend_ffi_cache_type_get ( type_def )) ) {
4074
+ memcpy ( & dcl , cached_dcl , sizeof ( zend_ffi_dcl ));
4067
4075
} else if (zend_ffi_parse_type (ZSTR_VAL (type_def ), ZSTR_LEN (type_def ), & dcl ) == FAILURE ) {
4068
4076
zend_ffi_type_dtor (dcl .type );
4069
4077
if (clean_tags && FFI_G (tags )) {
@@ -4089,7 +4097,13 @@ ZEND_METHOD(FFI, type) /* {{{ */
4089
4097
FFI_G (symbols ) = NULL ;
4090
4098
FFI_G (tags ) = NULL ;
4091
4099
if (zend_ffi_cache_type_add ) {
4092
- zend_ffi_cache_type_add (type_def , & dcl );
4100
+ cached_dcl = zend_ffi_cache_type_add (type_def , & dcl );
4101
+ if (cached_dcl ) {
4102
+ if (ZEND_FFI_TYPE_IS_OWNED (dcl .type )) {
4103
+ _zend_ffi_type_dtor (dcl .type );
4104
+ }
4105
+ memcpy (& dcl , cached_dcl , sizeof (zend_ffi_dcl ));
4106
+ }
4093
4107
}
4094
4108
}
4095
4109
0 commit comments