1 /*
2 +----------------------------------------------------------------------+
3 | Copyright (c) The PHP Group |
4 +----------------------------------------------------------------------+
5 | This source file is subject to version 3.01 of the PHP license, |
6 | that is bundled with this package in the file LICENSE, and is |
7 | available through the world-wide-web at the following url: |
8 | https://www.php.net/license/3_01.txt |
9 | If you did not receive a copy of the PHP license and are unable to |
10 | obtain it through the world-wide-web, please send a note to |
11 | license@php.net so we can mail you a copy immediately. |
12 +----------------------------------------------------------------------+
13 | Authors: Stig Sæther Bakken <ssb@php.net> |
14 | Thies C. Arntzen <thies@thieso.net> |
15 | |
16 | Collection support by Andy Sautins <asautins@veripost.net> |
17 | Temporary LOB support by David Benson <dbenson@mancala.com> |
18 | ZTS per process OCIPLogon by Harald Radi <harald.radi@nme.at> |
19 | |
20 | Redesigned by: Antony Dovgal <antony@zend.com> |
21 | Andi Gutmans <andi@php.net> |
22 | Wez Furlong <wez@omniti.com> |
23 +----------------------------------------------------------------------+
24 */
25
26 #ifdef HAVE_CONFIG_H
27 #include "config.h"
28 #endif
29
30 #include "php.h"
31 #include "ext/standard/info.h"
32 #include "php_ini.h"
33
34 #ifdef HAVE_OCI8
35
36 #include "php_oci8.h"
37 #include "php_oci8_int.h"
38
39 /* {{{ php_oci_collection_create()
40 Create and return connection handle */
php_oci_collection_create(php_oci_connection * connection,char * tdo,int tdo_len,char * schema,int schema_len)41 php_oci_collection *php_oci_collection_create(php_oci_connection *connection, char *tdo, int tdo_len, char *schema, int schema_len)
42 {
43 dvoid *dschp1 = NULL;
44 dvoid *parmp1;
45 dvoid *parmp2;
46 php_oci_collection *collection;
47 sword errstatus;
48
49 collection = emalloc(sizeof(php_oci_collection));
50
51 collection->connection = connection;
52 collection->collection = NULL;
53 GC_ADDREF(collection->connection->id);
54
55 /* get type handle by name */
56 PHP_OCI_CALL_RETURN(errstatus, OCITypeByName,
57 (
58 connection->env,
59 connection->err,
60 connection->svc,
61 (text *) schema,
62 (ub4) schema_len,
63 (text *) tdo,
64 (ub4) tdo_len,
65 (CONST text *) 0,
66 (ub4) 0,
67 OCI_DURATION_SESSION,
68 OCI_TYPEGET_ALL,
69 &(collection->tdo)
70 )
71 );
72
73 if (errstatus != OCI_SUCCESS) {
74 goto CLEANUP;
75 }
76
77 /* allocate describe handle */
78 PHP_OCI_CALL_RETURN(errstatus, OCIHandleAlloc, (connection->env, (dvoid **) &dschp1, (ub4) OCI_HTYPE_DESCRIBE, (size_t) 0, (dvoid **) 0));
79
80 if (errstatus != OCI_SUCCESS) {
81 goto CLEANUP;
82 }
83
84 /* describe TDO */
85 PHP_OCI_CALL_RETURN(errstatus, OCIDescribeAny,
86 (
87 connection->svc,
88 connection->err,
89 (dvoid *) collection->tdo,
90 (ub4) 0,
91 OCI_OTYPE_PTR,
92 (ub1) OCI_DEFAULT,
93 (ub1) OCI_PTYPE_TYPE,
94 dschp1
95 )
96 );
97
98 if (errstatus != OCI_SUCCESS) {
99 goto CLEANUP;
100 }
101
102 /* get first parameter handle */
103 PHP_OCI_CALL_RETURN(errstatus, OCIAttrGet, ((dvoid *) dschp1, (ub4) OCI_HTYPE_DESCRIBE, (dvoid *)&parmp1, (ub4 *)0, (ub4)OCI_ATTR_PARAM, connection->err));
104
105 if (errstatus != OCI_SUCCESS) {
106 goto CLEANUP;
107 }
108
109 /* get the collection type code of the attribute */
110 PHP_OCI_CALL_RETURN(errstatus, OCIAttrGet,
111 (
112 (dvoid*) parmp1,
113 (ub4) OCI_DTYPE_PARAM,
114 (dvoid*) &(collection->coll_typecode),
115 (ub4 *) 0,
116 (ub4) OCI_ATTR_COLLECTION_TYPECODE,
117 connection->err
118 )
119 );
120
121 if (errstatus != OCI_SUCCESS) {
122 goto CLEANUP;
123 }
124
125 switch(collection->coll_typecode) {
126 case OCI_TYPECODE_TABLE:
127 case OCI_TYPECODE_VARRAY:
128 /* get collection element handle */
129 PHP_OCI_CALL_RETURN(errstatus, OCIAttrGet,
130 (
131 (dvoid*) parmp1,
132 (ub4) OCI_DTYPE_PARAM,
133 (dvoid*) &parmp2,
134 (ub4 *) 0,
135 (ub4) OCI_ATTR_COLLECTION_ELEMENT,
136 connection->err
137 )
138 );
139
140 if (errstatus != OCI_SUCCESS) {
141 goto CLEANUP;
142 }
143
144 /* get REF of the TDO for the type */
145 PHP_OCI_CALL_RETURN(errstatus, OCIAttrGet,
146 (
147 (dvoid*) parmp2,
148 (ub4) OCI_DTYPE_PARAM,
149 (dvoid*) &(collection->elem_ref),
150 (ub4 *) 0,
151 (ub4) OCI_ATTR_REF_TDO,
152 connection->err
153 )
154 );
155
156 if (errstatus != OCI_SUCCESS) {
157 goto CLEANUP;
158 }
159
160 /* get the TDO (only header) */
161 PHP_OCI_CALL_RETURN(errstatus, OCITypeByRef,
162 (
163 connection->env,
164 connection->err,
165 collection->elem_ref,
166 OCI_DURATION_SESSION,
167 OCI_TYPEGET_HEADER,
168 &(collection->element_type)
169 )
170 );
171
172 if (errstatus != OCI_SUCCESS) {
173 goto CLEANUP;
174 }
175
176 /* get typecode */
177 PHP_OCI_CALL_RETURN(errstatus, OCIAttrGet,
178 (
179 (dvoid*) parmp2,
180 (ub4) OCI_DTYPE_PARAM,
181 (dvoid*) &(collection->element_typecode),
182 (ub4 *) 0,
183 (ub4) OCI_ATTR_TYPECODE,
184 connection->err
185 )
186 );
187
188 if (errstatus != OCI_SUCCESS) {
189 goto CLEANUP;
190 }
191 break;
192 /* we only support VARRAYs and TABLEs */
193 default:
194 php_error_docref(NULL, E_WARNING, "Unknown collection type %d", collection->coll_typecode);
195 break;
196 }
197
198 /* Create object to hold return table */
199 PHP_OCI_CALL_RETURN(errstatus, OCIObjectNew,
200 (
201 connection->env,
202 connection->err,
203 connection->svc,
204 OCI_TYPECODE_TABLE,
205 collection->tdo,
206 (dvoid *)0,
207 OCI_DURATION_DEFAULT,
208 TRUE,
209 (dvoid **) &(collection->collection)
210 )
211 );
212
213 if (errstatus != OCI_SUCCESS) {
214 goto CLEANUP;
215 }
216
217 /* free the describe handle (Bug #44113) */
218 PHP_OCI_CALL(OCIHandleFree, ((dvoid *) dschp1, OCI_HTYPE_DESCRIBE));
219 PHP_OCI_REGISTER_RESOURCE(collection, le_collection);
220 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
221 return collection;
222
223 CLEANUP:
224
225 if (dschp1) {
226 /* free the describe handle (Bug #44113) */
227 PHP_OCI_CALL(OCIHandleFree, ((dvoid *) dschp1, OCI_HTYPE_DESCRIBE));
228 }
229 connection->errcode = php_oci_error(connection->err, errstatus);
230 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
231 php_oci_collection_close(collection);
232 return NULL;
233 }
234 /* }}} */
235
236 /* {{{ php_oci_collection_size()
237 Return size of the collection */
php_oci_collection_size(php_oci_collection * collection,sb4 * size)238 int php_oci_collection_size(php_oci_collection *collection, sb4 *size)
239 {
240 php_oci_connection *connection = collection->connection;
241 sword errstatus;
242
243 PHP_OCI_CALL_RETURN(errstatus, OCICollSize, (connection->env, connection->err, collection->collection, (sb4 *)size));
244
245 if (errstatus != OCI_SUCCESS) {
246 connection->errcode = php_oci_error(connection->err, errstatus);
247 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
248 return 1;
249 }
250 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
251 return 0;
252 }
253 /* }}} */
254
255 /* {{{ php_oci_collection_max()
256 Return max number of elements in the collection */
php_oci_collection_max(php_oci_collection * collection,zend_long * max)257 int php_oci_collection_max(php_oci_collection *collection, zend_long *max)
258 {
259 php_oci_connection *connection = collection->connection;
260
261 PHP_OCI_CALL_RETURN(*max, OCICollMax, (connection->env, collection->collection));
262
263 /* error handling is not necessary here? */
264 return 0;
265 }
266 /* }}} */
267
268 /* {{{ php_oci_collection_trim()
269 Trim collection to the given number of elements */
php_oci_collection_trim(php_oci_collection * collection,zend_long trim_size)270 int php_oci_collection_trim(php_oci_collection *collection, zend_long trim_size)
271 {
272 php_oci_connection *connection = collection->connection;
273 sword errstatus;
274
275 PHP_OCI_CALL_RETURN(errstatus, OCICollTrim, (connection->env, connection->err, (sb4) trim_size, collection->collection));
276
277 if (errstatus != OCI_SUCCESS) {
278 errstatus = php_oci_error(connection->err, errstatus);
279 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
280 return 1;
281 }
282 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
283 return 0;
284 }
285 /* }}} */
286
287 /* {{{ php_oci_collection_append_null()
288 Append NULL element to the end of the collection */
php_oci_collection_append_null(php_oci_collection * collection)289 int php_oci_collection_append_null(php_oci_collection *collection)
290 {
291 OCIInd null_index = OCI_IND_NULL;
292 php_oci_connection *connection = collection->connection;
293 sword errstatus;
294
295 /* append NULL element */
296 PHP_OCI_CALL_RETURN(errstatus, OCICollAppend, (connection->env, connection->err, (dvoid *)0, &null_index, collection->collection));
297
298 if (errstatus != OCI_SUCCESS) {
299 errstatus = php_oci_error(connection->err, errstatus);
300 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
301 return 1;
302 }
303 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
304 return 0;
305 }
306 /* }}} */
307
308 /* {{{ php_oci_collection_append_date()
309 Append DATE element to the end of the collection (use "DD-MON-YY" format) */
php_oci_collection_append_date(php_oci_collection * collection,char * date,int date_len)310 int php_oci_collection_append_date(php_oci_collection *collection, char *date, int date_len)
311 {
312 OCIInd new_index = OCI_IND_NOTNULL;
313 OCIDate oci_date;
314 php_oci_connection *connection = collection->connection;
315 sword errstatus;
316
317 /* format and language are NULLs, so format is "DD-MON-YY" and language is the default language of the session */
318 PHP_OCI_CALL_RETURN(errstatus, OCIDateFromText, (connection->err, (CONST text *)date, date_len, NULL, 0, NULL, 0, &oci_date));
319
320 if (errstatus != OCI_SUCCESS) {
321 /* failed to convert string to date */
322 connection->errcode = php_oci_error(connection->err, errstatus);
323 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
324 return 1;
325 }
326
327 PHP_OCI_CALL_RETURN(errstatus, OCICollAppend,
328 (
329 connection->env,
330 connection->err,
331 (dvoid *) &oci_date,
332 (dvoid *) &new_index,
333 (OCIColl *) collection->collection
334 )
335 );
336
337 if (errstatus != OCI_SUCCESS) {
338 connection->errcode = php_oci_error(connection->err, errstatus);
339 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
340 return 1;
341 }
342
343 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
344 return 0;
345 }
346 /* }}} */
347
348 /* {{{ php_oci_collection_append_number()
349 Append NUMBER to the end of the collection */
php_oci_collection_append_number(php_oci_collection * collection,char * number,int number_len)350 int php_oci_collection_append_number(php_oci_collection *collection, char *number, int number_len)
351 {
352 OCIInd new_index = OCI_IND_NOTNULL;
353 double element_double;
354 OCINumber oci_number;
355 php_oci_connection *connection = collection->connection;
356 sword errstatus;
357
358 element_double = zend_strtod(number, NULL);
359
360 PHP_OCI_CALL_RETURN(errstatus, OCINumberFromReal, (connection->err, &element_double, sizeof(double), &oci_number));
361
362 if (errstatus != OCI_SUCCESS) {
363 connection->errcode = php_oci_error(connection->err, errstatus);
364 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
365 return 1;
366 }
367
368 PHP_OCI_CALL_RETURN(errstatus, OCICollAppend,
369 (
370 connection->env,
371 connection->err,
372 (dvoid *) &oci_number,
373 (dvoid *) &new_index,
374 (OCIColl *) collection->collection
375 )
376 );
377
378 if (errstatus != OCI_SUCCESS) {
379 connection->errcode = php_oci_error(connection->err, errstatus);
380 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
381 return 1;
382 }
383
384 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
385 return 0;
386 }
387 /* }}} */
388
389 /* {{{ php_oci_collection_append_string()
390 Append STRING to the end of the collection */
php_oci_collection_append_string(php_oci_collection * collection,char * element,int element_len)391 int php_oci_collection_append_string(php_oci_collection *collection, char *element, int element_len)
392 {
393 OCIInd new_index = OCI_IND_NOTNULL;
394 OCIString *ocistr = (OCIString *)0;
395 php_oci_connection *connection = collection->connection;
396 sword errstatus;
397
398 PHP_OCI_CALL_RETURN(errstatus, OCIStringAssignText, (connection->env, connection->err, (CONST oratext *)element, element_len, &ocistr));
399
400 if (errstatus != OCI_SUCCESS) {
401 connection->errcode = php_oci_error(connection->err, errstatus);
402 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
403 return 1;
404 }
405
406 PHP_OCI_CALL_RETURN(errstatus, OCICollAppend,
407 (
408 connection->env,
409 connection->err,
410 (dvoid *) ocistr,
411 (dvoid *) &new_index,
412 (OCIColl *) collection->collection
413 )
414 );
415
416 if (errstatus != OCI_SUCCESS) {
417 connection->errcode = php_oci_error(connection->err, errstatus);
418 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
419 return 1;
420 }
421
422 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
423 return 0;
424 }
425 /* }}} */
426
427 /* {{{ php_oci_collection_append()
428 Append wrapper. Appends any supported element to the end of the collection */
php_oci_collection_append(php_oci_collection * collection,char * element,int element_len)429 int php_oci_collection_append(php_oci_collection *collection, char *element, int element_len)
430 {
431 if (element_len == 0) {
432 return php_oci_collection_append_null(collection);
433 }
434
435 switch(collection->element_typecode) {
436 case OCI_TYPECODE_DATE:
437 return php_oci_collection_append_date(collection, element, element_len);
438 break;
439
440 case OCI_TYPECODE_VARCHAR2 :
441 return php_oci_collection_append_string(collection, element, element_len);
442 break;
443
444 case OCI_TYPECODE_UNSIGNED16 : /* UNSIGNED SHORT */
445 case OCI_TYPECODE_UNSIGNED32 : /* UNSIGNED LONG */
446 case OCI_TYPECODE_REAL : /* REAL */
447 case OCI_TYPECODE_DOUBLE : /* DOUBLE */
448 case OCI_TYPECODE_INTEGER : /* INT */
449 case OCI_TYPECODE_SIGNED16 : /* SHORT */
450 case OCI_TYPECODE_SIGNED32 : /* LONG */
451 case OCI_TYPECODE_DECIMAL : /* DECIMAL */
452 case OCI_TYPECODE_FLOAT : /* FLOAT */
453 case OCI_TYPECODE_NUMBER : /* NUMBER */
454 case OCI_TYPECODE_SMALLINT : /* SMALLINT */
455 return php_oci_collection_append_number(collection, element, element_len);
456 break;
457
458 default:
459 php_error_docref(NULL, E_NOTICE, "Unknown or unsupported type of element: %d", collection->element_typecode);
460 return 1;
461 break;
462 }
463 /* never reached */
464 return 1;
465 }
466 /* }}} */
467
468 /* {{{ php_oci_collection_element_get()
469 Get the element with the given index */
php_oci_collection_element_get(php_oci_collection * collection,zend_long index,zval * result_element)470 int php_oci_collection_element_get(php_oci_collection *collection, zend_long index, zval *result_element)
471 {
472 php_oci_connection *connection = collection->connection;
473 dvoid *element;
474 OCIInd *element_index;
475 boolean exists;
476 oratext buff[1024];
477 ub4 buff_len = 1024;
478 sword errstatus;
479
480 ZVAL_NULL(result_element);
481
482 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
483
484 PHP_OCI_CALL_RETURN(errstatus, OCICollGetElem,
485 (
486 connection->env,
487 connection->err,
488 collection->collection,
489 (ub4)index,
490 &exists,
491 &element,
492 (dvoid **)&element_index
493 )
494 );
495
496 if (errstatus != OCI_SUCCESS) {
497 connection->errcode = php_oci_error(connection->err, errstatus);
498 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
499 return 1;
500 }
501
502 if (exists == 0) {
503 /* element doesn't exist */
504 return 1;
505 }
506
507 if (*element_index == OCI_IND_NULL) {
508 /* this is not an error, we're returning NULL here */
509 return 0;
510 }
511
512 switch (collection->element_typecode) {
513 case OCI_TYPECODE_DATE:
514 PHP_OCI_CALL_RETURN(errstatus, OCIDateToText, (connection->err, element, 0, 0, 0, 0, &buff_len, buff));
515
516 if (errstatus != OCI_SUCCESS) {
517 connection->errcode = php_oci_error(connection->err, errstatus);
518 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
519 return 1;
520 }
521
522 ZVAL_STRINGL(result_element, (char *)buff, buff_len);
523 Z_STRVAL_P(result_element)[buff_len] = '\0';
524
525 return 0;
526 break;
527
528 case OCI_TYPECODE_VARCHAR2:
529 {
530 OCIString *oci_string = *(OCIString **)element;
531 text *str;
532
533 PHP_OCI_CALL_RETURN(str, OCIStringPtr, (connection->env, oci_string));
534
535 if (str) {
536 ZVAL_STRING(result_element, (char *)str);
537 }
538 return 0;
539 }
540 break;
541
542 case OCI_TYPECODE_UNSIGNED16: /* UNSIGNED SHORT */
543 case OCI_TYPECODE_UNSIGNED32: /* UNSIGNED LONG */
544 case OCI_TYPECODE_REAL: /* REAL */
545 case OCI_TYPECODE_DOUBLE: /* DOUBLE */
546 case OCI_TYPECODE_INTEGER: /* INT */
547 case OCI_TYPECODE_SIGNED16: /* SHORT */
548 case OCI_TYPECODE_SIGNED32: /* LONG */
549 case OCI_TYPECODE_DECIMAL: /* DECIMAL */
550 case OCI_TYPECODE_FLOAT: /* FLOAT */
551 case OCI_TYPECODE_NUMBER: /* NUMBER */
552 case OCI_TYPECODE_SMALLINT: /* SMALLINT */
553 {
554 double double_number;
555
556 PHP_OCI_CALL_RETURN(errstatus, OCINumberToReal, (connection->err, (CONST OCINumber *) element, (uword) sizeof(double), (dvoid *) &double_number));
557
558 if (errstatus != OCI_SUCCESS) {
559 connection->errcode = php_oci_error(connection->err, errstatus);
560 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
561 return 1;
562 }
563
564 ZVAL_DOUBLE(result_element, double_number);
565
566 return 0;
567 }
568 break;
569 default:
570 php_error_docref(NULL, E_NOTICE, "Unknown or unsupported type of element: %d", collection->element_typecode);
571 return 1;
572 break;
573 }
574 /* never reached */
575 return 1;
576 }
577 /* }}} */
578
579 /* {{{ php_oci_collection_element_set_null()
580 Set the element with the given index to NULL */
php_oci_collection_element_set_null(php_oci_collection * collection,zend_long index)581 int php_oci_collection_element_set_null(php_oci_collection *collection, zend_long index)
582 {
583 OCIInd null_index = OCI_IND_NULL;
584 php_oci_connection *connection = collection->connection;
585 sword errstatus;
586
587 /* set NULL element */
588 PHP_OCI_CALL_RETURN(errstatus, OCICollAssignElem, (connection->env, connection->err, (ub4) index, (dvoid *)"", &null_index, collection->collection));
589
590 if (errstatus != OCI_SUCCESS) {
591 connection->errcode = php_oci_error(connection->err, errstatus);
592 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
593 return 1;
594 }
595 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
596 return 0;
597 }
598 /* }}} */
599
600 /* {{{ php_oci_collection_element_set_date()
601 Change element's value to the given DATE */
php_oci_collection_element_set_date(php_oci_collection * collection,zend_long index,char * date,int date_len)602 int php_oci_collection_element_set_date(php_oci_collection *collection, zend_long index, char *date, int date_len)
603 {
604 OCIInd new_index = OCI_IND_NOTNULL;
605 OCIDate oci_date;
606 php_oci_connection *connection = collection->connection;
607 sword errstatus;
608
609 /* format and language are NULLs, so format is "DD-MON-YY" and language is the default language of the session */
610 PHP_OCI_CALL_RETURN(errstatus, OCIDateFromText, (connection->err, (CONST text *)date, date_len, NULL, 0, NULL, 0, &oci_date));
611
612 if (errstatus != OCI_SUCCESS) {
613 /* failed to convert string to date */
614 connection->errcode = php_oci_error(connection->err, errstatus);
615 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
616 return 1;
617 }
618
619 PHP_OCI_CALL_RETURN(errstatus, OCICollAssignElem,
620 (
621 connection->env,
622 connection->err,
623 (ub4)index,
624 (dvoid *) &oci_date,
625 (dvoid *) &new_index,
626 (OCIColl *) collection->collection
627 )
628 );
629
630 if (errstatus != OCI_SUCCESS) {
631 connection->errcode = php_oci_error(connection->err, errstatus);
632 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
633 return 1;
634 }
635
636 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
637 return 0;
638 }
639 /* }}} */
640
641 /* {{{ php_oci_collection_element_set_number()
642 Change element's value to the given NUMBER */
php_oci_collection_element_set_number(php_oci_collection * collection,zend_long index,char * number,int number_len)643 int php_oci_collection_element_set_number(php_oci_collection *collection, zend_long index, char *number, int number_len)
644 {
645 OCIInd new_index = OCI_IND_NOTNULL;
646 double element_double;
647 OCINumber oci_number;
648 php_oci_connection *connection = collection->connection;
649 sword errstatus;
650
651 element_double = zend_strtod(number, NULL);
652
653 PHP_OCI_CALL_RETURN(errstatus, OCINumberFromReal, (connection->err, &element_double, sizeof(double), &oci_number));
654
655 if (errstatus != OCI_SUCCESS) {
656 connection->errcode = php_oci_error(connection->err, errstatus);
657 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
658 return 1;
659 }
660
661 PHP_OCI_CALL_RETURN(errstatus, OCICollAssignElem,
662 (
663 connection->env,
664 connection->err,
665 (ub4) index,
666 (dvoid *) &oci_number,
667 (dvoid *) &new_index,
668 (OCIColl *) collection->collection
669 )
670 );
671
672 if (errstatus != OCI_SUCCESS) {
673 connection->errcode = php_oci_error(connection->err, errstatus);
674 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
675 return 1;
676 }
677
678 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
679 return 0;
680 }
681 /* }}} */
682
683 /* {{{ php_oci_collection_element_set_string()
684 Change element's value to the given string */
php_oci_collection_element_set_string(php_oci_collection * collection,zend_long index,char * element,int element_len)685 int php_oci_collection_element_set_string(php_oci_collection *collection, zend_long index, char *element, int element_len)
686 {
687 OCIInd new_index = OCI_IND_NOTNULL;
688 OCIString *ocistr = (OCIString *)0;
689 php_oci_connection *connection = collection->connection;
690 sword errstatus;
691
692 PHP_OCI_CALL_RETURN(errstatus, OCIStringAssignText, (connection->env, connection->err, (CONST oratext *)element, element_len, &ocistr));
693
694 if (errstatus != OCI_SUCCESS) {
695 connection->errcode = php_oci_error(connection->err, errstatus);
696 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
697 return 1;
698 }
699
700 PHP_OCI_CALL_RETURN(errstatus, OCICollAssignElem,
701 (
702 connection->env,
703 connection->err,
704 (ub4)index,
705 (dvoid *) ocistr,
706 (dvoid *) &new_index,
707 (OCIColl *) collection->collection
708 )
709 );
710
711 if (errstatus != OCI_SUCCESS) {
712 connection->errcode = php_oci_error(connection->err, errstatus);
713 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
714 return 1;
715 }
716
717 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
718 return 0;
719 }
720 /* }}} */
721
722 /* {{{ php_oci_collection_element_set()
723 Collection element setter */
php_oci_collection_element_set(php_oci_collection * collection,zend_long index,char * value,int value_len)724 int php_oci_collection_element_set(php_oci_collection *collection, zend_long index, char *value, int value_len)
725 {
726 if (value_len == 0) {
727 return php_oci_collection_element_set_null(collection, index);
728 }
729
730 switch(collection->element_typecode) {
731 case OCI_TYPECODE_DATE:
732 return php_oci_collection_element_set_date(collection, index, value, value_len);
733 break;
734
735 case OCI_TYPECODE_VARCHAR2 :
736 return php_oci_collection_element_set_string(collection, index, value, value_len);
737 break;
738
739 case OCI_TYPECODE_UNSIGNED16 : /* UNSIGNED SHORT */
740 case OCI_TYPECODE_UNSIGNED32 : /* UNSIGNED LONG */
741 case OCI_TYPECODE_REAL : /* REAL */
742 case OCI_TYPECODE_DOUBLE : /* DOUBLE */
743 case OCI_TYPECODE_INTEGER : /* INT */
744 case OCI_TYPECODE_SIGNED16 : /* SHORT */
745 case OCI_TYPECODE_SIGNED32 : /* LONG */
746 case OCI_TYPECODE_DECIMAL : /* DECIMAL */
747 case OCI_TYPECODE_FLOAT : /* FLOAT */
748 case OCI_TYPECODE_NUMBER : /* NUMBER */
749 case OCI_TYPECODE_SMALLINT : /* SMALLINT */
750 return php_oci_collection_element_set_number(collection, index, value, value_len);
751 break;
752
753 default:
754 php_error_docref(NULL, E_NOTICE, "Unknown or unsupported type of element: %d", collection->element_typecode);
755 return 1;
756 break;
757 }
758 /* never reached */
759 return 1;
760 }
761 /* }}} */
762
763 /* {{{ php_oci_collection_assign()
764 Assigns a value to the collection from another collection */
php_oci_collection_assign(php_oci_collection * collection_dest,php_oci_collection * collection_from)765 int php_oci_collection_assign(php_oci_collection *collection_dest, php_oci_collection *collection_from)
766 {
767 php_oci_connection *connection = collection_dest->connection;
768 sword errstatus;
769
770 PHP_OCI_CALL_RETURN(errstatus, OCICollAssign, (connection->env, connection->err, collection_from->collection, collection_dest->collection));
771
772 if (errstatus != OCI_SUCCESS) {
773 connection->errcode = php_oci_error(connection->err, errstatus);
774 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
775 return 1;
776 }
777 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
778 return 0;
779 }
780 /* }}} */
781
782 /* {{{ php_oci_collection_close()
783 Destroy collection and all associated resources */
php_oci_collection_close(php_oci_collection * collection)784 void php_oci_collection_close(php_oci_collection *collection)
785 {
786 php_oci_connection *connection = collection->connection;
787 sword errstatus;
788
789 if (collection->collection) {
790 PHP_OCI_CALL_RETURN(errstatus, OCIObjectFree, (connection->env, connection->err, (dvoid *)collection->collection, (ub2)OCI_OBJECTFREE_FORCE));
791
792 if (errstatus != OCI_SUCCESS) {
793 connection->errcode = php_oci_error(connection->err, errstatus);
794 PHP_OCI_HANDLE_ERROR(connection, connection->errcode);
795 } else {
796 connection->errcode = 0; /* retain backwards compat with OCI8 1.4 */
797 }
798 }
799
800 zend_list_delete(collection->connection->id);
801 efree(collection);
802 return;
803 }
804 /* }}} */
805
806 #endif /* HAVE_OCI8 */
807