Jump to content

Archived

This topic is now archived and is closed to further replies.

daeken

call_user_function_ex() documentation

Recommended Posts

Ok... the documentation on call_user_function_ex() in the manual (if it\'s still there) is outdated and incomplete... here\'s my version.

 

ZEND_API int call_user_function_ex(HashTable *function_table, zval **object_pp, zval *function_name, zval **retval_ptr_ptr, zend_uint param_count, zval **params[], int no_seperation, HashTable *symbol_table TSRMLS_DC);

 

function_table is the hash table where the function you wish to call is located. If you\'re using object_pp, set this to NULL. If the function is global, most likely it\'s located in the hash table returned by the macro CG() with the parameter `function_table\', i.e.

CG(function_table)

.

 

object_pp is a pointer to a zval pointer where an initialized object is located. If you use this, set function_table to NULL, as previously noted.

 

function_name is a pointer to a zval which contains the name of the function in string form.

 

retval_ptr_ptr is a pointer to a zval pointer which will contain the return value of the function. The zval passed doesn\'t need to be initialized, and it may cause problems if you initialize it when it\'s not neccesary. You must always pass a real pointer to a zval pointer, you may not use NULL for this as it will cause a segmentation fault.

 

param_count is the number of parameters you wish to pass to the function being called.

 

params is an array of pointers to zval pointers. Note: this is _not_ a PHP/zval array, it is a C array. Example:

zval *foo; zval *bar; zval **params[2]; params[0] = &foo; params[1] = bar;

 

no_seperation is either 1 or 0, 0 being no zval seperation, 1 enabling zval seperation. Anyone know what this is? I haven\'t been able to find out anywhere :P

 

symbol_table is the hash table for symbols. I currently don\'t know what this is, so when I find out, I\'ll edit the post and put it here :)

 

After the symbol_table parameter, you should put TSRMLS_CC to make it threadsafe.

 

call_user_function_ex() returns FAILURE if it couldn\'t call the function, and SUCCESS if it could.

 

Here\'s an example calling a global function with no parameters:


PHP_FUNCTION(example_call_func)

{

 zval *function;

 MAKE_STD_ZVAL(function);

 ZVAL_STRING(function, "example_usermode_function", 1);

 if(call_user_function_ex(CG(function_table), NULL, function, &return_value, 0, NULL, 0, NULL TSRMLS_CC) != FAILURE)

   return;

 else

   RETURN_FALSE;

}

 

Now the same example with 1 parameter being passed to the usermode function:


PHP_FUNCTION(example_call_func)

{

 zval *function, *num;

 zval **params[1]; // Creates array of parameters with 1 element allocated.

 MAKE_STD_ZVAL(function);

 MAKE_STD_ZVAL(num);

 ZVAL_STRING(function, "example_usermode_function", 1);

 ZVAL_LONG(num, 15);

 params[0] = num; // Makes num the first parameter to example_usermode_function().

 if(call_user_function_ex(CG(function_table), NULL, function, &return_value, 1, params, 0, NULL TSRMLS_CC) != FAILURE)

   return;

 else

   RETURN_FALSE;

}

 

And now an example taking an object and method name as parameters and calling the method:


PHP_FUNCTION(example_call_func)

{

 zval *object, *method;

 if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "zz", &object, &method) == FAILURE)

 {

   zend_error(E_WARNING, "You must pass an object and a method name to example_call_func");

   return;

 }

 if(call_user_function_ex(NULL, &object, method, &return_value, 0, NULL, 0, NULL TSRMLS_CC) != FAILURE)

   return;

 else

   RETURN_FALSE;

}

 

Hopefully you found this useful. If you have any questions, feel free to post here and ask :)

 

Happy hacking,

Lord Daeken M. BlackBlade

(Cody Brocious)

Share this post


Link to post
Share on other sites

ah, excellent. Now I understand a few more of those cryptic parameters :)

Share this post


Link to post
Share on other sites

×

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.