1/*********************************************************************
2 *
3 * This is based on code created by Peter Harvey,
4 * (pharvey@codebydesign.com).
5 *
6 * Modified and extended by Nick Gorham
7 * (nick@lurcher.org).
8 *
9 * Any bugs or problems should be considered the fault of Nick and not
10 * Peter.
11 *
12 * copyright (c) 1999 Nick Gorham
13 *
14 * This library is free software; you can redistribute it and/or
15 * modify it under the terms of the GNU Lesser General Public
16 * License as published by the Free Software Foundation; either
17 * version 2 of the License, or (at your option) any later version.
18 *
19 * This library is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22 * Lesser General Public License for more details.
23 *
24 * You should have received a copy of the GNU Lesser General Public
25 * License along with this library; if not, write to the Free Software
26 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
27 *
28 **********************************************************************
29 *
30 * $Id: SQLSetConnectAttr.c,v 1.17 2009/02/18 17:59:08 lurcher Exp $
31 *
32 * $Log: SQLSetConnectAttr.c,v $
33 * Revision 1.17 2009/02/18 17:59:08 lurcher
34 * Shift to using config.h, the compile lines were making it hard to spot warnings
35 *
36 * Revision 1.16 2006/04/11 10:22:56 lurcher
37 * Fix a data type check
38 *
39 * Revision 1.15 2005/03/01 15:50:50 lurcher
40 * Add Eric's SQLSetConnectAttr patch
41 *
42 * Revision 1.14 2004/06/21 10:01:11 lurcher
43 *
44 * Fix a couple of 64 bit issues
45 *
46 * Revision 1.13 2003/10/30 18:20:46 lurcher
47 *
48 * Fix broken thread protection
49 * Remove SQLNumResultCols after execute, lease S4/S% to driver
50 * Fix string overrun in SQLDriverConnect
51 * Add initial support for Interix
52 *
53 * Revision 1.12 2003/03/05 09:48:44 lurcher
54 *
55 * Add some 64 bit fixes
56 *
57 * Revision 1.11 2003/02/27 12:19:39 lurcher
58 *
59 * Add the A functions as well as the W
60 *
61 * Revision 1.10 2002/12/05 17:44:31 lurcher
62 *
63 * Display unknown return values in return logging
64 *
65 * Revision 1.9 2002/07/24 08:49:52 lurcher
66 *
67 * Alter UNICODE support to use iconv for UNICODE-ANSI conversion
68 *
69 * Revision 1.8 2002/07/16 13:08:18 lurcher
70 *
71 * Filter attribute values from SQLSetStmtAttr to SQLSetStmtOption to fit
72 * within ODBC 2
73 * Make DSN's double clickable in ODBCConfig
74 *
75 * Revision 1.7 2002/07/04 17:27:56 lurcher
76 *
77 * Small bug fixes
78 *
79 * Revision 1.5 2002/01/30 12:20:02 lurcher
80 *
81 * Add MyODBC 3 driver source
82 *
83 * Revision 1.4 2002/01/10 11:17:20 lurcher
84 *
85 * Allow SQL_ATTR_LOGIN_TIMEOUT to be set when connected to mirror what the
86 * MS DM does
87 *
88 * Revision 1.3 2001/12/13 13:00:32 lurcher
89 *
90 * Remove most if not all warnings on 64 bit platforms
91 * Add support for new MS 3.52 64 bit changes
92 * Add override to disable the stopping of tracing
93 * Add MAX_ROWS support in postgres driver
94 *
95 * Revision 1.2 2001/11/14 12:33:20 lurcher
96 *
97 * Remove the comments around the tracing code
98 *
99 * Revision 1.1.1.1 2001/10/17 16:40:06 lurcher
100 *
101 * First upload to SourceForge
102 *
103 * Revision 1.12 2001/09/27 17:05:48 nick
104 *
105 * Assorted fixes and tweeks
106 *
107 * Revision 1.11 2001/08/08 17:05:17 nick
108 *
109 * Add support for attribute setting in the ini files
110 *
111 * Revision 1.10 2001/08/03 15:19:00 nick
112 *
113 * Add changes to set values before connect
114 *
115 * Revision 1.9 2001/07/03 09:30:41 nick
116 *
117 * Add ability to alter size of displayed message in the log
118 *
119 * Revision 1.8 2001/04/25 14:29:36 nick
120 *
121 * remove comment
122 *
123 * Revision 1.7 2001/04/23 13:58:43 nick
124 *
125 * Assorted tweeks to text driver to get it to work with StarOffice
126 *
127 * Revision 1.6 2001/04/20 13:58:13 nick
128 *
129 * Add txt driver
130 *
131 * Revision 1.5 2001/04/12 17:43:36 nick
132 *
133 * Change logging and added autotest to odbctest
134 *
135 * Revision 1.4 2001/02/06 18:43:38 nick
136 *
137 * Fix problem with SQLSetConnectAttr.c looking for UNICODE versions in
138 * ansi side of call
139 *
140 * Revision 1.3 2000/12/31 20:30:54 nick
141 *
142 * Add UNICODE support
143 *
144 * Revision 1.2 2000/11/14 10:15:27 nick
145 *
146 * Add test for localtime_r
147 *
148 * Revision 1.1.1.1 2000/09/04 16:42:52 nick
149 * Imported Sources
150 *
151 * Revision 1.11 2000/06/20 13:30:09 ngorham
152 *
153 * Fix problems when using bookmarks
154 *
155 * Revision 1.10 2000/05/21 21:49:19 ngorham
156 *
157 * Assorted fixes
158 *
159 * Revision 1.9 1999/11/13 23:41:00 ngorham
160 *
161 * Alter the way DM logging works
162 * Upgrade the Postgres driver to 6.4.6
163 *
164 * Revision 1.8 1999/11/10 03:51:34 ngorham
165 *
166 * Update the error reporting in the DM to enable ODBC 3 and 2 calls to
167 * work at the same time
168 *
169 * Revision 1.7 1999/10/24 23:54:18 ngorham
170 *
171 * First part of the changes to the error reporting
172 *
173 * Revision 1.6 1999/09/21 22:34:25 ngorham
174 *
175 * Improve performance by removing unneeded logging calls when logging is
176 * disabled
177 *
178 * Revision 1.5 1999/09/19 22:24:34 ngorham
179 *
180 * Added support for the cursor library
181 *
182 * Revision 1.4 1999/07/10 21:10:17 ngorham
183 *
184 * Adjust error sqlstate from driver manager, depending on requested
185 * version (ODBC2/3)
186 *
187 * Revision 1.3 1999/07/04 21:05:08 ngorham
188 *
189 * Add LGPL Headers to code
190 *
191 * Revision 1.2 1999/06/30 23:56:55 ngorham
192 *
193 * Add initial thread safety code
194 *
195 * Revision 1.1.1.1 1999/05/29 13:41:08 sShandyb
196 * first go at it
197 *
198 * Revision 1.1.1.1 1999/05/27 18:23:18 pharvey
199 * Imported sources
200 *
201 * Revision 1.2 1999/05/09 23:27:11 nick
202 * All the API done now
203 *
204 * Revision 1.1 1999/04/25 23:06:11 nick
205 * Initial revision
206 *
207 *
208 **********************************************************************/
209
210#include <config.h>
211#include "drivermanager.h"
212
213static char const rcsid[]= "$RCSfile: SQLSetConnectAttr.c,v $ $Revision: 1.17 $";
214
215SQLRETURN SQLSetConnectAttrA( SQLHDBC connection_handle,
216 SQLINTEGER attribute,
217 SQLPOINTER value,
218 SQLINTEGER string_length )
219{
220 return SQLSetConnectAttr( connection_handle,
221 attribute,
222 value,
223 string_length );
224}
225
226SQLRETURN SQLSetConnectAttr( SQLHDBC connection_handle,
227 SQLINTEGER attribute,
228 SQLPOINTER value,
229 SQLINTEGER string_length )
230{
231 DMHDBC connection = (DMHDBC)connection_handle;
232 SQLRETURN ret;
233 SQLCHAR s1[ 100 + LOG_MESSAGE_LEN ];
234
235 /*
236 * doesn't require a handle
237 */
238 if ( attribute == SQL_ATTR_TRACE )
239 {
240 if ((SQLLEN) value != SQL_OPT_TRACE_OFF &&
241 (SQLLEN) value != SQL_OPT_TRACE_ON )
242 {
243 if ( __validate_dbc( connection ))
244 {
245 thread_protect( SQL_HANDLE_DBC, connection );
246 dm_log_write( __FILE__,
247 __LINE__,
248 LOG_INFO,
249 LOG_INFO,
250 "Error: HY024" );
251
252 __post_internal_error( &connection -> error,
253 ERROR_HY024, NULL,
254 connection -> environment -> requested_version );
255
256 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
257 }
258 else
259 {
260 return SQL_INVALID_HANDLE;
261 }
262 }
263
264 if ((SQLLEN) value == SQL_OPT_TRACE_OFF )
265 {
266 char force_string[ 30 ];
267
268 SQLGetPrivateProfileString( "ODBC", "ForceTrace", "0",
269 force_string, sizeof( force_string ),
270 "ODBCINST.INI" );
271
272 if ( force_string[ 0 ] == '1' ||
273 toupper( force_string[ 0 ] ) == 'Y' ||
274 ( toupper( force_string[ 0 ] ) == 'O' &&
275 toupper( force_string[ 1 ] ) == 'N' ))
276 {
277 if ( log_info.log_flag )
278 {
279 dm_log_write( __FILE__,
280 __LINE__,
281 LOG_INFO,
282 LOG_INFO,
283 "Application tried to turn logging off" );
284 }
285 }
286 else
287 {
288 if ( log_info.log_flag )
289 {
290 dm_log_write( __FILE__,
291 __LINE__,
292 LOG_INFO,
293 LOG_INFO,
294 "Application turning logging off" );
295 }
296 log_info.log_flag = 0;
297 }
298 }
299 else
300 {
301 log_info.log_flag = 1;
302 }
303
304 return SQL_SUCCESS;
305 }
306 else if ( attribute == SQL_ATTR_TRACEFILE )
307 {
308 if ( value )
309 {
310 if (((SQLCHAR*)value)[ 0 ] == '\0' )
311 {
312 if ( __validate_dbc( connection ))
313 {
314 thread_protect( SQL_HANDLE_DBC, connection );
315 dm_log_write( __FILE__,
316 __LINE__,
317 LOG_INFO,
318 LOG_INFO,
319 "Error: HY024" );
320
321 __post_internal_error( &connection -> error,
322 ERROR_HY024, NULL,
323 connection -> environment -> requested_version );
324
325 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
326 }
327 else
328 {
329 return SQL_INVALID_HANDLE;
330 }
331 }
332 else
333 {
334 if ( log_info.log_file_name )
335 {
336 free( log_info.log_file_name );
337 }
338 log_info.log_file_name = strdup( value );
339 }
340 }
341 else
342 {
343 if ( __validate_dbc( connection ))
344 {
345 thread_protect( SQL_HANDLE_DBC, connection );
346 dm_log_write( __FILE__,
347 __LINE__,
348 LOG_INFO,
349 LOG_INFO,
350 "Error: HY024" );
351
352 __post_internal_error( &connection -> error,
353 ERROR_HY024, NULL,
354 connection -> environment -> requested_version );
355
356 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
357 }
358 else
359 {
360 return SQL_INVALID_HANDLE;
361 }
362 }
363 return SQL_SUCCESS;
364 }
365
366 /*
367 * check connection
368 */
369
370 if ( !__validate_dbc( connection ))
371 {
372 dm_log_write( __FILE__,
373 __LINE__,
374 LOG_INFO,
375 LOG_INFO,
376 "Error: SQL_INVALID_HANDLE" );
377
378 return SQL_INVALID_HANDLE;
379 }
380
381 function_entry( connection );
382
383 if ( log_info.log_flag )
384 {
385 sprintf( connection -> msg, "\n\t\tEntry:\
386\n\t\t\tConnection = %p\
387\n\t\t\tAttribute = %s\
388\n\t\t\tValue = %p\
389\n\t\t\tStrLen = %d",
390 connection,
391 __con_attr_as_string( s1, attribute ),
392 value,
393 (int)string_length );
394
395 dm_log_write( __FILE__,
396 __LINE__,
397 LOG_INFO,
398 LOG_INFO,
399 connection -> msg );
400 }
401
402 thread_protect( SQL_HANDLE_DBC, connection );
403
404 if ( connection -> state == STATE_C2 )
405 {
406 if ( attribute == SQL_ATTR_TRANSLATE_OPTION ||
407 attribute == SQL_ATTR_TRANSLATE_LIB )
408 {
409 dm_log_write( __FILE__,
410 __LINE__,
411 LOG_INFO,
412 LOG_INFO,
413 "Error: 08003" );
414
415 __post_internal_error( &connection -> error,
416 ERROR_08003, NULL,
417 connection -> environment -> requested_version );
418
419 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
420 }
421 }
422 else if ( connection -> state == STATE_C3 )
423 {
424 dm_log_write( __FILE__,
425 __LINE__,
426 LOG_INFO,
427 LOG_INFO,
428 "Error: HY010" );
429
430 __post_internal_error( &connection -> error,
431 ERROR_HY010, NULL,
432 connection -> environment -> requested_version );
433
434 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
435 }
436 else if ( connection -> state == STATE_C4 ||
437 connection -> state == STATE_C5 ||
438 connection -> state == STATE_C6 )
439 {
440 if ( attribute == SQL_ATTR_ODBC_CURSORS )
441 {
442 dm_log_write( __FILE__,
443 __LINE__,
444 LOG_INFO,
445 LOG_INFO,
446 "Error: 08002" );
447
448 __post_internal_error( &connection -> error,
449 ERROR_08002, NULL,
450 connection -> environment -> requested_version );
451
452 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
453 }
454 else if ( attribute == SQL_ATTR_PACKET_SIZE )
455 {
456 dm_log_write( __FILE__,
457 __LINE__,
458 LOG_INFO,
459 LOG_INFO,
460 "Error: HY011" );
461
462 __post_internal_error( &connection -> error,
463 ERROR_HY011, NULL,
464 connection -> environment -> requested_version );
465
466 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
467 }
468 }
469
470 /*
471 * is it a legitimate value
472 */
473 ret = dm_check_connection_attrs( connection, attribute, value );
474
475 if ( ret != SQL_SUCCESS )
476 {
477 dm_log_write( __FILE__,
478 __LINE__,
479 LOG_INFO,
480 LOG_INFO,
481 "Error: HY024" );
482
483 __post_internal_error( &connection -> error,
484 ERROR_HY024, NULL,
485 connection -> environment -> requested_version );
486
487 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
488 }
489
490 /*
491 * is it a connection attribute or statement, check state of any active connections
492 */
493
494 switch( attribute )
495 {
496 /* ODBC 3.x statement attributes are not settable at the connection level */
497 case SQL_ATTR_APP_PARAM_DESC:
498 case SQL_ATTR_APP_ROW_DESC:
499 case SQL_ATTR_CURSOR_SCROLLABLE:
500 case SQL_ATTR_CURSOR_SENSITIVITY:
501 case SQL_ATTR_ENABLE_AUTO_IPD:
502 case SQL_ATTR_FETCH_BOOKMARK_PTR:
503 case SQL_ATTR_IMP_PARAM_DESC:
504 case SQL_ATTR_IMP_ROW_DESC:
505 case SQL_ATTR_PARAM_BIND_OFFSET_PTR:
506 case SQL_ATTR_PARAM_BIND_TYPE:
507 case SQL_ATTR_PARAM_OPERATION_PTR:
508 case SQL_ATTR_PARAM_STATUS_PTR:
509 case SQL_ATTR_PARAMS_PROCESSED_PTR:
510 case SQL_ATTR_PARAMSET_SIZE:
511 case SQL_ATTR_ROW_ARRAY_SIZE:
512 case SQL_ATTR_ROW_BIND_OFFSET_PTR:
513 case SQL_ATTR_ROW_OPERATION_PTR:
514 case SQL_ATTR_ROW_STATUS_PTR:
515 case SQL_ATTR_ROWS_FETCHED_PTR:
516 __post_internal_error( &connection -> error,
517 ERROR_HY092, NULL,
518 connection -> environment -> requested_version );
519
520 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
521
522 case SQL_ATTR_CONCURRENCY:
523 case SQL_BIND_TYPE:
524 case SQL_ATTR_CURSOR_TYPE:
525 case SQL_ATTR_MAX_LENGTH:
526 case SQL_MAX_ROWS:
527 case SQL_ATTR_KEYSET_SIZE:
528 case SQL_ROWSET_SIZE:
529 case SQL_ATTR_NOSCAN:
530 case SQL_ATTR_QUERY_TIMEOUT:
531 case SQL_ATTR_RETRIEVE_DATA:
532 case SQL_ATTR_SIMULATE_CURSOR:
533 case SQL_ATTR_USE_BOOKMARKS:
534 if( __check_stmt_from_dbc_v( connection, 5, STATE_S8, STATE_S9, STATE_S10, STATE_S11, STATE_S12 )) {
535
536 dm_log_write( __FILE__,
537 __LINE__,
538 LOG_INFO,
539 LOG_INFO,
540 "Error: 24000" );
541
542 __post_internal_error( &connection -> error,
543 ERROR_24000, NULL,
544 connection -> environment -> requested_version );
545
546 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
547 }
548 break;
549
550 default:
551
552 if( __check_stmt_from_dbc_v( connection, 5, STATE_S8, STATE_S9, STATE_S10, STATE_S11, STATE_S12 )) {
553
554 dm_log_write( __FILE__,
555 __LINE__,
556 LOG_INFO,
557 LOG_INFO,
558 "Error: HY010" );
559
560 __post_internal_error( &connection -> error,
561 ERROR_HY010, NULL,
562 connection -> environment -> requested_version );
563
564 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
565 }
566 break;
567 }
568
569 /*
570 * is it something overridden
571 */
572
573 value = __attr_override( connection, SQL_HANDLE_DBC, attribute, value, &string_length );
574
575 /*
576 * we need to save this even if connected so we can use it for the next connect
577 */
578 if ( attribute == SQL_ATTR_LOGIN_TIMEOUT )
579 {
580 connection -> login_timeout = ( SQLLEN ) value;
581 connection -> login_timeout_set = 1;
582 }
583
584 /*
585 * if connected, call the driver
586 * otherwise we need to save the states and set them when we
587 * do connect
588 */
589 if ( connection -> state == STATE_C2 )
590 {
591 /*
592 * is it for us
593 */
594
595 if ( attribute == SQL_ATTR_ODBC_CURSORS )
596 {
597 connection -> cursors = ( SQLLEN ) value;
598 }
599 else if ( attribute == SQL_ATTR_ACCESS_MODE )
600 {
601 connection -> access_mode = ( SQLLEN ) value;
602 connection -> access_mode_set = 1;
603 }
604 else if ( attribute == SQL_ATTR_ASYNC_ENABLE )
605 {
606 connection -> async_enable = ( SQLLEN ) value;
607 connection -> async_enable_set = 1;
608 }
609 else if ( attribute == SQL_ATTR_AUTO_IPD )
610 {
611 connection -> auto_ipd = ( SQLLEN ) value;
612 connection -> auto_ipd_set = 1;
613 }
614 else if ( attribute == SQL_ATTR_AUTOCOMMIT )
615 {
616 connection -> auto_commit = ( SQLLEN ) value;
617 connection -> auto_commit_set = 1;
618 }
619 else if ( attribute == SQL_ATTR_CONNECTION_TIMEOUT )
620 {
621 connection -> connection_timeout = ( SQLLEN ) value;
622 connection -> connection_timeout_set = 1;
623 }
624 else if ( attribute == SQL_ATTR_METADATA_ID )
625 {
626 connection -> metadata_id = ( SQLLEN ) value;
627 connection -> metadata_id_set = 1;
628 }
629 else if ( attribute == SQL_ATTR_PACKET_SIZE )
630 {
631 connection -> packet_size = ( SQLLEN ) value;
632 connection -> packet_size_set = 1;
633 }
634 else if ( attribute == SQL_ATTR_QUIET_MODE )
635 {
636 connection -> quite_mode = ( SQLLEN ) value;
637 connection -> quite_mode_set = 1;
638 }
639 else if ( attribute == SQL_ATTR_TXN_ISOLATION )
640 {
641 connection -> txn_isolation = ( SQLLEN ) value;
642 connection -> txn_isolation_set = 1;
643 }
644 else if ( attribute != SQL_ATTR_LOGIN_TIMEOUT )
645 {
646 /*
647 * save any unknown attributes untill connect
648 */
649
650 struct save_attr *sa = calloc( 1, sizeof( struct save_attr ));
651
652 sa -> attr_type = attribute;
653 if ( string_length > 0 )
654 {
655 sa -> str_attr = malloc( string_length );
656 memcpy( sa -> str_attr, value, string_length );
657 sa -> str_len = string_length;
658 }
659 else if ( string_length == SQL_NTS )
660 {
661 if (!value)
662 {
663 __post_internal_error( &connection -> error,
664 ERROR_HY024, "Invalid argument value",
665 connection -> environment -> requested_version );
666 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
667 }
668 else
669 {
670 sa -> str_attr = strdup( value );
671 sa -> str_len = string_length;
672 }
673 }
674 else
675 {
676 sa -> int_attr = ( SQLLEN ) value;
677 sa -> str_len = string_length;
678 }
679 sa -> next = connection -> save_attr;
680 connection -> save_attr = sa;
681 }
682
683 sprintf( connection -> msg,
684 "\n\t\tExit:[%s]",
685 __get_return_status( SQL_SUCCESS, s1 ));
686
687 dm_log_write( __FILE__,
688 __LINE__,
689 LOG_INFO,
690 LOG_INFO,
691 connection -> msg );
692
693 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_SUCCESS );
694 }
695 else
696 {
697 if ( !connection -> unicode_driver )
698 {
699 if ( !CHECK_SQLSETCONNECTATTR( connection ))
700 {
701 if ( CHECK_SQLSETCONNECTOPTION( connection ))
702 {
703 /*
704 * Is it in the legal range of values
705 */
706
707 if ( attribute < SQL_CONN_DRIVER_MIN &&
708 ( attribute > SQL_PACKET_SIZE || attribute < SQL_ACCESS_MODE ))
709 {
710 dm_log_write( __FILE__,
711 __LINE__,
712 LOG_INFO,
713 LOG_INFO,
714 "Error: HY092" );
715
716 __post_internal_error( &connection -> error,
717 ERROR_HY092, NULL,
718 connection -> environment -> requested_version );
719
720 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
721 }
722
723 ret = SQLSETCONNECTOPTION( connection,
724 connection -> driver_dbc,
725 attribute,
726 value );
727 }
728 else
729 {
730 dm_log_write( __FILE__,
731 __LINE__,
732 LOG_INFO,
733 LOG_INFO,
734 "Error: IM001" );
735
736 __post_internal_error( &connection -> error,
737 ERROR_IM001, NULL,
738 connection -> environment -> requested_version );
739
740 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
741 }
742 }
743 else
744 {
745 ret = SQLSETCONNECTATTR( connection,
746 connection -> driver_dbc,
747 attribute,
748 value,
749 string_length );
750 }
751 }
752 else
753 {
754 if ( !CHECK_SQLSETCONNECTATTRW( connection ))
755 {
756 if ( CHECK_SQLSETCONNECTOPTIONW( connection ))
757 {
758 SQLWCHAR *s1;
759
760 /*
761 * Is it in the legal range of values
762 */
763
764 if ( attribute < SQL_CONN_DRIVER_MIN &&
765 ( attribute > SQL_PACKET_SIZE || attribute < SQL_ACCESS_MODE ))
766 {
767 dm_log_write( __FILE__,
768 __LINE__,
769 LOG_INFO,
770 LOG_INFO,
771 "Error: HY092" );
772
773 __post_internal_error( &connection -> error,
774 ERROR_HY092, NULL,
775 connection -> environment -> requested_version );
776
777 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
778 }
779
780 switch( attribute )
781 {
782 case SQL_ATTR_CURRENT_CATALOG:
783 case SQL_ATTR_TRACEFILE:
784 case SQL_ATTR_TRANSLATE_LIB:
785 s1 = ansi_to_unicode_alloc( value, SQL_NTS, connection, NULL );
786
787 ret = SQLSETCONNECTOPTIONW( connection,
788 connection -> driver_dbc,
789 attribute,
790 s1 );
791
792 if ( s1 )
793 free( s1 );
794
795 break;
796
797 default:
798 ret = SQLSETCONNECTOPTIONW( connection,
799 connection -> driver_dbc,
800 attribute,
801 value );
802 break;
803 }
804 }
805 else
806 {
807 dm_log_write( __FILE__,
808 __LINE__,
809 LOG_INFO,
810 LOG_INFO,
811 "Error: IM001" );
812
813 __post_internal_error( &connection -> error,
814 ERROR_IM001, NULL,
815 connection -> environment -> requested_version );
816
817 return function_return_nodrv( SQL_HANDLE_DBC, connection, SQL_ERROR );
818 }
819 }
820 else
821 {
822 SQLWCHAR *s1;
823
824 switch( attribute )
825 {
826 case SQL_ATTR_CURRENT_CATALOG:
827 case SQL_ATTR_TRACEFILE:
828 case SQL_ATTR_TRANSLATE_LIB:
829 s1 = ansi_to_unicode_alloc( value, string_length, connection, NULL );
830
831 ret = SQLSETCONNECTATTRW( connection,
832 connection -> driver_dbc,
833 attribute,
834 s1,
835 string_length == SQL_NTS ? SQL_NTS : string_length * sizeof( SQLWCHAR ));
836
837 if ( s1 )
838 free( s1 );
839 break;
840
841 default:
842 ret = SQLSETCONNECTATTRW( connection,
843 connection -> driver_dbc,
844 attribute,
845 value,
846 string_length );
847 break;
848 }
849 }
850 }
851
852 if ( log_info.log_flag )
853 {
854 sprintf( connection -> msg,
855 "\n\t\tExit:[%s]",
856 __get_return_status( ret, s1 ));
857
858 dm_log_write( __FILE__,
859 __LINE__,
860 LOG_INFO,
861 LOG_INFO,
862 connection -> msg );
863 }
864 }
865
866 /*
867 * catch this
868 */
869
870 if ( attribute == SQL_ATTR_USE_BOOKMARKS && SQL_SUCCEEDED( ret ))
871 {
872 connection -> bookmarks_on = (SQLLEN) value;
873 }
874
875 return function_return( SQL_HANDLE_DBC, connection, ret );
876}
877