@@ -2257,74 +2257,84 @@ zend_object_iterator *pdo_stmt_iter_get(zend_class_entry *ce, zval *object, int
22572257/* }}} */
22582258
22592259/* {{{ overloaded handlers for PDORow class (used by PDO_FETCH_LAZY) */
2260+ static zval * row_read_column_name (pdo_stmt_t * stmt , zend_string * name , zval * rv )
2261+ {
2262+ /* TODO: replace this with a hash of available column names to column numbers */
2263+ for (int colno = 0 ; colno < stmt -> column_count ; colno ++ ) {
2264+ if (zend_string_equals (stmt -> columns [colno ].name , name )) {
2265+ fetch_value (stmt , rv , colno , NULL );
2266+ return rv ;
2267+ }
2268+ }
2269+ return NULL ;
2270+ }
2271+
2272+ static zval * row_read_column_number (pdo_stmt_t * stmt , zend_long column , zval * rv )
2273+ {
2274+ if (column >= 0 && column < stmt -> column_count ) {
2275+ fetch_value (stmt , rv , column , NULL );
2276+ return rv ;
2277+ }
2278+ return NULL ;
2279+ }
22602280
22612281static zval * row_prop_read (zend_object * object , zend_string * name , int type , void * * cache_slot , zval * rv )
22622282{
22632283 pdo_row_t * row = (pdo_row_t * )object ;
22642284 pdo_stmt_t * stmt = row -> stmt ;
2265- int colno = -1 ;
22662285 zend_long lval ;
2286+ zval * retval ;
22672287 ZEND_ASSERT (stmt );
22682288
22692289 ZVAL_NULL (rv );
22702290 if (zend_string_equals_literal (name , "queryString" )) {
22712291 return zend_std_read_property (& stmt -> std , name , type , cache_slot , rv );
2272- } else if (is_numeric_string (ZSTR_VAL (name ), ZSTR_LEN (name ), & lval , NULL , 0 ) == IS_LONG ) {
2273- if (lval >= 0 && lval < stmt -> column_count ) {
2274- fetch_value (stmt , rv , lval , NULL );
2275- }
2292+ } else if (is_numeric_str_function (name , & lval , /* dval */ NULL ) == IS_LONG ) {
2293+ retval = row_read_column_number (stmt , lval , rv );
22762294 } else {
2277- /* TODO: replace this with a hash of available column names to column
2278- * numbers */
2279- for (colno = 0 ; colno < stmt -> column_count ; colno ++ ) {
2280- if (zend_string_equals (stmt -> columns [colno ].name , name )) {
2281- fetch_value (stmt , rv , colno , NULL );
2282- return rv ;
2283- }
2284- }
2295+ retval = row_read_column_name (stmt , name , rv );
22852296 }
2286-
2287- return rv ;
2297+ if (UNEXPECTED (!retval )) {
2298+ // TODO throw an error on master
2299+ //if (type != BP_VAR_IS) {
2300+ // if (is_numeric) {
2301+ // zend_value_error("Invalid column index");
2302+ // } else {
2303+ // zend_throw_error(NULL, "No column named \"%s\" exists", ZSTR_VAL(name));
2304+ // }
2305+ //}
2306+ //return &EG(uninitialized_zval);
2307+ ZVAL_NULL (rv );
2308+ return rv ;
2309+ }
2310+ return retval ;
22882311}
22892312
2290- static zval * row_dim_read (zend_object * object , zval * member , int type , zval * rv )
2313+ static zval * row_dim_read (zend_object * object , zval * offset , int type , zval * rv )
22912314{
2292- pdo_row_t * row = (pdo_row_t * )object ;
2293- pdo_stmt_t * stmt = row -> stmt ;
2294- int colno = -1 ;
2295- zend_long lval ;
2296- ZEND_ASSERT (stmt );
2315+ if (UNEXPECTED (!offset )) {
2316+ zend_throw_error (NULL , "Cannot append to PDORow offset" );
2317+ return NULL ;
2318+ }
2319+ if (Z_TYPE_P (offset ) == IS_LONG ) {
2320+ pdo_row_t * row = (pdo_row_t * )object ;
2321+ pdo_stmt_t * stmt = row -> stmt ;
2322+ ZEND_ASSERT (stmt );
22972323
2298- ZVAL_NULL (rv );
2299- if (Z_TYPE_P (member ) == IS_LONG ) {
2300- if (Z_LVAL_P (member ) >= 0 && Z_LVAL_P (member ) < stmt -> column_count ) {
2301- fetch_value (stmt , rv , Z_LVAL_P (member ), NULL );
2302- }
2303- } else if (Z_TYPE_P (member ) == IS_STRING
2304- && is_numeric_string (Z_STRVAL_P (member ), Z_STRLEN_P (member ), & lval , NULL , 0 ) == IS_LONG ) {
2305- if (lval >= 0 && lval < stmt -> column_count ) {
2306- fetch_value (stmt , rv , lval , NULL );
2324+ ZVAL_NULL (rv );
2325+ if (Z_LVAL_P (offset ) >= 0 && Z_LVAL_P (offset ) < stmt -> column_count ) {
2326+ fetch_value (stmt , rv , Z_LVAL_P (offset ), NULL );
23072327 }
2328+ return rv ;
23082329 } else {
2309- if (!try_convert_to_string (member )) {
2310- return & EG (uninitialized_zval );
2311- }
2312-
2313- if (zend_string_equals_literal (Z_STR_P (member ), "queryString" )) {
2314- return zend_std_read_property (& stmt -> std , Z_STR_P (member ), type , NULL , rv );
2315- }
2316-
2317- /* TODO: replace this with a hash of available column names to column
2318- * numbers */
2319- for (colno = 0 ; colno < stmt -> column_count ; colno ++ ) {
2320- if (zend_string_equals (stmt -> columns [colno ].name , Z_STR_P (member ))) {
2321- fetch_value (stmt , rv , colno , NULL );
2322- return rv ;
2323- }
2330+ zend_string * member = zval_try_get_string (offset );
2331+ if (!member ) {
2332+ return NULL ;
23242333 }
2334+ zval * result = row_prop_read (object , member , type , NULL , rv );
2335+ zend_string_release_ex (member , false);
2336+ return result ;
23252337 }
2326-
2327- return rv ;
23282338}
23292339
23302340static zval * row_prop_write (zend_object * object , zend_string * name , zval * value , void * * cache_slot )
@@ -2335,75 +2345,67 @@ static zval *row_prop_write(zend_object *object, zend_string *name, zval *value,
23352345
23362346static void row_dim_write (zend_object * object , zval * member , zval * value )
23372347{
2338- zend_throw_error (NULL , "Cannot write to PDORow offset" );
2348+ if (!member ) {
2349+ zend_throw_error (NULL , "Cannot append to PDORow offset" );
2350+ } else {
2351+ zend_throw_error (NULL , "Cannot write to PDORow offset" );
2352+ }
23392353}
23402354
23412355static int row_prop_exists (zend_object * object , zend_string * name , int check_empty , void * * cache_slot )
23422356{
23432357 pdo_row_t * row = (pdo_row_t * )object ;
23442358 pdo_stmt_t * stmt = row -> stmt ;
2345- int colno = -1 ;
23462359 zend_long lval ;
2360+ zval tmp_val ;
2361+ zval * retval = NULL ;
23472362 ZEND_ASSERT (stmt );
23482363
2349- if (is_numeric_string (ZSTR_VAL (name ), ZSTR_LEN (name ), & lval , NULL , 0 ) == IS_LONG ) {
2350- return lval >=0 && lval < stmt -> column_count ;
2364+ if (is_numeric_str_function (name , & lval , /* dval */ NULL ) == IS_LONG ) {
2365+ retval = row_read_column_number (stmt , lval , & tmp_val );
2366+ } else {
2367+ retval = row_read_column_name (stmt , name , & tmp_val );
23512368 }
23522369
2353- /* TODO: replace this with a hash of available column names to column
2354- * numbers */
2355- for (colno = 0 ; colno < stmt -> column_count ; colno ++ ) {
2356- if (zend_string_equals (stmt -> columns [colno ].name , name )) {
2357- int res ;
2358- zval val ;
2359-
2360- fetch_value (stmt , & val , colno , NULL );
2361- res = check_empty ? i_zend_is_true (& val ) : Z_TYPE (val ) != IS_NULL ;
2362- zval_ptr_dtor_nogc (& val );
2363-
2364- return res ;
2365- }
2370+ if (!retval ) {
2371+ return false;
23662372 }
2367-
2368- return 0 ;
2373+ ZEND_ASSERT (retval == & tmp_val );
2374+ int res = check_empty ? i_zend_is_true (retval ) : Z_TYPE (tmp_val ) != IS_NULL ;
2375+ zval_ptr_dtor_nogc (retval );
2376+ return res ;
23692377}
23702378
2371- static int row_dim_exists (zend_object * object , zval * member , int check_empty )
2379+ static int row_dim_exists (zend_object * object , zval * offset , int check_empty )
23722380{
2373- pdo_row_t * row = ( pdo_row_t * ) object ;
2374- pdo_stmt_t * stmt = row -> stmt ;
2375- int colno = -1 ;
2376- zend_long lval ;
2377- ZEND_ASSERT ( stmt );
2381+ if ( Z_TYPE_P ( offset ) == IS_LONG ) {
2382+ pdo_row_t * row = ( pdo_row_t * ) object ;
2383+ pdo_stmt_t * stmt = row -> stmt ;
2384+ ZEND_ASSERT ( stmt ) ;
2385+ zend_long column = Z_LVAL_P ( offset );
23782386
2379- if (Z_TYPE_P (member ) == IS_LONG ) {
2380- return Z_LVAL_P (member ) >= 0 && Z_LVAL_P (member ) < stmt -> column_count ;
2381- } else if (Z_TYPE_P (member ) == IS_STRING ) {
2382- if (is_numeric_string (Z_STRVAL_P (member ), Z_STRLEN_P (member ), & lval , NULL , 0 ) == IS_LONG ) {
2383- return lval >=0 && lval < stmt -> column_count ;
2387+ if (!check_empty ) {
2388+ return column >= 0 && column < stmt -> column_count ;
23842389 }
2390+
2391+ zval tmp_val ;
2392+ zval * retval = row_read_column_number (stmt , column , & tmp_val );
2393+ if (!retval ) {
2394+ return false;
2395+ }
2396+ ZEND_ASSERT (retval == & tmp_val );
2397+ int res = check_empty ? i_zend_is_true (retval ) : Z_TYPE (tmp_val ) != IS_NULL ;
2398+ zval_ptr_dtor_nogc (retval );
2399+ return res ;
23852400 } else {
2386- if (!try_convert_to_string (member )) {
2401+ zend_string * member = zval_try_get_string (offset );
2402+ if (!member ) {
23872403 return 0 ;
23882404 }
2405+ int result = row_prop_exists (object , member , check_empty , NULL );
2406+ zend_string_release_ex (member , false);
2407+ return result ;
23892408 }
2390-
2391- /* TODO: replace this with a hash of available column names to column
2392- * numbers */
2393- for (colno = 0 ; colno < stmt -> column_count ; colno ++ ) {
2394- if (zend_string_equals (stmt -> columns [colno ].name , Z_STR_P (member ))) {
2395- int res ;
2396- zval val ;
2397-
2398- fetch_value (stmt , & val , colno , NULL );
2399- res = check_empty ? i_zend_is_true (& val ) : Z_TYPE (val ) != IS_NULL ;
2400- zval_ptr_dtor_nogc (& val );
2401-
2402- return res ;
2403- }
2404- }
2405-
2406- return 0 ;
24072409}
24082410
24092411static void row_prop_delete (zend_object * object , zend_string * offset , void * * cache_slot )
0 commit comments