[svn:PHP-Sandwich] rev 1042 - in PHP-Sandwich/trunk: . t
[email protected] 6 May 2005 17:46:14 -0000
| Newsgroups | perl.php.sandwich.dev |
|---|---|
| Message-ID | <[email protected]> |
Author: gschlossnagle
Date: Fri May 6 10:46:14 2005
New Revision: 1042
Modified:
PHP-Sandwich/trunk/phpfuncs.c
PHP-Sandwich/trunk/t/15.t
Log:
enable overloading style calls to perl methods from
PHP
Modified: PHP-Sandwich/trunk/phpfuncs.c
==============================================================================
--- PHP-Sandwich/trunk/phpfuncs.c (original)
+++ PHP-Sandwich/trunk/phpfuncs.c Fri May 6 10:46:14 2005
@@ -28,7 +28,7 @@
}
static zval *
-perl_dim_read(zval *obj, zval *offset, int type TSRMLS_DC)
+sandwich_dim_read(zval *obj, zval *offset, int type TSRMLS_DC)
{
SV *value;
zval *return_value;
@@ -75,7 +75,7 @@
}
static void
-perl_dim_write(zval *obj, zval *offset, zval *value TSRMLS_DC)
+sandwich_dim_write(zval *obj, zval *offset, zval *value TSRMLS_DC)
{
return;
}
@@ -181,46 +181,141 @@
SV *sparam;
SV *prv;
pTHX;
- dSP;
+ pl = zend_object_store_get_object(getThis() TSRMLS_CC);
+ aTHX = pl->perl;
- argc = ZEND_NUM_ARGS();
- if(argc < 1) {
- WRONG_PARAM_COUNT;
- }
- args = (zval ***) safe_emalloc(sizeof(zval **), argc, 0);
- if(zend_get_parameters_array_ex(argc, args) == FAILURE) {
+ {
+ dSP;
+
+ argc = ZEND_NUM_ARGS();
+ if(argc < 1) {
+ WRONG_PARAM_COUNT;
+ }
+ args = (zval ***) safe_emalloc(sizeof(zval **), argc, 0);
+ if(zend_get_parameters_array_ex(argc, args) == FAILURE) {
+ efree(args);
+ WRONG_PARAM_COUNT;
+ }
+ name = Z_STRVAL_PP(args[0]);
+
+ ENTER;
+ SAVETMPS;
+ PUSHMARK(SP);
+ for(i = 1; i < argc; i++) {
+ var = sv_2mortal(newSVzval(*args[i], SandwichG(php)));
+ XPUSHs(var);
+ }
+ PUTBACK;
+ call_pv(name, G_SCALAR);
+ SPAGAIN;
+ prv = POPs;
+ /*
+ if(coe && SvTRUE(ERRSV)) {
+ croak(SvPVx(ERRSV, n_a));
+ }
+ */
+ SvREFCNT_inc(prv);
+ PUTBACK;
+ retval = SvZval(prv);
+ RETURN_ZVAL(retval, 1, 0);
+ SvREFCNT_dec(prv);
+ FREETMPS;
+ LEAVE;
efree(args);
- WRONG_PARAM_COUNT;
}
- name = Z_STRVAL_PP(args[0]);
-
+}
+
+static int sandwich_call_method(char *method, INTERNAL_FUNCTION_PARAMETERS)
+{
+ struct plobj *pl;
+ SV *var;
+ zval *retval;
+ char *name;
+ int namelen;
+ zval *param;
+ zval ***args;
+ SV *sparam;
+ int argc, i;
+ SV *prv;
+ pTHX;
+
pl = zend_object_store_get_object(getThis() TSRMLS_CC);
aTHX = pl->perl;
-
- ENTER;
- SAVETMPS;
- PUSHMARK(SP);
- for(i = 1; i < argc; i++) {
- var = sv_2mortal(newSVzval(*args[i], SandwichG(php)));
- XPUSHs(var);
- }
- PUTBACK;
- call_pv(name, G_SCALAR);
- SPAGAIN;
- prv = POPs;
- /*
- if(coe && SvTRUE(ERRSV)) {
- croak(SvPVx(ERRSV, n_a));
+ {
+ dSP;
+
+ argc = ZEND_NUM_ARGS();
+ args = (zval ***) safe_emalloc(sizeof(zval **), argc, 0);
+ if(zend_get_parameters_array_ex(argc, args) == FAILURE) {
+ efree(args);
+ WRONG_PARAM_COUNT;
+ }
+
+ pl = zend_object_store_get_object(getThis() TSRMLS_CC);
+ aTHX = pl->perl;
+
+ ENTER;
+ SAVETMPS;
+ PUSHMARK(SP);
+ for(i = 0; i < argc; i++) {
+ var = newSVzval(*args[i], SandwichG(php));
+ var = sv_2mortal(var);
+ XPUSHs(var);
+ }
+ PUTBACK;
+ call_pv(method, G_SCALAR);
+ SPAGAIN;
+ prv = POPs;
+ /*
+ if(coe && SvTRUE(ERRSV)) {
+ croak(SvPVx(ERRSV, n_a));
+ }
+ */
+ SvREFCNT_inc(prv);
+ PUTBACK;
+ retval = SvZval(prv);
+ RETURN_ZVAL(retval, 1, 0);
+ SvREFCNT_dec(prv);
+ FREETMPS;
+ LEAVE;
+ efree(args);
}
- */
- SvREFCNT_inc(prv);
- PUTBACK;
- retval = SvZval(prv);
- RETURN_ZVAL(retval, 1, 0);
- SvREFCNT_dec(prv);
- FREETMPS;
- LEAVE;
- efree(args);
+}
+
+static PHP_FUNCTION(sandwich_method_handler)
+{
+ sandwich_call_method(
+ ((zend_internal_function*)EG(function_state_ptr)->function)->function_name,
+ INTERNAL_FUNCTION_PARAM_PASSTHRU);
+}
+
+static union _zend_function *sandwich_get_method(zval **object_ptr, char *name, int len TSRMLS_DC)
+{
+ zval *object = *object_ptr;
+ zend_internal_function f, *fptr = NULL;
+ union _zend_function *func;
+ struct plobj *pl;
+ char *lc_method_name;
+
+ lc_method_name = emalloc(len + 1);
+ zend_str_tolower_copy(lc_method_name, name, len);
+ if (zend_hash_find(&plobj_ce->function_table, lc_method_name, len+1, (void**)&func) == SUCCESS) {
+ efree(lc_method_name);
+ return func;
+ }
+ efree(lc_method_name);
+
+ f.type = ZEND_OVERLOADED_FUNCTION;
+ f.num_args = 0;
+ f.arg_info = NULL;
+ f.scope = plobj_ce;
+ f.fn_flags=0;
+ f.function_name= estrndup(name, len);
+ f.handler= PHP_FN(sandwich_method_handler);
+
+ func = emalloc(sizeof(*func));
+ memcpy(func, &f,sizeof(f));
+ return func;
}
PHP_METHOD(perl, getinstance)
@@ -396,8 +491,10 @@
memcpy(&plobj_handlers, zend_get_std_object_handlers(),
sizeof(plobj_handlers));
- plobj_handlers.read_dimension = perl_dim_read;
- plobj_handlers.write_dimension = perl_dim_write;
+ plobj_handlers.read_dimension = sandwich_dim_read;
+ plobj_handlers.write_dimension = sandwich_dim_write;
+ plobj_handlers.get_method = sandwich_get_method;
+ plobj_handlers.call_method = sandwich_call_method;
return SUCCESS;
}
Modified: PHP-Sandwich/trunk/t/15.t
==============================================================================
--- PHP-Sandwich/trunk/t/15.t (original)
+++ PHP-Sandwich/trunk/t/15.t Fri May 6 10:46:14 2005
@@ -1,6 +1,6 @@
#!/opt/ecelerity/3rdParty/bin/perl
use strict;
-use Test::More tests => 5;
+use Test::More tests => 7;
BEGIN {
diag "Testing Perl::call";
@@ -24,3 +24,11 @@
/), 'Test use of Perl::call';
is $rv, 'hello world', "Check return value of call";
+
+ok $rv = $p->eval(q/
+ $perl = Perl::getInstance();
+ $rv = $perl->hello('world');
+ return $rv;
+/), 'Test use of Perl::call via PHP overloading';
+
+is $rv, 'hello world', "Check return value of call";