2000-08-26 12:53:14 +00:00
/*
+ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
2001-12-11 15:32:16 +00:00
| PHP Version 4 |
2000-08-26 12:53:14 +00:00
+ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
2001-12-11 15:32:16 +00:00
| Copyright ( c ) 1997 - 2002 The PHP Group |
2000-08-26 12:53:14 +00:00
+ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
| This source file is subject to version 2.02 of the PHP license , |
| that is bundled with this package in the file LICENSE , and is |
| available at through the world - wide - web at |
| http : //www.php.net/license/2_02.txt. |
| If you did not receive a copy of the PHP license and are unable to |
| obtain it through the world - wide - web , please send a note to |
| license @ php . net so we can mail you a copy immediately . |
+ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
| Author : Sam Ruby < rubys @ us . ibm . com > |
2001-05-13 14:15:26 +00:00
| Harald Radi < h . radi @ nme . at > |
2000-08-26 12:53:14 +00:00
+ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +
*/
/*
* This module implements support for Microsoft . Net components .
*/
2001-01-28 03:41:43 +00:00
/*
* 28.1 .2001
* use external unicode conversion functions
*
* harald radi < h . radi @ nme . at >
*/
2000-08-26 12:53:14 +00:00
# ifdef PHP_WIN32
2001-10-26 17:52:41 +00:00
# include <iostream>
2000-08-26 12:53:14 +00:00
# include <math.h>
# include <comdef.h>
2001-08-07 17:18:20 +00:00
extern " C "
{
2000-08-26 12:53:14 +00:00
# include "php.h"
2001-02-02 15:02:05 +00:00
# include "ext/standard/info.h"
2001-01-28 03:41:43 +00:00
}
2000-08-26 12:53:14 +00:00
2001-08-07 17:18:20 +00:00
# include "ext/com/conversion.h"
# include "ext/com/php_COM.h"
2000-08-26 12:53:14 +00:00
# include "Mscoree.h"
# include "mscorlib.h"
using namespace mscorlib ;
static ICorRuntimeHost * pHost ;
static mscorlib : : _AppDomain * pDomain ;
static zend_class_entry dotnet_class_entry ;
2001-02-17 02:16:29 +00:00
static int codepage ;
2000-08-26 12:53:14 +00:00
HRESULT dotnet_init ( ) {
HRESULT hr ;
hr = CoCreateInstance ( CLSID_CorRuntimeHost , NULL , CLSCTX_ALL ,
IID_ICorRuntimeHost , ( void * * ) & pHost ) ;
if ( FAILED ( hr ) ) return hr ;
hr = pHost - > Start ( ) ;
if ( FAILED ( hr ) ) return hr ;
IUnknown * uDomain ;
hr = pHost - > GetDefaultDomain ( & uDomain ) ;
if ( FAILED ( hr ) ) return hr ;
hr = uDomain - > QueryInterface ( __uuidof ( _AppDomain ) , ( void * * ) & pDomain ) ;
if ( FAILED ( hr ) ) return - 1 ;
uDomain - > Release ( ) ;
return ERROR_SUCCESS ;
}
2001-08-07 17:18:20 +00:00
HRESULT dotnet_create ( OLECHAR * assembly , OLECHAR * datatype , comval * obj TSRMLS_DC ) {
2000-08-26 12:53:14 +00:00
HRESULT hr ;
_ObjectHandle * pHandle ;
hr = pDomain - > CreateInstance ( _bstr_t ( assembly ) , _bstr_t ( datatype ) , & pHandle ) ;
if ( FAILED ( hr ) ) return hr ;
if ( ! pHandle ) return hr ;
_variant_t unwrapped ;
hr = pHandle - > Unwrap ( & unwrapped ) ;
pHandle - > Release ( ) ;
if ( FAILED ( hr ) ) return hr ;
2001-08-07 17:18:20 +00:00
php_COM_set ( obj , & unwrapped . pdispVal , TRUE TSRMLS_CC ) ;
2000-08-26 12:53:14 +00:00
return ERROR_SUCCESS ;
}
void dotnet_term ( ) {
if ( pHost ) pHost - > Stop ( ) ;
if ( pHost ) pHost - > Release ( ) ;
if ( pDomain ) pDomain - > Release ( ) ;
pHost = 0 ;
pDomain = 0 ;
}
2001-05-13 14:15:26 +00:00
/* {{{ proto int dotnet_load(string assembly_name [, string datatype_name, int codepage])
2000-08-26 12:53:14 +00:00
Loads a DOTNET module */
2001-05-13 14:15:26 +00:00
PHP_FUNCTION ( dotnet_load )
2000-08-26 12:53:14 +00:00
{
HRESULT hr ;
2003-01-15 02:54:54 +00:00
zval * * assembly_name , * * datatype_name , * * code_page ;
2000-08-26 12:53:14 +00:00
OLECHAR * assembly , * datatype ;
2001-06-24 21:20:23 +00:00
comval * obj ;
2000-08-26 12:53:14 +00:00
2001-05-13 14:15:26 +00:00
switch ( ZEND_NUM_ARGS ( ) )
{
case 2 :
2003-01-15 02:54:54 +00:00
zend_get_parameters_ex ( 2 , & assembly_name , & datatype_name ) ;
2001-05-13 14:15:26 +00:00
codepage = CP_ACP ;
break ;
case 3 :
2003-01-15 02:54:54 +00:00
zend_get_parameters_ex ( 3 , & assembly_name , & datatype_name , & code_page ) ;
2001-05-13 14:15:26 +00:00
2003-01-15 02:54:54 +00:00
convert_to_long_ex ( code_page ) ;
codepage = Z_LVAL_PP ( code_page ) ;
2001-05-13 14:15:26 +00:00
break ;
default :
WRONG_PARAM_COUNT ;
break ;
}
2001-02-17 02:16:29 +00:00
2003-01-15 02:54:54 +00:00
convert_to_string_ex ( assembly_name ) ;
assembly = php_char_to_OLECHAR ( Z_STRVAL_PP ( assembly_name ) , Z_STRLEN_PP ( assembly_name ) , codepage TSRMLS_CC ) ;
2000-08-26 12:53:14 +00:00
2003-01-15 02:54:54 +00:00
convert_to_string_ex ( datatype_name ) ;
datatype = php_char_to_OLECHAR ( Z_STRVAL_PP ( datatype_name ) , Z_STRLEN_PP ( datatype_name ) , codepage TSRMLS_CC ) ;
2000-08-26 12:53:14 +00:00
2001-06-24 21:20:23 +00:00
ALLOC_COM ( obj ) ;
2001-05-02 21:52:12 +00:00
2000-08-26 12:53:14 +00:00
/* obtain IDispatch */
2001-08-07 17:18:20 +00:00
hr = dotnet_create ( assembly , datatype , obj TSRMLS_CC ) ;
2000-08-26 12:53:14 +00:00
efree ( assembly ) ;
efree ( datatype ) ;
if ( FAILED ( hr ) ) {
char * error_message ;
2001-08-07 17:18:20 +00:00
error_message = php_COM_error_message ( hr TSRMLS_CC ) ;
2003-01-19 00:45:53 +00:00
php_error_docref ( NULL TSRMLS_CC , E_WARNING , " Error obtaining .Net class for %s in assembly %s: %s " , datatype_name - > value . str . val , assembly_name - > value . str . val , error_message ) ;
2000-08-26 12:53:14 +00:00
LocalFree ( error_message ) ;
2001-05-02 21:52:12 +00:00
efree ( obj ) ;
2000-08-26 12:53:14 +00:00
RETURN_FALSE ;
}
2001-06-24 21:20:23 +00:00
if ( C_DISPATCH ( obj ) = = NULL ) {
2003-01-19 00:45:53 +00:00
php_error_docref ( NULL TSRMLS_CC , E_WARNING , " Unable to locate %s in assembly %s " , datatype_name - > value . str . val , assembly_name - > value . str . val ) ;
2001-05-02 21:52:12 +00:00
efree ( obj ) ;
2000-08-26 12:53:14 +00:00
RETURN_FALSE ;
}
2001-06-24 21:20:23 +00:00
RETURN_LONG ( zend_list_insert ( obj , IS_COM ) ) ;
2000-08-26 12:53:14 +00:00
}
/* }}} */
void php_DOTNET_call_function_handler ( INTERNAL_FUNCTION_PARAMETERS , zend_property_reference * property_reference )
{
pval * object = property_reference - > object ;
zend_overloaded_element * function_name = ( zend_overloaded_element * ) property_reference - > elements_list - > tail - > data ;
if ( zend_llist_count ( property_reference - > elements_list ) = = 1
2001-06-24 21:20:23 +00:00
& & ! strcmp ( Z_STRVAL ( function_name - > element ) , " dotnet " ) ) { /* constructor */
2000-08-26 12:53:14 +00:00
pval * object_handle ;
2001-05-13 14:15:26 +00:00
PHP_FN ( dotnet_load ) ( INTERNAL_FUNCTION_PARAM_PASSTHRU ) ;
2001-08-07 17:18:20 +00:00
if ( ! Z_LVAL_P ( return_value ) ) {
ZVAL_FALSE ( object ) ;
2000-08-26 12:53:14 +00:00
return ;
}
ALLOC_ZVAL ( object_handle ) ;
* object_handle = * return_value ;
pval_copy_constructor ( object_handle ) ;
INIT_PZVAL ( object_handle ) ;
2001-08-13 16:40:12 +00:00
zend_hash_index_update ( Z_OBJPROP_P ( object ) , 0 , & object_handle , sizeof ( pval * ) , NULL ) ;
2000-08-26 12:53:14 +00:00
pval_destructor ( & function_name - > element ) ;
} else {
php_COM_call_function_handler ( INTERNAL_FUNCTION_PARAM_PASSTHRU , property_reference ) ;
}
}
2001-07-31 04:53:54 +00:00
void php_register_DOTNET_class ( TSRMLS_D )
2000-08-26 12:53:14 +00:00
{
INIT_OVERLOADED_CLASS_ENTRY ( dotnet_class_entry , " DOTNET " , NULL ,
php_DOTNET_call_function_handler ,
php_COM_get_property_handler ,
php_COM_set_property_handler ) ;
2001-07-30 01:56:43 +00:00
zend_register_internal_class ( & dotnet_class_entry TSRMLS_CC ) ;
2000-08-26 12:53:14 +00:00
}
function_entry DOTNET_functions [ ] = {
{ NULL , NULL , NULL }
} ;
static PHP_MINFO_FUNCTION ( DOTNET )
{
2001-02-02 15:02:05 +00:00
php_info_print_table_start ( ) ;
2001-02-02 18:11:39 +00:00
php_info_print_table_row ( 2 , " .NET support " , " enabled " ) ;
2001-02-02 15:02:05 +00:00
php_info_print_table_end ( ) ;
2000-08-26 12:53:14 +00:00
}
PHP_MINIT_FUNCTION ( DOTNET )
{
HRESULT hr ;
2001-07-31 04:53:54 +00:00
2001-08-15 10:39:59 +00:00
if ( FAILED ( hr = dotnet_init ( ) ) ) {
2001-07-31 04:53:54 +00:00
return hr ;
}
2000-08-26 12:53:14 +00:00
2001-07-31 04:53:54 +00:00
php_register_DOTNET_class ( TSRMLS_C ) ;
2000-08-26 12:53:14 +00:00
return SUCCESS ;
}
PHP_MSHUTDOWN_FUNCTION ( DOTNET )
{
dotnet_term ( ) ;
return SUCCESS ;
}
zend_module_entry dotnet_module_entry = {
2001-10-11 23:33:59 +00:00
STANDARD_MODULE_HEADER ,
" dotnet " , DOTNET_functions , PHP_MINIT ( DOTNET ) , PHP_MSHUTDOWN ( DOTNET ) , NULL , NULL , PHP_MINFO ( DOTNET ) , NO_VERSION_YET , STANDARD_MODULE_PROPERTIES
2000-08-26 12:53:14 +00:00
} ;
2001-01-29 21:54:46 +00:00
BEGIN_EXTERN_C ( )
ZEND_GET_MODULE ( dotnet )
END_EXTERN_C ( )
2000-08-26 12:53:14 +00:00
# endif