wez Wed Apr 21 20:50:50 2004 EDT Modified files: /php-src/ext/com_dotnet com_variant.c Log: (probable) fix for Bug #27974: PHP Arrays are not mapped to VARIANTs. http://cvs.php.net/diff.php/php-src/ext/com_dotnet/com_variant.c?r1=1.4&r2=1.5&ty=u Index: php-src/ext/com_dotnet/com_variant.c diff -u php-src/ext/com_dotnet/com_variant.c:1.4 php-src/ext/com_dotnet/com_variant.c:1.5 --- php-src/ext/com_dotnet/com_variant.c:1.4 Thu Jan 8 03:14:20 2004 +++ php-src/ext/com_dotnet/com_variant.c Wed Apr 21 20:50:49 2004 @@ -16,7 +16,7 @@ +----------------------------------------------------------------------+ */ -/* $Id: com_variant.c,v 1.4 2004/01/08 08:14:20 andi Exp $ */ +/* $Id: com_variant.c,v 1.5 2004/04/22 00:50:49 wez Exp $ */ #ifdef HAVE_CONFIG_H #include "config.h" @@ -28,6 +28,70 @@ #include "php_com_dotnet.h" #include "php_com_dotnet_internal.h" +/* create an automation SafeArray from a PHP array. + * Only creates a single-dimensional array of variants. + * The keys of the PHP hash MUST be numeric. If the array + * is sparse, then the gaps will be filled with NULL variants */ +static void safe_array_from_zval(VARIANT *v, zval *z, int codepage TSRMLS_DC) +{ + SAFEARRAY *sa = NULL; + SAFEARRAYBOUND bound; + HashPosition pos; + char *strindex; + int strindexlen; + long intindex; + long max_index = 0; + VARIANT *va; + zval **item; + + /* find the largest array index, and assert that all keys are integers */ + zend_hash_internal_pointer_reset_ex(HASH_OF(z), &pos); + for (;; zend_hash_move_forward_ex(HASH_OF(z), &pos)) { + if (HASH_KEY_IS_LONG != zend_hash_get_current_key_ex(HASH_OF(z), &strindex, &strindexlen, &intindex, 0, &pos)) { + goto bogus; + } + if (intindex > max_index) { + max_index = intindex; + } + } + + /* allocate the structure */ + bound.lLbound = 0; + bound.cElements = intindex; + sa = SafeArrayCreate(VT_VARIANT, 1, &bound); + + /* get a lock on the array itself */ + SafeArrayLock(sa); + va = (VARIANT*)sa->pvData; + + /* now fill it in */ + zend_hash_internal_pointer_reset_ex(HASH_OF(z), &pos); + for (;; zend_hash_move_forward_ex(HASH_OF(z), &pos)) { + if (FAILURE == zend_hash_get_current_data_ex(HASH_OF(z), (void**)&item, &pos)) { + goto bogus; + } + zend_hash_get_current_key_ex(HASH_OF(z), &strindex, &strindexlen, &intindex, 0, &pos); + php_com_variant_from_zval(&va[intindex], *item, codepage TSRMLS_CC); + } + + /* Unlock it and stuff it into our variant */ + SafeArrayUnlock(sa); + V_VT(v) = VT_ARRAY|VT_VARIANT; + V_ARRAY(v) = sa; + + return; + +bogus: + php_error_docref(NULL TSRMLS_CC, E_WARNING, "COM: converting from PHP array to VARIANT array; only arrays with numeric keys are allowed"); + + V_VT(v) = VT_NULL; + + if (sa) { + SafeArrayUnlock(sa); + SafeArrayDestroy(sa); + } +} + PHPAPI void php_com_variant_from_zval(VARIANT *v, zval *z, int codepage TSRMLS_DC) { OLECHAR *olestring; @@ -66,8 +130,8 @@ break; case IS_ARRAY: - V_VT(v) = VT_NULL; - /* TODO: map as safe array ? */ + /* map as safe array */ + safe_array_from_zval(v, z, codepage TSRMLS_CC); break; case IS_LONG:
-- PHP CVS Mailing List (http://www.php.net/) To unsubscribe, visit: http://www.php.net/unsub.php