@@ -136,11 +136,11 @@ int openpty(int *master, int *slave, char *name, struct termios *termp, struct w
136136
137137static int le_proc_open ; /* Resource number for `proc` resources */
138138
139- /* {{{ _php_array_to_envp
139+ /* {{{ php_array_to_envp
140140 * Process the `environment` argument to `proc_open`
141141 * Convert into data structures which can be passed to underlying OS APIs like `exec` on POSIX or
142142 * `CreateProcessW` on Win32 */
143- static php_process_env _php_array_to_envp ( zval * environment )
143+ ZEND_ATTRIBUTE_NONNULL static php_process_env php_array_to_envp ( const HashTable * environment )
144144{
145145 zval * element ;
146146 php_process_env env ;
@@ -154,13 +154,9 @@ static php_process_env _php_array_to_envp(zval *environment)
154154
155155 memset (& env , 0 , sizeof (env ));
156156
157- if (!environment ) {
158- return env ;
159- }
160-
161- uint32_t cnt = zend_hash_num_elements (Z_ARRVAL_P (environment ));
157+ uint32_t cnt = zend_hash_num_elements (environment );
162158
163- if (cnt < 1 ) {
159+ if (cnt == 0 ) {
164160#ifndef PHP_WIN32
165161 env .envarray = (char * * ) ecalloc (1 , sizeof (char * ));
166162#endif
@@ -172,7 +168,7 @@ static php_process_env _php_array_to_envp(zval *environment)
172168 zend_hash_init (env_hash , cnt , NULL , NULL , 0 );
173169
174170 /* first, we have to get the size of all the elements in the hash */
175- ZEND_HASH_FOREACH_STR_KEY_VAL (Z_ARRVAL_P ( environment ) , key , element ) {
171+ ZEND_HASH_FOREACH_STR_KEY_VAL (environment , key , element ) {
176172 str = zval_get_string (element );
177173
178174 if (ZSTR_LEN (str ) == 0 ) {
@@ -221,7 +217,7 @@ static php_process_env _php_array_to_envp(zval *environment)
221217/* }}} */
222218
223219/* {{{ _php_free_envp
224- * Free the structures allocated by `_php_array_to_envp` */
220+ * Free the structures allocated by php_array_to_envp */
225221static void _php_free_envp (php_process_env env )
226222{
227223#ifndef PHP_WIN32
@@ -506,7 +502,7 @@ typedef struct _descriptorspec_item {
506502 int mode_flags ; /* mode for opening FDs: r/o, r/w, binary (on Win32), etc */
507503} descriptorspec_item ;
508504
509- static zend_string * get_valid_arg_string (zval * zv , int elem_num ) {
505+ static zend_string * get_valid_arg_string (zval * zv , uint32_t elem_num ) {
510506 zend_string * str = zval_get_string (zv );
511507 if (!str ) {
512508 return NULL ;
@@ -518,7 +514,7 @@ static zend_string *get_valid_arg_string(zval *zv, int elem_num) {
518514 return NULL ;
519515 }
520516
521- if (strlen ( ZSTR_VAL ( str )) != ZSTR_LEN (str )) {
517+ if (zend_str_has_nul_byte (str )) {
522518 zend_value_error ("Command array element %d contains a null byte" , elem_num );
523519 zend_string_release (str );
524520 return NULL ;
@@ -630,7 +626,7 @@ static zend_string *create_win_command_from_args(HashTable *args)
630626 zval * arg_zv ;
631627 bool is_prog_name = true;
632628 bool is_cmd_execution = false;
633- int elem_num = 0 ;
629+ uint32_t elem_num = 0 ;
634630
635631 ZEND_HASH_FOREACH_VAL (args , arg_zv ) {
636632 zend_string * arg_str = get_valid_arg_string (arg_zv , ++ elem_num );
@@ -778,11 +774,11 @@ static zend_result convert_command_to_use_shell(wchar_t **cmdw, size_t cmdw_len)
778774
779775#ifndef PHP_WIN32
780776/* Convert command parameter array passed as first argument to `proc_open` into command string */
781- static zend_string * get_command_from_array (HashTable * array , char * * * argv , int num_elems )
777+ static zend_string * get_command_from_array (const HashTable * array , char * * * argv , uint32_t num_elems )
782778{
783779 zval * arg_zv ;
784780 zend_string * command = NULL ;
785- int i = 0 ;
781+ uint32_t i = 0 ;
786782
787783 * argv = safe_emalloc (sizeof (char * ), num_elems + 1 , 0 );
788784
@@ -810,16 +806,16 @@ static zend_string* get_command_from_array(HashTable *array, char ***argv, int n
810806}
811807#endif
812808
813- static descriptorspec_item * alloc_descriptor_array (HashTable * descriptorspec )
809+ static descriptorspec_item * alloc_descriptor_array (const HashTable * descriptorspec )
814810{
815811 uint32_t ndescriptors = zend_hash_num_elements (descriptorspec );
816812 return ecalloc (ndescriptors , sizeof (descriptorspec_item ));
817813}
818814
819- static zend_string * get_string_parameter (zval * array , int index , char * param_name )
815+ static zend_string * get_string_parameter (const HashTable * ht , unsigned int index , const char * param_name )
820816{
821817 zval * array_item ;
822- if ((array_item = zend_hash_index_find (Z_ARRVAL_P ( array ) , index )) == NULL ) {
818+ if ((array_item = zend_hash_index_find (ht , index )) == NULL ) {
823819 zend_value_error ("Missing %s" , param_name );
824820 return NULL ;
825821 }
@@ -995,7 +991,7 @@ static zend_result dup_proc_descriptor(php_file_descriptor_t from, php_file_desc
995991}
996992
997993static zend_result redirect_proc_descriptor (descriptorspec_item * desc , int target ,
998- descriptorspec_item * descriptors , int ndesc , int nindex )
994+ const descriptorspec_item * descriptors , int ndesc , int nindex )
999995{
1000996 php_file_descriptor_t redirect_to = PHP_INVALID_FD ;
1001997
@@ -1030,9 +1026,9 @@ static zend_result redirect_proc_descriptor(descriptorspec_item *desc, int targe
10301026}
10311027
10321028/* Process one item from `$descriptorspec` argument to `proc_open` */
1033- static zend_result set_proc_descriptor_from_array (zval * descitem , descriptorspec_item * descriptors ,
1029+ static zend_result set_proc_descriptor_from_array (const HashTable * ht , descriptorspec_item * descriptors ,
10341030 int ndesc , int nindex , int * pty_master_fd , int * pty_slave_fd ) {
1035- zend_string * ztype = get_string_parameter (descitem , 0 , "handle qualifier" );
1031+ zend_string * ztype = get_string_parameter (ht , 0 , "handle qualifier" );
10361032 if (!ztype ) {
10371033 return FAILURE ;
10381034 }
@@ -1042,7 +1038,7 @@ static zend_result set_proc_descriptor_from_array(zval *descitem, descriptorspec
10421038
10431039 if (zend_string_equals_literal (ztype , "pipe" )) {
10441040 /* Set descriptor to pipe */
1045- zmode = get_string_parameter (descitem , 1 , "mode parameter for 'pipe'" );
1041+ zmode = get_string_parameter (ht , 1 , "mode parameter for 'pipe'" );
10461042 if (zmode == NULL ) {
10471043 goto finish ;
10481044 }
@@ -1052,16 +1048,16 @@ static zend_result set_proc_descriptor_from_array(zval *descitem, descriptorspec
10521048 retval = set_proc_descriptor_to_socket (& descriptors [ndesc ]);
10531049 } else if (zend_string_equals (ztype , ZSTR_KNOWN (ZEND_STR_FILE ))) {
10541050 /* Set descriptor to file */
1055- if ((zfile = get_string_parameter (descitem , 1 , "file name parameter for 'file'" )) == NULL ) {
1051+ if ((zfile = get_string_parameter (ht , 1 , "file name parameter for 'file'" )) == NULL ) {
10561052 goto finish ;
10571053 }
1058- if ((zmode = get_string_parameter (descitem , 2 , "mode parameter for 'file'" )) == NULL ) {
1054+ if ((zmode = get_string_parameter (ht , 2 , "mode parameter for 'file'" )) == NULL ) {
10591055 goto finish ;
10601056 }
10611057 retval = set_proc_descriptor_to_file (& descriptors [ndesc ], zfile , zmode );
10621058 } else if (zend_string_equals_literal (ztype , "redirect" )) {
10631059 /* Redirect descriptor to whatever another descriptor is set to */
1064- zval * ztarget = zend_hash_index_find_deref (Z_ARRVAL_P ( descitem ) , 1 );
1060+ zval * ztarget = zend_hash_index_find_deref (ht , 1 );
10651061 if (!ztarget ) {
10661062 zend_value_error ("Missing redirection target" );
10671063 goto finish ;
@@ -1116,7 +1112,7 @@ static zend_result set_proc_descriptor_from_resource(zval *resource, descriptors
11161112
11171113#ifndef PHP_WIN32
11181114#if defined(USE_POSIX_SPAWN )
1119- static zend_result close_parentends_of_pipes (posix_spawn_file_actions_t * actions , descriptorspec_item * descriptors , int ndesc )
1115+ static zend_result close_parentends_of_pipes (posix_spawn_file_actions_t * actions , const descriptorspec_item * descriptors , int ndesc )
11201116{
11211117 int r ;
11221118 for (int i = 0 ; i < ndesc ; i ++ ) {
@@ -1200,9 +1196,10 @@ PHP_FUNCTION(proc_open)
12001196 HashTable * command_ht ;
12011197 HashTable * descriptorspec ; /* Mandatory argument */
12021198 zval * pipes ; /* Mandatory argument */
1203- char * cwd = NULL ; /* Optional argument */
1204- size_t cwd_len = 0 ; /* Optional argument */
1205- zval * environment = NULL , * other_options = NULL ; /* Optional arguments */
1199+ char * cwd = NULL ; /* Optional argument */
1200+ size_t cwd_len = 0 ; /* Optional argument */
1201+ HashTable * environment = NULL ; /* Optional arguments */
1202+ zval * other_options = NULL ; /* Optional arguments */
12061203
12071204 php_process_env env ;
12081205 int ndesc = 0 ;
@@ -1239,7 +1236,7 @@ PHP_FUNCTION(proc_open)
12391236 Z_PARAM_ZVAL (pipes )
12401237 Z_PARAM_OPTIONAL
12411238 Z_PARAM_STRING_OR_NULL (cwd , cwd_len )
1242- Z_PARAM_ARRAY_OR_NULL (environment )
1239+ Z_PARAM_ARRAY_HT_OR_NULL (environment )
12431240 Z_PARAM_ARRAY_OR_NULL (other_options )
12441241 ZEND_PARSE_PARAMETERS_END ();
12451242
@@ -1282,7 +1279,7 @@ PHP_FUNCTION(proc_open)
12821279#endif
12831280
12841281 if (environment ) {
1285- env = _php_array_to_envp (environment );
1282+ env = php_array_to_envp (environment );
12861283 }
12871284
12881285 descriptors = alloc_descriptor_array (descriptorspec );
@@ -1302,7 +1299,7 @@ PHP_FUNCTION(proc_open)
13021299 goto exit_fail ;
13031300 }
13041301 } else if (Z_TYPE_P (descitem ) == IS_ARRAY ) {
1305- if (set_proc_descriptor_from_array (descitem , descriptors , ndesc , (int )nindex ,
1302+ if (set_proc_descriptor_from_array (Z_ARRVAL_P ( descitem ) , descriptors , ndesc , (int )nindex ,
13061303 & pty_master_fd , & pty_slave_fd ) == FAILURE ) {
13071304 goto exit_fail ;
13081305 }
0 commit comments