File: drivermanager.h

package info (click to toggle)
unixodbc 2.3.1-3
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 11,524 kB
  • ctags: 7,656
  • sloc: ansic: 89,405; sh: 15,975; makefile: 1,574; yacc: 969; sql: 1
file content (1444 lines) | stat: -rw-r--r-- 56,705 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
1418
1419
1420
1421
1422
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
#ifndef _DRIVERMANAGER_H
#define _DRIVERMANAGER_H

#define ODBCVER 0x0380

#ifdef HAVE_SYS_TYPES_H
#include <sys/types.h>
#endif
#ifdef HAVE_PWD_H
#include <pwd.h>
#endif
#include <ltdl.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_TIME_H
#include <time.h>
#endif

#ifdef HAVE_SYNCH_H
#include <synch.h>
#endif
    
#ifdef HAVE_LIBPTH
#include <pth.h>
#elif HAVE_LIBPTHREAD
#include <pthread.h>
#elif HAVE_LIBTHREAD
#include <thread.h>
#endif

#define SQL_NOUNICODEMAP
#define  UNICODE

#include <log.h>
#include <ini.h>
#include <odbcinstext.h>
#include <sqlext.h>                     /* THIS WILL BRING IN sql.h and
                                           sqltypes.h AS WELL AS PROVIDE
                                           MS EXTENSIONS */
#include <sqlucode.h>
#include "__stats.h"

/*
 * iconv support
 */

#ifdef HAVE_ICONV
#include <stdlib.h>
#include <iconv.h>
#endif

#ifdef UNICODE_ENCODING
#define DEFAULT_ICONV_ENCODING      UNICODE_ENCODING 
#else
#define DEFAULT_ICONV_ENCODING      "auto-search"
#endif

#define ERROR_PREFIX        "[unixODBC]"
#define DM_ERROR_PREFIX     "[Driver Manager]"
#define LOG_MESSAGE_LEN     128         /* length of string to display in log */

/*
 * SQLSetStmt/ConnectionAttr limits
 */

#define SQL_CONN_DRIVER_MIN     20000
#define SQL_STMT_DRIVER_MIN     20000

/*
 * its possible that the driver has a different definition of a handle to the driver
 * manager, DB2 64bit is a example of this
 */

#define DRV_SQLHANDLE			SQLHANDLE
#define DRV_SQLHDESC			SQLHDESC

/*
 * DEFAULT FILE NAMES
 *
 */

/*
 * magic numbers
 */

#define HENV_MAGIC      19289
#define HDBC_MAGIC      19290
#define HSTMT_MAGIC     19291
#define HDESC_MAGIC     19292

/*
 * states
 */

#define STATE_E0        0
#define STATE_E1        1
#define STATE_E2        2

#define STATE_C0        0
#define STATE_C1        1
#define STATE_C2        2
#define STATE_C3        3
#define STATE_C4        4
#define STATE_C5        5
#define STATE_C6        6

#define STATE_S0        0
#define STATE_S1        1
#define STATE_S2        2
#define STATE_S3        3
#define STATE_S4        4
#define STATE_S5        5
#define STATE_S6        6
#define STATE_S7        7
#define STATE_S8        8
#define STATE_S9        9
#define STATE_S10       10
#define STATE_S11       11
#define STATE_S12       12

#define STATE_D0        0
#define STATE_D1i       1
#define STATE_D1e       2

/*
 * structure to contain the loaded lib entry points
 */

struct driver_func
{
    int         ordinal;
    char        *name;
    void        *dm_func;               /* this is to fix what seems a bug in */
			                            /* some dlopen implemnations where dlsym */
					                    /* will return the driver manager func */
					                    /* not the driver one */
    void        *dm_funcW;
    SQLRETURN   (*func)();
    SQLRETURN   (*funcW)();             /* function with a unicode W */
    SQLRETURN   (*funcA)();             /* function with a unicode A */
    int         can_supply;             /* this is used to indicate that */
                                        /* the DM can execute the function */
                                        /* even if the driver does not */
                                        /* supply it */
};

typedef struct error
{
    SQLWCHAR    sqlstate[ 6 ];
    SQLWCHAR    *msg;
    SQLINTEGER  native_error;
    int         return_val;
    SQLRETURN   diag_column_number_ret;
    SQLRETURN   diag_row_number_ret;
    SQLRETURN   diag_class_origin_ret;
    SQLRETURN   diag_subclass_origin_ret;
    SQLRETURN   diag_connection_name_ret;
    SQLRETURN   diag_server_name_ret;
    SQLINTEGER  diag_column_number;
    SQLINTEGER  diag_row_number;
    SQLWCHAR    diag_class_origin[ 128 ];
    SQLWCHAR    diag_subclass_origin[ 128 ];
    SQLWCHAR    diag_connection_name[ 128 ];
    SQLWCHAR    diag_server_name[ 128 ];
    struct error *next;
    struct error *prev;

} ERROR;

typedef struct error_header
{
    int         error_count;
    ERROR       *error_list_head;
    ERROR       *error_list_tail;
    int         internal_count;
    ERROR       *internal_list_head;
    ERROR       *internal_list_tail;
} EHEADER;

typedef struct error_head
{
    EHEADER     sql_error_head;
    EHEADER     sql_diag_head;
    void        *owning_handle;
    int         handle_type;
    SQLRETURN   return_code;
    SQLINTEGER  header_set;
    SQLRETURN   diag_cursor_row_count_ret;
    SQLRETURN   diag_dynamic_function_ret;
    SQLRETURN   diag_dynamic_function_code_ret;
    SQLRETURN   diag_number_ret;
    SQLRETURN   diag_row_count_ret;
    SQLLEN      diag_cursor_row_count;
    SQLWCHAR    diag_dynamic_function[ 128 ];
    SQLINTEGER  diag_dynamic_function_code;
    SQLLEN      diag_number;
    SQLLEN      diag_row_count;
} EHEAD;

struct log_structure
{
    char    *program_name;
    char    *log_file_name;
    int     log_flag;
    int     pid_logging;            /* the log path specifies a directory, and a */
                                    /* log file per pid is created */

};

extern struct log_structure log_info;

/*
 * save connection attr untill after the connect, and then pass on
 */

struct save_attr
{
    int                 attr_type;
    char                *str_attr;
    int                 str_len;
    int                 int_attr;
    struct save_attr    *next;
};

/*
 * attribute extension support
 */

struct attr_set
{
    char            *keyword;
    char            *value;
    int             override;
    int             attribute;
    int             is_int_type;
    int             int_value;
    struct attr_set *next;
};

struct attr_struct
{
    int             count;
    struct attr_set *list;
};

int __parse_attribute_string( struct attr_struct *attr_str,
    char *str, int str_len );
void __release_attr_str( struct attr_struct *attr_str );
void __set_attributes( void *handle, int type );
void __set_local_attributes( void *handle, int type );
void *__attr_override( void *handle, int type, int attribute, void * value, SQLINTEGER *string_length );
void *__attr_override_wide( void *handle, int type, int attribute, void * value, SQLINTEGER *string_length, SQLWCHAR *buffer );

/*
 * use this to maintain a list of the drivers that are loaded under this env,
 * and to decide if we want to call SQLAllocHandle( SQL_ENV ) om them
 */

struct env_lib_struct
{
    char            *lib_name;
    DRV_SQLHANDLE   env_handle;
    int             count;
    struct env_lib_struct   *next;
};

typedef struct environment
{
    int             type;               /* magic number */
    struct environment *next_class_list;/* static list of all env handles */
    char            msg[ LOG_MSG_MAX ];	/* buff to format msgs */
    int             state;              /* state of environment */
    SQLINTEGER      requested_version;  /* SQL_OV_ODBC2 or SQL_OV_ODBC3 */
    int             connection_count;   /* number of hdbc of this env */
    int             sql_driver_count;   /* used for SQLDrivers */
    EHEAD           error;              /* keep track of errors */
    SQLINTEGER      connection_pooling; /* does connection pooling operate */
    SQLINTEGER      cp_match;
    int             fetch_mode;         /* for SQLDataSources */
    int             entry;
    void            *sh;                /* statistics handle */
    int             driver_act_ver;     /* real version of the driver */
    struct env_lib_struct *env_lib_list;/* use this to avoid multiple AllocEnv in the driver */
} *DMHENV;


#ifdef FAST_HANDLE_VALIDATE
    struct statement;
#endif


/*
 * connection pooling attributes
 */

typedef struct connection
{
    int             type;               /* magic number */
    struct connection *next_class_list; /* static list of all dbc handles */
    char            msg[ LOG_MSG_MAX ]; /* buff to format msgs */
    int             state;              /* state of connection */
    DMHENV          environment;        /* environment that own's the
                                           connection */
#ifdef FAST_HANDLE_VALIDATE
    struct statement *statements;       /* List of statements owned by this 
                                           connection */
#endif
    
    void            *dl_handle;         /* handle of the loaded lib */
    char            dl_name[ 256 ];     /* name of loaded lib */
    struct driver_func *functions;      /* entry points */
    struct driver_func  ini_func;       /* optinal start end functions */
    struct driver_func  fini_func;
    int             unicode_driver;     /* do we use the W functions in the */
                                        /* driver ? */
    DRV_SQLHANDLE 	driver_env;         /* environment handle in client */
    DRV_SQLHANDLE   driver_dbc;         /* connection handle in client */
    int             driver_version;     /* required version of the connected */
                                        /* driver */
    int             driver_act_ver;     /* real version of the driver */
    int             statement_count;    /* number of statements on this dbc */
    EHEAD           error;              /* keep track of errors */
    char            dsn[ SQL_MAX_DSN_LENGTH + 1 ];  /* where we are connected */
    int             access_mode;        /* variables set via SQLSetConnectAttr */
    int             access_mode_set;      
    int             login_timeout;
    int             login_timeout_set;
    int             auto_commit;
    int             auto_commit_set;
    int             async_enable;
    int             async_enable_set;
    int             auto_ipd;
    int             auto_ipd_set;
    int             connection_timeout;
    int             connection_timeout_set;
    int             metadata_id;
    int             metadata_id_set;
    int             packet_size;
    int             packet_size_set;
    SQLLEN          quite_mode;
    int             quite_mode_set;
    int             txn_isolation;
    int             txn_isolation_set;

    SQLINTEGER      cursors;
    void            *cl_handle;         /* handle to the cursor lib */
    int             trace;
    char            tracefile[ INI_MAX_PROPERTY_VALUE + 1 ];
#ifdef HAVE_LIBPTH
    pth_mutex_t     mutex;              /* protect the object */
    int             protection_level;
#elif HAVE_LIBPTHREAD
    pthread_mutex_t mutex;              /* protect the object */
    int             protection_level;
#elif HAVE_LIBTHREAD
    mutex_t mutex;              		/* protect the object */
    int             protection_level;
#endif
    int             ex_fetch_mapping;   /* disable SQLFetch -> SQLExtendedFetch */
    int             disable_gf;         /* dont call SQLGetFunctions in the driver */
    int             dont_dlclose;       /* disable dlclosing of the handle */
    int             bookmarks_on;       /* bookmarks are set on */
    void            *pooled_connection; /* points to t connection pool structure */
    int             pooling_timeout;
    int             ttl;
    char            driver_connect_string[ 1024 ];
    int             dsn_length;
    char            server[ 128 ];
    int             server_length;
    char            user[ 128 ];
    int             user_length;
    char            password[ 128 ];
    int             password_length;
    char            cli_year[ 5 ];
    struct attr_struct  env_attribute;      /* Extended attribute set info */
    struct attr_struct  dbc_attribute;
    struct attr_struct  stmt_attribute;
    struct save_attr    *save_attr;         /* SQLConnectAttr before connect */
#ifdef HAVE_ICONV
    iconv_t         iconv_cd_uc_to_ascii;   /* in and out conversion descriptor */
    iconv_t         iconv_cd_ascii_to_uc;
    char            unicode_string[ 64 ];   /* name of unicode conversion */
#endif
    struct env_lib_struct *env_list_ent;    /* pointer to reference in the env list */
    char            probe_sql[ 512 ];       /* SQL to use to check a pool is valid */
	int				threading_level;		/* level of thread protection the DM proves */
	int				cbs_found;				/* Have we queried the driver for the effect of a */
	SQLSMALLINT		ccb_value;				/* COMMIT or a ROLLBACK */
	SQLSMALLINT		crb_value;
} *DMHDBC;

typedef struct connection_pool
{
    char    driver_connect_string[ 1024 ];
    int     dsn_length;
    char    server[ 128 ];
    int     server_length;
    char    user[ 128 ];
    int     user_length;
    char    password[ 128 ];
    int     password_length;
    time_t  expiry_time;
    int     ttl;
    int     timeout;
    int     in_use;
    struct  connection_pool *next;
    struct  connection connection;
    int     cursors;
} CPOOL;

typedef struct descriptor
{
    int             type;               /* magic number */
    struct descriptor *next_class_list; /* static list of all desc handles */
    char            msg[ LOG_MSG_MAX ]; /* buff to format msgs */
    int             state;              /* state of descriptor */

#ifdef FAST_HANDLE_VALIDATE
    struct descriptor *prev_class_list;/* static list of all desc handles */
#endif    

    EHEAD           error;              /* keep track of errors */
    DRV_SQLHDESC    driver_desc;        /* driver descriptor */
    DMHDBC          connection;         /* DM connection that owns this */
    int             implicit;           /* created by a AllocStmt */
    void            *associated_with;   /* statement that this is a descriptor of */
#ifdef HAVE_LIBPTH
    pth_mutex_t     mutex;              /* protect the object */
#elif HAVE_LIBPTHREAD
    pthread_mutex_t mutex;              /* protect the object */
#elif HAVE_LIBTHREAD
    mutex_t mutex;              		/* protect the object */
#endif
} *DMHDESC;

typedef struct statement
{
    int             type;               /* magic number */
    struct statement *next_class_list;  /* static list of all stmt handles */
    char            msg[ LOG_MSG_MAX ]; /* buff to format msgs */
    int             state;              /* state of statement */
#ifdef FAST_HANDLE_VALIDATE
    struct statement *prev_class_list;  /* static list of all stmt handles */
    struct statement *next_conn_list;   /* Single linked list storing statements 
                                           owned by "connection" connection */
#endif
    DMHDBC          connection;         /* DM connection that owns this */
    DRV_SQLHANDLE   driver_stmt;        /* statement in the driver */
    SQLSMALLINT     hascols;            /* is there a result set */
    int             prepared;           /* the statement has been prepared */
    int             interupted_func;    /* current function running async */
                                        /* or NEED_DATA */
    int             interupted_state;   /* state we went into need data or */
                                        /* still executing from */
    int             bookmarks_on;       /* bookmarks are set on */
    EHEAD           error;              /* keep track of errors */
    SQLINTEGER      metadata_id;
    DMHDESC         ipd;                /* current descriptors */
    DMHDESC         apd;
    DMHDESC         ird;
    DMHDESC         ard;
    DMHDESC         implicit_ipd;       /* implicit descriptors */
    DMHDESC         implicit_apd;
    DMHDESC         implicit_ird;
    DMHDESC         implicit_ard;
    SQLULEN		    *fetch_bm_ptr;      /* Saved for ODBC3 to ODBC2 mapping */ 
    SQLULEN     	*row_ct_ptr;        /* row count ptr */
    SQLUSMALLINT    *row_st_arr;        /* row status array */
    SQLULEN     	row_array_size;
	SQLPOINTER      valueptr;           /* Default buffer for SQLParamData() */

#ifdef HAVE_LIBPTH
    pth_mutex_t     mutex;              /* protect the object */
#elif HAVE_LIBPTHREAD
    pthread_mutex_t mutex;              /* protect the object */
#elif HAVE_LIBTHREAD
    mutex_t mutex;              		/* protect the object */

#endif

    int             eod;                /* when in S6 has EOD been returned */
} *DMHSTMT;

#if defined ( HAVE_LIBPTHREAD ) || defined ( HAVE_LIBTHREAD ) || defined ( HAVE_LIBPTH )
#define TS_LEVEL0   0           /* no implicit protection, only for */
                                /* dm internal structures */
#define TS_LEVEL1   1           /* protection on a statement level */
#define TS_LEVEL2   2           /* protection on a connection level */
#define TS_LEVEL3   3           /* protection on a environment level */
#endif

void mutex_lib_entry( void );
void mutex_lib_exit( void );

void mutex_pool_entry( void );
void mutex_pool_exit( void );

void mutex_iconv_entry( void );
void mutex_iconv_exit( void );

typedef struct connection_pair
{
    char            *name;
    char            *value;
    struct connection_pair *next;
} *connection_attribute;

/*
 * defined down here to get the DMHDBC definition
 */

void __handle_attr_extensions( DMHDBC connection, char *dsn, char *driver_name );

/*
 * handle allocation functions
 */

DMHENV __alloc_env( void );
int __validate_env( DMHENV );
void __release_env( DMHENV environment );

DMHDBC __alloc_dbc( void );
int __validate_dbc( DMHDBC );
void __release_dbc( DMHDBC connection );

DMHSTMT __alloc_stmt( void );
void __register_stmt ( DMHDBC connection, DMHSTMT statement );
void __set_stmt_state ( DMHDBC connection, SQLSMALLINT cb_value );
int __validate_stmt( DMHSTMT );
void __release_stmt( DMHSTMT );

DMHDESC __alloc_desc( void );
int __validate_desc( DMHDESC );
void __release_desc( DMHDESC );

/*
 * generic functions
 */

SQLRETURN __SQLAllocHandle( SQLSMALLINT handle_type,
           SQLHANDLE input_handle,
           SQLHANDLE *output_handle,
           SQLINTEGER requested_version );

SQLRETURN __SQLFreeHandle( SQLSMALLINT handle_type,
           SQLHANDLE handle );

SQLRETURN __SQLGetInfo( SQLHDBC connection_handle,
		 	SQLUSMALLINT info_type,
			SQLPOINTER info_value,
			SQLSMALLINT buffer_length,
			SQLSMALLINT *string_length );

int __connect_part_one( DMHDBC connection, char *driver_lib, char *driver_name, int *warnings );
void __disconnect_part_one( DMHDBC connection );
int __connect_part_two( DMHDBC connection );
void __disconnect_part_two( DMHDBC connection );
void __disconnect_part_three( DMHDBC connection );
void __disconnect_part_four( DMHDBC connection );
DMHDBC __get_dbc_root( void );

void  __check_for_function( DMHDBC connection,
        SQLUSMALLINT function_id,
        SQLUSMALLINT *supported );

int __clean_stmt_from_dbc( DMHDBC connection );
int __clean_desc_from_dbc( DMHDBC connection );
void __map_error_state( char * state, int requested_version );
void __map_error_state_w( SQLWCHAR * wstate, int requested_version );

/*
 * mapping from ODBC 2 <-> 3 datetime types
 */

#define MAP_SQL_DM2D 	0
#define MAP_SQL_D2DM 	1
#define MAP_C_DM2D 	2
#define MAP_C_D2DM 	3

SQLSMALLINT __map_type( int map, DMHDBC connection, SQLSMALLINT type);

/*
 * error functions
 */

typedef enum error_id
{
    ERROR_01000,
    ERROR_01004,
    ERROR_01S02,
    ERROR_01S06,
    ERROR_07005,
    ERROR_07009,
    ERROR_08002,
    ERROR_08003,
    ERROR_24000,
    ERROR_25000,
    ERROR_25S01,
    ERROR_S1000,
    ERROR_S1003,
    ERROR_S1010,
    ERROR_S1011,
    ERROR_S1107,
    ERROR_S1108,
    ERROR_S1C00,
    ERROR_HY001,
    ERROR_HY003,
    ERROR_HY004,
    ERROR_HY007,
    ERROR_HY009,
    ERROR_HY010,
    ERROR_HY011,
    ERROR_HY012,
    ERROR_HY013,
    ERROR_HY017,
    ERROR_HY024,
    ERROR_HY090,
    ERROR_HY092,
    ERROR_HY097,
    ERROR_HY098,
    ERROR_HY099,
    ERROR_HY100,
    ERROR_HY101,
    ERROR_HY103,
    ERROR_HY105,
    ERROR_HY106,
    ERROR_HY110,
    ERROR_HY111,
    ERROR_HYC00,
    ERROR_IM001,
    ERROR_IM002,
    ERROR_IM003,
    ERROR_IM004,
    ERROR_IM005,
    ERROR_IM010,
    ERROR_IM012,
    ERROR_SL004,
    ERROR_SL009,
    ERROR_SL010,
    ERROR_SL008,
    ERROR_HY000
} error_id;

#define IGNORE_THREAD       (-1)

#define function_return(l,h,r)    function_return_ex(l,h,r,FALSE)

#define SUBCLASS_ODBC           0
#define SUBCLASS_ISO            1

void __post_internal_error( EHEAD *error_handle,
        error_id, char *txt, int connection_mode );
void __post_internal_error_api( EHEAD *error_handle,
        error_id, char *txt, int connection_mode, int calling_api );
void __post_internal_error_ex( EHEAD *error_handle,
        SQLCHAR *sqlstate,
        SQLINTEGER native_error,
        SQLCHAR *message_text,
        int class_origin,
        int subclass_origin );
void __post_internal_error_ex_w( EHEAD *error_handle,
        SQLWCHAR *sqlstate,
        SQLINTEGER native_error,
        SQLWCHAR *message_text,
        int class_origin,
        int subclass_origin );
int function_return_ex( int level, void * handle, int ret_code, int save_to_diag );
void function_entry( void *handle );
void setup_error_head( EHEAD *error_header, void *handle, int handle_type );
void clear_error_head( EHEAD *error_header );
SQLWCHAR *ansi_to_unicode_copy( SQLWCHAR * dest, char *src, SQLINTEGER buffer_len, DMHDBC connection );
SQLWCHAR *ansi_to_unicode_alloc( SQLCHAR *str, SQLINTEGER len, DMHDBC connection );
char *unicode_to_ansi_copy( char* dest, int dest_len, SQLWCHAR *src, SQLINTEGER len, DMHDBC connection );
char *unicode_to_ansi_alloc( SQLWCHAR *str, SQLINTEGER len, DMHDBC connection );
int unicode_setup( DMHDBC connection );
void unicode_shutdown( DMHDBC connection );
char * __get_return_status( SQLRETURN ret, SQLCHAR *buffer );
char * __sql_as_text( SQLINTEGER type );
char * __c_as_text( SQLINTEGER type );
char * __string_with_length( SQLCHAR *out, SQLCHAR *str, SQLINTEGER len );
char * __string_with_length_pass( SQLCHAR *out, SQLCHAR *str, SQLINTEGER len );
char * __string_with_length_hide_pwd( SQLCHAR *out, SQLCHAR *str, SQLINTEGER len );
char * __wstring_with_length( SQLCHAR *out, SQLWCHAR *str, SQLINTEGER len );
char * __wstring_with_length_pass( SQLCHAR *out, SQLWCHAR *str, SQLINTEGER len );
char * __wstring_with_length_hide_pwd( SQLCHAR *out, SQLWCHAR *str, SQLINTEGER len );
SQLWCHAR *wide_strcpy( SQLWCHAR *str1, SQLWCHAR *str2 );
SQLWCHAR *wide_strncpy( SQLWCHAR *str1, SQLWCHAR *str2, int buffer_length );
SQLWCHAR *wide_strcat( SQLWCHAR *str1, SQLWCHAR *str2 );
SQLWCHAR *wide_strdup( SQLWCHAR *str1 );
int wide_strlen( SQLWCHAR *str1 );
int wide_ansi_strncmp( SQLWCHAR *str1, char *str2, int len );
char * __get_pid( SQLCHAR *str );
char * __iptr_as_string( SQLCHAR *s, SQLINTEGER *ptr );
char * __ptr_as_string( SQLCHAR *s, SQLLEN *ptr );
char * __sptr_as_string( SQLCHAR *s, SQLSMALLINT *ptr );
char * __info_as_string( SQLCHAR *s, SQLINTEGER typ );
void __clear_internal_error( struct error *error_handle );
char * __data_as_string( SQLCHAR *s, SQLINTEGER type, 
        SQLLEN *ptr, SQLPOINTER buf );
char * __sdata_as_string( SQLCHAR *s, SQLINTEGER type, 
        SQLSMALLINT *ptr, SQLPOINTER buf );
char * __idata_as_string( SQLCHAR *s, SQLINTEGER type, 
        SQLINTEGER *ptr, SQLPOINTER buf );
char * __col_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __fid_as_string( SQLCHAR *s, SQLINTEGER fid );
char * __con_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __env_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __stmt_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __desc_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __diag_attr_as_string( SQLCHAR *s, SQLINTEGER type );
char * __type_as_string( SQLCHAR *s, SQLSMALLINT type );
DMHDBC __get_connection( EHEAD * head );
DRV_SQLHANDLE __get_driver_handle( EHEAD * head );
int __get_version( EHEAD * head );
int dm_check_connection_attrs( DMHDBC connection, SQLINTEGER attribute, SQLPOINTER value );
int dm_check_statement_attrs( DMHSTMT statement, SQLINTEGER attribute, SQLPOINTER value );
int __check_stmt_from_dbc( DMHDBC connection, int state );
int __check_stmt_from_desc( DMHDESC desc, int state );
int __check_stmt_from_desc_ird( DMHDESC desc, int state );

/* 
 * These are passed to the cursor lib as helper functions
 */

struct driver_helper_funcs
{
    void (*__post_internal_error_ex)( EHEAD *error_header,
            SQLCHAR *sqlstate,
            SQLINTEGER native_error,
            SQLCHAR *message_text,
            int class_origin,
            int subclass_origin );

    void (*__post_internal_error)( EHEAD *error_handle,
        error_id id, char *txt, int connection_mode );
    void (*dm_log_write)( char *function_name, int line, int type, int severity,
        char *message );
};

/*
 * thread protection funcs
 */

#if defined ( HAVE_LIBPTHREAD ) || defined ( HAVE_LIBTHREAD ) || defined ( HAVE_LIBPTH )

void thread_protect( int type, void *handle );
void thread_release( int type, void *handle );

#else

#define thread_protect(a,b)
#define thread_release(a,b)

#endif

void dbc_change_thread_support( DMHDBC connection, int level );

#ifdef WITH_HANDLE_REDIRECT

void *find_parent_handle( DRV_SQLHANDLE hand, int type );

#endif

/*
 * lookup functions
 */

char *__find_lib_name( char *dsn, char *lib_name, char *driver_name );

/*
 * setup the cursor library
 */

SQLRETURN SQL_API CLConnect( DMHDBC connection, struct driver_helper_funcs * );

/*
 * connection string functions
 */

struct con_pair
{
    char            *keyword;
    char            *attribute;
    char            *identifier;
    struct con_pair *next;
};

struct con_struct
{
    int             count;
    struct con_pair *list;
};

void __generate_connection_string( struct con_struct *con_str, char *str, int str_len );
int __parse_connection_string( struct con_struct *con_str,
    char *str, int str_len );
int __parse_connection_string_w( struct con_struct *con_str,
    SQLWCHAR *str, int str_len );
char * __get_attribute_value( struct con_struct * con_str, char * keyword );
void __release_conn( struct con_struct *con_str );
void __get_attr( char ** cp, char ** keyword, char ** value );
struct con_pair * __get_pair( char ** cp );
int __append_pair( struct con_struct *con_str, char *kword, char *value );
void __handle_attr_extensions_cs( DMHDBC connection, struct con_struct *con_str );

/*
 * the following two are part of a effort to get a particular unicode driver working
 */

SQLINTEGER map_ca_odbc3_to_2( SQLINTEGER field_identifier );
SQLINTEGER map_ca_odbc2_to_3( SQLINTEGER field_identifier );

/*
 * check the type passed to SQLBindCol is a valid C_TYPE
 */

int check_target_type( int c_type );

/*
 * entry exit functions in drivers
 */

#define ODBC_INI_FUNCTION           "SQLDriverLoad"
#define ODBC_FINI_FUNCTION          "SQLDriverUnload"

/*
 * driver manager logging functions
 */

void dm_log_open( char *program_name, char *log_file, int pid_logging );

void dm_log_write( char *function_name, int line, int type, int severity, char *message );
void dm_log_write_diag( char *message );

void dm_log_close( void );

/*
 * connection pooling functions
 */

int search_for_pool( DMHDBC connection,
           SQLCHAR *server_name,
           SQLSMALLINT name_length1,
           SQLCHAR *user_name,
           SQLSMALLINT name_length2,
           SQLCHAR *authentication,
           SQLSMALLINT name_length3,
           SQLCHAR *connect_string,
           SQLSMALLINT connect_string_length );

void return_to_pool( DMHDBC connection );

/*
 * Macros to check and call functions in the driver
 */

#define DM_SQLALLOCCONNECT          0
#define CHECK_SQLALLOCCONNECT(con)  (con->functions[0].func!=NULL)
#define SQLALLOCCONNECT(con,env,oh)\
                                    (con->functions[0].func)(env,oh)

#define DM_SQLALLOCENV              1
#define CHECK_SQLALLOCENV(con)      (con->functions[1].func!=NULL)
#define SQLALLOCENV(con,oh)\
                                    (con->functions[1].func)(oh)

#define DM_SQLALLOCHANDLE           2
#define CHECK_SQLALLOCHANDLE(con)   (con->functions[2].func!=NULL)
    /*
     * if the function is in the cursor lib, pass a additional
     * arg that allows the cursor lib to get the dm handle
     */
#define SQLALLOCHANDLE(con,ht,ih,oh,dmh)\
            (con->cl_handle?\
                    (con->functions[2].func)(ht,ih,oh,dmh):\
                    (con->functions[2].func)(ht,ih,oh))

#define DM_SQLALLOCSTMT             3
#define CHECK_SQLALLOCSTMT(con)     (con->functions[3].func!=NULL)
#define SQLALLOCSTMT(con,dbc,oh,dmh)\
            (con->cl_handle?\
                    (con->functions[3].func)(dbc,oh,dmh):\
                    (con->functions[3].func)(dbc,oh))

#define DM_SQLALLOCHANDLESTD        4

#define DM_SQLBINDCOL               5
#define CHECK_SQLBINDCOL(con)       (con->functions[5].func!=NULL)
#define SQLBINDCOL(con,stmt,cn,tt,tvp,bl,sli)\
                                    (con->functions[5].func)\
                                        (stmt,cn,tt,tvp,bl,sli)

#define DM_SQLBINDPARAM             6
#define CHECK_SQLBINDPARAM(con)     (con->functions[6].func!=NULL)
#define SQLBINDPARAM(con,stmt,pn,vt,pt,cs,dd,pvp,ind)\
                                    (con->functions[6].func)\
                                        (stmt,pn,vt,pt,cs,dd,pvp,ind)

#define DM_SQLBINDPARAMETER         7
#define CHECK_SQLBINDPARAMETER(con) (con->functions[7].func!=NULL)
#define SQLBINDPARAMETER(con,stmt,pn,typ,vt,pt,cs,dd,pvp,bl,ind)\
                                    (con->functions[7].func)\
                                        (stmt,pn,typ,vt,pt,cs,dd,pvp,bl,ind)

#define DM_SQLBROWSECONNECT         8
#define CHECK_SQLBROWSECONNECT(con) (con->functions[8].func!=NULL)
#define SQLBROWSECONNECT(con,dbc,ics,sl1,ocs,bl,sl2)\
                                    (con->functions[8].func)\
                                    (dbc,ics,sl1,ocs,bl,sl2)
#define CHECK_SQLBROWSECONNECTW(con) (con->functions[8].funcW!=NULL)
#define SQLBROWSECONNECTW(con,dbc,ics,sl1,ocs,bl,sl2)\
                                    (con->functions[8].funcW)\
                                    (dbc,ics,sl1,ocs,bl,sl2)
    
#define DM_SQLBULKOPERATIONS        9
#define CHECK_SQLBULKOPERATIONS(con)    (con->functions[9].func!=NULL)
#define SQLBULKOPERATIONS(con,stmt,op)\
                                    (con->functions[9].func)(stmt,op)

#define DM_SQLCANCEL                10
#define CHECK_SQLCANCEL(con)        (con->functions[10].func!=NULL)
#define SQLCANCEL(con,stmt)\
                                    (con->functions[10].func)(stmt)

#define DM_SQLCLOSECURSOR           11
#define CHECK_SQLCLOSECURSOR(con)   (con->functions[11].func!=NULL)
#define SQLCLOSECURSOR(con,stmt)\
                                    (con->functions[11].func)(stmt)

#define DM_SQLCOLATTRIBUTE          12
#define CHECK_SQLCOLATTRIBUTE(con)  (con->functions[12].func!=NULL)
#define SQLCOLATTRIBUTE(con,stmt,cn,fi,cap,bl,slp,nap)\
                                    (con->functions[12].func)\
                                        (stmt,cn,fi,cap,bl,slp,nap)
#define CHECK_SQLCOLATTRIBUTEW(con)  (con->functions[12].funcW!=NULL)
#define SQLCOLATTRIBUTEW(con,stmt,cn,fi,cap,bl,slp,nap)\
                                    (con->functions[12].funcW)\
                                        (stmt,cn,fi,cap,bl,slp,nap)

#define DM_SQLCOLATTRIBUTES         13
#define CHECK_SQLCOLATTRIBUTES(con) (con->functions[13].func!=NULL)
#define SQLCOLATTRIBUTES(con,stmt,cn,fi,cap,bl,slp,nap)\
                                    (con->functions[13].func)\
                                        (stmt,cn,fi,cap,bl,slp,nap)
#define CHECK_SQLCOLATTRIBUTESW(con) (con->functions[13].funcW!=NULL)
#define SQLCOLATTRIBUTESW(con,stmt,cn,fi,cap,bl,slp,nap)\
                                    (con->functions[13].funcW)\
                                        (stmt,cn,fi,cap,bl,slp,nap)

#define DM_SQLCOLUMNPRIVILEGES      14 
#define CHECK_SQLCOLUMNPRIVILEGES(con)  (con->functions[14].func!=NULL)
#define SQLCOLUMNPRIVILEGES(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[14].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)
#define CHECK_SQLCOLUMNPRIVILEGESW(con)  (con->functions[14].funcW!=NULL)
#define SQLCOLUMNPRIVILEGESW(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[14].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)

#define DM_SQLCOLUMNS               15
#define CHECK_SQLCOLUMNS(con)       (con->functions[15].func!=NULL)
#define SQLCOLUMNS(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[15].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)
#define CHECK_SQLCOLUMNSW(con)       (con->functions[15].funcW!=NULL)
#define SQLCOLUMNSW(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[15].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)

#define DM_SQLCONNECT               16
#define CHECK_SQLCONNECT(con)       (con->functions[16].func!=NULL)
#define SQLCONNECT(con,dbc,dsn,l1,uid,l2,at,l3)\
                                    (con->functions[16].func)\
                                    (dbc,dsn,l1,uid,l2,at,l3)
#define CHECK_SQLCONNECTW(con)       (con->functions[16].funcW!=NULL)
#define SQLCONNECTW(con,dbc,dsn,l1,uid,l2,at,l3)\
                                    (con->functions[16].funcW)\
                                    (dbc,dsn,l1,uid,l2,at,l3)

#define DM_SQLCOPYDESC              17
#define CHECK_SQLCOPYDESC(con)      (con->functions[17].func!=NULL)
#define SQLCOPYDESC(con,sd,td)\
                                    (con->functions[17].func)(sd,td)

#define DM_SQLDATASOURCES           18

#define DM_SQLDESCRIBECOL           19
#define CHECK_SQLDESCRIBECOL(con)   (con->functions[19].func!=NULL)
#define SQLDESCRIBECOL(con,stmt,cnum,cn,bli,nl,dt,cs,dd,n)\
                                    (con->functions[19].func)\
                                        (stmt,cnum,cn,bli,nl,dt,cs,dd,n)
#define CHECK_SQLDESCRIBECOLW(con)   (con->functions[19].funcW!=NULL)
#define SQLDESCRIBECOLW(con,stmt,cnum,cn,bli,nl,dt,cs,dd,n)\
                                    (con->functions[19].funcW)\
                                        (stmt,cnum,cn,bli,nl,dt,cs,dd,n)

#define DM_SQLDESCRIBEPARAM         20
#define CHECK_SQLDESCRIBEPARAM(con) (con->functions[20].func!=NULL)
#define SQLDESCRIBEPARAM(con,stmt,pn,dtp,psp,ddp,np)\
                                    (con->functions[20].func)\
                                        (stmt,pn,dtp,psp,ddp,np)

#define DM_SQLDISCONNECT            21
#define CHECK_SQLDISCONNECT(con)    (con->functions[21].func!=NULL)
#define SQLDISCONNECT(con,dbc)\
                                    (con->functions[21].func)(dbc)

#define DM_SQLDRIVERCONNECT         22
#define CHECK_SQLDRIVERCONNECT(con) (con->functions[22].func!=NULL)
#define SQLDRIVERCONNECT(con,dbc,wh,ics,sl1,ocs,bl,sl2p,dc)\
                                    (con->functions[22].func)\
                                        (dbc,wh,ics,sl1,ocs,bl,sl2p,dc)

#define CHECK_SQLDRIVERCONNECTW(con) (con->functions[22].funcW!=NULL)
#define SQLDRIVERCONNECTW(con,dbc,wh,ics,sl1,ocs,bl,sl2p,dc)\
                                     (con->functions[22].funcW)\
                                        (dbc,wh,ics,sl1,ocs,bl,sl2p,dc)

#define DM_SQLDRIVERS               23

#define DM_SQLENDTRAN               24
#define CHECK_SQLENDTRAN(con)       (con->functions[24].func!=NULL)
#define SQLENDTRAN(con,ht,h,op)\
                                    (con->functions[24].func)(ht,h,op)

#define DM_SQLERROR                 25
#define CHECK_SQLERROR(con)         (con->functions[25].func!=NULL)
#define SQLERROR(con,env,dbc,stmt,st,nat,msg,mm,pcb)\
                                    (con->functions[25].func)\
                                        (env,dbc,stmt,st,nat,msg,mm,pcb)
#define CHECK_SQLERRORW(con)         (con->functions[25].funcW!=NULL)
#define SQLERRORW(con,env,dbc,stmt,st,nat,msg,mm,pcb)\
                                     (con->functions[25].funcW)\
                                        (env,dbc,stmt,st,nat,msg,mm,pcb)

#define DM_SQLEXECDIRECT            26
#define CHECK_SQLEXECDIRECT(con)    (con->functions[26].func!=NULL)
#define SQLEXECDIRECT(con,stmt,sql,len)\
                                    (con->functions[26].func)(stmt,sql,len)
#define CHECK_SQLEXECDIRECTW(con)    (con->functions[26].funcW!=NULL)
#define SQLEXECDIRECTW(con,stmt,sql,len)\
                                    (con->functions[26].funcW)(stmt,sql,len)

#define DM_SQLEXECUTE               27
#define CHECK_SQLEXECUTE(con)       (con->functions[27].func!=NULL)
#define SQLEXECUTE(con,stmt)\
                                    (con->functions[27].func)(stmt)

#define DM_SQLEXTENDEDFETCH         28
#define CHECK_SQLEXTENDEDFETCH(con) (con->functions[28].func!=NULL)
#define SQLEXTENDEDFETCH(con,stmt,fo,of,rcp,ssa)\
                                    (con->functions[28].func)\
                                        (stmt,fo,of,rcp,ssa)

#define DM_FETCH                    29
#define CHECK_SQLFETCH(con)         (con->functions[29].func!=NULL)
#define SQLFETCH(con,stmt)\
                                    (con->functions[29].func)(stmt)

#define DM_SQLFETCHSCROLL           30
#define CHECK_SQLFETCHSCROLL(con)   (con->functions[30].func!=NULL)
#define SQLFETCHSCROLL(con,stmt,or,of)\
                                    (con->functions[30].func)\
                                        (stmt,or,of)

#define DM_SQLFOREIGNKEYS           31
#define CHECK_SQLFOREIGNKEYS(con)   (con->functions[31].func!=NULL)
#define SQLFOREIGNKEYS(con,stmt,cn,nl1,sn,nl2,tn,nl3,fcn,nl4,fsn,nl5,ftn,nl6)\
                                    (con->functions[31].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,fcn,nl4,fsn,nl5,ftn,nl6)
#define CHECK_SQLFOREIGNKEYSW(con)   (con->functions[31].funcW!=NULL)
#define SQLFOREIGNKEYSW(con,stmt,cn,nl1,sn,nl2,tn,nl3,fcn,nl4,fsn,nl5,ftn,nl6)\
                                    (con->functions[31].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,fcn,nl4,fsn,nl5,ftn,nl6)

#define DM_SQLFREEENV               32
#define CHECK_SQLFREEENV(con)       (con->functions[32].func!=NULL)
#define SQLFREEENV(con,env)\
                                    (con->functions[32].func)(env)

#define DM_SQLFREEHANDLE            33
#define CHECK_SQLFREEHANDLE(con)    (con->functions[33].func!=NULL)
#define SQLFREEHANDLE(con,typ,env)\
                                    (con->functions[33].func)(typ,env)

#define DM_SQLFREESTMT              34
#define CHECK_SQLFREESTMT(con)      (con->functions[34].func!=NULL)
#define SQLFREESTMT(con,stmt,opt)\
                                    (con->functions[34].func)(stmt,opt)

#define DM_SQLFREECONNECT           35
#define CHECK_SQLFREECONNECT(con)   (con->functions[35].func!=NULL)
#define SQLFREECONNECT(con,dbc)\
                                    (con->functions[35].func)(dbc)

#define DM_SQLGETCONNECTATTR        36
#define CHECK_SQLGETCONNECTATTR(con)    (con->functions[36].func!=NULL)
#define SQLGETCONNECTATTR(con,dbc,at,vp,bl,slp)\
                                    (con->functions[36].func)\
                                        (dbc,at,vp,bl,slp)
#define CHECK_SQLGETCONNECTATTRW(con)    (con->functions[36].funcW!=NULL)
#define SQLGETCONNECTATTRW(con,dbc,at,vp,bl,slp)\
                                    (con->functions[36].funcW)\
                                        (dbc,at,vp,bl,slp)

#define DM_SQLGETCONNECTOPTION      37
#define CHECK_SQLGETCONNECTOPTION(con)  (con->functions[37].func!=NULL)
#define SQLGETCONNECTOPTION(con,dbc,at,val)\
                                    (con->functions[37].func)\
                                        (dbc,at,val)
#define CHECK_SQLGETCONNECTOPTIONW(con)  (con->functions[37].funcW!=NULL)
#define SQLGETCONNECTOPTIONW(con,dbc,at,val)\
                                    (con->functions[37].funcW)\
                                        (dbc,at,val)

#define DM_SQLGETCURSORNAME         38
#define CHECK_SQLGETCURSORNAME(con) (con->functions[38].func!=NULL)
#define SQLGETCURSORNAME(con,stmt,cn,bl,nlp)\
                                    (con->functions[38].func)\
                                        (stmt,cn,bl,nlp)
#define CHECK_SQLGETCURSORNAMEW(con) (con->functions[38].funcW!=NULL)
#define SQLGETCURSORNAMEW(con,stmt,cn,bl,nlp)\
                                    (con->functions[38].funcW)\
                                        (stmt,cn,bl,nlp)

#define DM_SQLGETDATA               39
#define CHECK_SQLGETDATA(con)       (con->functions[39].func!=NULL)
#define SQLGETDATA(con,stmt,cn,tt,tvp,bl,sli)\
                                    (con->functions[39].func)\
                                        (stmt,cn,tt,tvp,bl,sli)

#define DM_SQLGETDESCFIELD          40
#define CHECK_SQLGETDESCFIELD(con)  (con->functions[40].func!=NULL)
#define SQLGETDESCFIELD(con,des,rn,fi,vp,bl,slp)\
                                    (con->functions[40].func)\
                                        (des,rn,fi,vp,bl,slp)
#define CHECK_SQLGETDESCFIELDW(con)  (con->functions[40].funcW!=NULL)
#define SQLGETDESCFIELDW(con,des,rn,fi,vp,bl,slp)\
                                    (con->functions[40].funcW)\
                                        (des,rn,fi,vp,bl,slp)

#define DM_SQLGETDESCREC            41
#define CHECK_SQLGETDESCREC(con)    (con->functions[41].func!=NULL)
#define SQLGETDESCREC(con,des,rn,n,bl,slp,tp,stp,lp,pp,sp,np)\
                                    (con->functions[41].func)\
                                        (des,rn,n,bl,slp,tp,stp,lp,pp,sp,np)
#define CHECK_SQLGETDESCRECW(con)    (con->functions[41].funcW!=NULL)
#define SQLGETDESCRECW(con,des,rn,n,bl,slp,tp,stp,lp,pp,sp,np)\
                                    (con->functions[41].funcW)\
                                        (des,rn,n,bl,slp,tp,stp,lp,pp,sp,np)

#define DM_SQLGETDIAGFIELD          42
#define CHECK_SQLGETDIAGFIELD(con)  (con->functions[42].func!=NULL)
#define SQLGETDIAGFIELD(con,typ,han,rn,di,dip,bl,slp)\
                                    (con->functions[42].func)\
                                        (typ,han,rn,di,dip,bl,slp)
#define CHECK_SQLGETDIAGFIELDW(con)  (con->functions[42].funcW!=NULL)
#define SQLGETDIAGFIELDW(con,typ,han,rn,di,dip,bl,slp)\
                                    (con->functions[42].funcW)\
                                        (typ,han,rn,di,dip,bl,slp)

#define DM_SQLGETENVATTR            43
#define CHECK_SQLGETENVATTR(con)    (con->functions[43].func!=NULL)
#define SQLGETENVATTR(con,env,attr,val,len,ol)\
                                    (con->functions[43].func)\
                                    (env,attr,val,len,ol)

#define DM_SQLGETFUNCTIONS          44
#define CHECK_SQLGETFUNCTIONS(con)  (con->functions[44].func!=NULL)
#define SQLGETFUNCTIONS(con,dbc,id,ptr)\
                                    (con->functions[44].func)\
                                        (dbc,id,ptr)

#define DM_SQLGETINFO               45
#define CHECK_SQLGETINFO(con)       (con->functions[45].func!=NULL)
#define SQLGETINFO(con,dbc,it,ivo,bl,slp)\
                                    (con->functions[45].func)\
                                        (dbc,it,ivo,bl,slp)
#define CHECK_SQLGETINFOW(con)       (con->functions[45].funcW!=NULL)
#define SQLGETINFOW(con,dbc,it,ivo,bl,slp)\
                                    (con->functions[45].funcW)\
                                        (dbc,it,ivo,bl,slp)

#define DM_SQLGETSTMTATTR           46
#define CHECK_SQLGETSTMTATTR(con)   (con->functions[46].func!=NULL)
#define SQLGETSTMTATTR(con,stmt,at,vp,bl,slp)\
                                    (con->functions[46].func)\
                                        (stmt,at,vp,bl,slp)
#define CHECK_SQLGETSTMTATTRW(con)   (con->functions[46].funcW!=NULL)
#define SQLGETSTMTATTRW(con,stmt,at,vp,bl,slp)\
                                    (con->functions[46].funcW)\
                                        (stmt,at,vp,bl,slp)
#define DM_SQLGETSTMTOPTION         47
#define CHECK_SQLGETSTMTOPTION(con) (con->functions[47].func!=NULL)
#define SQLGETSTMTOPTION(con,stmt,op,val)\
                                    (con->functions[47].func)\
                                        (stmt,op,val)
#define CHECK_SQLGETSTMTOPTIONW(con) (con->functions[47].funcW!=NULL)
#define SQLGETSTMTOPTIONW(con,stmt,op,val)\
                                    (con->functions[47].funcW)\
                                        (stmt,op,val)

#define DM_SQLGETTYPEINFO           48
#define CHECK_SQLGETTYPEINFO(con)   (con->functions[48].func!=NULL)
#define SQLGETTYPEINFO(con,stmt,typ)\
                                    (con->functions[48].func)(stmt,typ)
#define CHECK_SQLGETTYPEINFOW(con)   (con->functions[48].funcW!=NULL)
#define SQLGETTYPEINFOW(con,stmt,typ)\
                                    (con->functions[48].funcW)(stmt,typ)

#define DM_SQLMORERESULTS           49
#define CHECK_SQLMORERESULTS(con)   (con->functions[49].func!=NULL)
#define SQLMORERESULTS(con,stmt)\
                                    (con->functions[49].func)(stmt)

#define DM_SQLNATIVESQL             50
#define CHECK_SQLNATIVESQL(con)     (con->functions[50].func!=NULL)
#define SQLNATIVESQL(con,dbc,ist,tl,ost,bl,tlp)\
                                    (con->functions[50].func)\
                                        (dbc,ist,tl,ost,bl,tlp)
#define CHECK_SQLNATIVESQLW(con)     (con->functions[50].funcW!=NULL)
#define SQLNATIVESQLW(con,dbc,ist,tl,ost,bl,tlp)\
                                    (con->functions[50].funcW)\
                                        (dbc,ist,tl,ost,bl,tlp)

#define DM_SQLNUMPARAMS             51
#define CHECK_SQLNUMPARAMS(con)     (con->functions[51].func!=NULL)
#define SQLNUMPARAMS(con,stmt,cnt)\
                                    (con->functions[51].func)(stmt,cnt)

#define DM_SQLNUMRESULTCOLS         52
#define CHECK_SQLNUMRESULTCOLS(con) (con->functions[52].func!=NULL)
#define SQLNUMRESULTCOLS(con,stmt,cnt)\
                                    (con->functions[52].func)(stmt,cnt)

#define DM_SQLPARAMDATA             53
#define CHECK_SQLPARAMDATA(con)     (con->functions[53].func!=NULL)
#define SQLPARAMDATA(con,stmt,val)\
                                    (con->functions[53].func)(stmt,val)

#define DM_SQLPARAMOPTIONS          54
#define CHECK_SQLPARAMOPTIONS(con)  (con->functions[54].func!=NULL)
#define SQLPARAMOPTIONS(con,stmt,cr,pi)\
                                    (con->functions[54].func)(stmt,cr,pi)

#define DM_SQLPREPARE               55
#define CHECK_SQLPREPARE(con)       (con->functions[55].func!=NULL)
#define SQLPREPARE(con,stmt,sql,len)\
                                    (con->functions[55].func)(stmt,sql,len)
#define CHECK_SQLPREPAREW(con)       (con->functions[55].funcW!=NULL)
#define SQLPREPAREW(con,stmt,sql,len)\
                                    (con->functions[55].funcW)(stmt,sql,len)

#define DM_SQLPRIMARYKEYS           56
#define CHECK_SQLPRIMARYKEYS(con)   (con->functions[56].func!=NULL)
#define SQLPRIMARYKEYS(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[56].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)
#define CHECK_SQLPRIMARYKEYSW(con)   (con->functions[56].funcW!=NULL)
#define SQLPRIMARYKEYSW(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[56].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)

#define DM_SQLPROCEDURECOLUMNS      57
#define CHECK_SQLPROCEDURECOLUMNS(con)  (con->functions[57].func!=NULL)
#define SQLPROCEDURECOLUMNS(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[57].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)
#define CHECK_SQLPROCEDURECOLUMNSW(con)  (con->functions[57].funcW!=NULL)
#define SQLPROCEDURECOLUMNSW(con,stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)\
                                    (con->functions[57].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,col,nl4)

#define DM_SQLPROCEDURES            58
#define CHECK_SQLPROCEDURES(con)    (con->functions[58].func!=NULL)
#define SQLPROCEDURES(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[58].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)
#define CHECK_SQLPROCEDURESW(con)    (con->functions[58].funcW!=NULL)
#define SQLPROCEDURESW(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[58].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)

#define DM_SQLPUTDATA               59
#define CHECK_SQLPUTDATA(con)       (con->functions[59].func!=NULL)
#define SQLPUTDATA(con,stmt,d,p)\
                                    (con->functions[59].func)(stmt,d,p)

#define DM_SQLROWCOUNT              60
#define CHECK_SQLROWCOUNT(con)      (con->functions[60].func!=NULL)
#define DEF_SQLROWCOUNT(con,stmt,cnt)\
                                    (con->functions[60].func)(stmt,cnt)

#define DM_SQLSETCONNECTATTR        61
#define CHECK_SQLSETCONNECTATTR(con)    (con->functions[61].func!=NULL)
#define SQLSETCONNECTATTR(con,dbc,at,vp,sl)\
                                    (con->functions[61].func)\
                                        (dbc,at,vp,sl)
#define CHECK_SQLSETCONNECTATTRW(con)    (con->functions[61].funcW!=NULL)
#define SQLSETCONNECTATTRW(con,dbc,at,vp,sl)\
                                    (con->functions[61].funcW)\
                                        (dbc,at,vp,sl)

#define DM_SQLSETCONNECTOPTION      62
#define CHECK_SQLSETCONNECTOPTION(con)  (con->functions[62].func!=NULL)
#define SQLSETCONNECTOPTION(con,dbc,op,p)\
                                    (con->functions[62].func)\
                                        (dbc,op,p)
#define CHECK_SQLSETCONNECTOPTIONW(con)  (con->functions[62].funcW!=NULL)
#define SQLSETCONNECTOPTIONW(con,dbc,op,p)\
                                    (con->functions[62].funcW)\
                                        (dbc,op,p)

#define DM_SQLSETCURSORNAME         63
#define CHECK_SQLSETCURSORNAME(con) (con->functions[63].func!=NULL)
#define SQLSETCURSORNAME(con,stmt,nam,len)\
                                    (con->functions[63].func)(stmt,nam,len)
#define CHECK_SQLSETCURSORNAMEW(con) (con->functions[63].funcW!=NULL)
#define SQLSETCURSORNAMEW(con,stmt,nam,len)\
                                    (con->functions[63].funcW)(stmt,nam,len)

#define DM_SQLSETDESCFIELD          64
#define CHECK_SQLSETDESCFIELD(con)  (con->functions[64].func!=NULL)
#define SQLSETDESCFIELD(con,des,rn,fi,vp,bl)\
                                    (con->functions[64].func)\
                                    (des,rn,fi,vp,bl)
#define CHECK_SQLSETDESCFIELDW(con)  (con->functions[64].funcW!=NULL)
#define SQLSETDESCFIELDW(con,des,rn,fi,vp,bl)\
                                    (con->functions[64].funcW)\
                                    (des,rn,fi,vp,bl)

#define DM_SQLSETDESCREC            65
#define CHECK_SQLSETDESCREC(con)    (con->functions[65].func!=NULL)
#define SQLSETDESCREC(con,des,rn,t,st,l,p,sc,dp,slp,ip)\
                                    (con->functions[65].func)\
                                        (des,rn,t,st,l,p,sc,dp,slp,ip)

#define DM_SQLSETENVATTR            66
#define CHECK_SQLSETENVATTR(con)    (con->functions[66].func!=NULL)
#define SQLSETENVATTR(con,env,attr,val,len)\
                                    (con->functions[66].func)(env,attr,val,len)

#define DM_SQLSETPARAM              67
#define CHECK_SQLSETPARAM(con)      (con->functions[67].func!=NULL)
#define SQLSETPARAM(con,stmt,pn,vt,pt,lp,ps,pv,sli)\
                                    (con->functions[67].func)\
                                        (stmt,pn,vt,pt,lp,ps,pv,sli)

#define DM_SQLSETPOS                68
#define CHECK_SQLSETPOS(con)        (con->functions[68].func!=NULL)
#define SQLSETPOS(con,stmt,rn,op,lt)\
                                    (con->functions[68].func)\
                                        (stmt,rn,op,lt)

#define DM_SQLSETSCROLLOPTIONS      69
#define CHECK_SQLSETSCROLLOPTIONS(con)  (con->functions[69].func!=NULL)
#define SQLSETSCROLLOPTIONS(con,stmt,fc,cr,rs)\
                                    (con->functions[69].func)\
                                        (stmt,fc,cr,rs)
#define DM_SQLSETSTMTATTR           70
#define CHECK_SQLSETSTMTATTR(con)   (con->functions[70].func!=NULL)
#define SQLSETSTMTATTR(con,stmt,attr,vp,sl)\
                                    (con->functions[70].func)\
                                        (stmt,attr,vp,sl)
#define CHECK_SQLSETSTMTATTRW(con)   (con->functions[70].funcW!=NULL)
#define SQLSETSTMTATTRW(con,stmt,attr,vp,sl)\
                                    (con->functions[70].funcW)\
                                        (stmt,attr,vp,sl)

#define DM_SQLSETSTMTOPTION         71
#define CHECK_SQLSETSTMTOPTION(con) (con->functions[71].func!=NULL)
#define SQLSETSTMTOPTION(con,stmt,op,val)\
                                    (con->functions[71].func)\
                                        (stmt,op,val)

#define CHECK_SQLSETSTMTOPTIONW(con)   (con->functions[71].funcW!=NULL)
#define SQLSETSTMTOPTIONW(con,stmt,op,val)\
                                    (con->functions[71].funcW)\
                                        (stmt,op,val)

#define DM_SQLSPECIALCOLUMNS        72
#define CHECK_SQLSPECIALCOLUMNS(con)    (con->functions[72].func!=NULL)
#define SQLSPECIALCOLUMNS(con,stmt,it,cn,nl1,sn,nl2,tn,nl3,s,n)\
                                    (con->functions[72].func)\
                                        (stmt,it,cn,nl1,sn,nl2,tn,nl3,s,n)
#define CHECK_SQLSPECIALCOLUMNSW(con)    (con->functions[72].funcW!=NULL)
#define SQLSPECIALCOLUMNSW(con,stmt,it,cn,nl1,sn,nl2,tn,nl3,s,n)\
                                    (con->functions[72].funcW)\
                                        (stmt,it,cn,nl1,sn,nl2,tn,nl3,s,n)

#define DM_SQLSTATISTICS            73
#define CHECK_SQLSTATISTICS(con)    (con->functions[73].func!=NULL)
#define SQLSTATISTICS(con,stmt,cn,nl1,sn,nl2,tn,nl3,un,res)\
                                    (con->functions[73].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,un,res)
#define CHECK_SQLSTATISTICSW(con)    (con->functions[73].funcW!=NULL)
#define SQLSTATISTICSW(con,stmt,cn,nl1,sn,nl2,tn,nl3,un,res)\
                                    (con->functions[73].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,un,res)

#define DM_SQLTABLEPRIVILEGES       74
#define CHECK_SQLTABLEPRIVILEGES(con)   (con->functions[74].func!=NULL)
#define SQLTABLEPRIVILEGES(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[74].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)
#define CHECK_SQLTABLEPRIVILEGESW(con)   (con->functions[74].funcW!=NULL)
#define SQLTABLEPRIVILEGESW(con,stmt,cn,nl1,sn,nl2,tn,nl3)\
                                    (con->functions[74].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3)

#define DM_SQLTABLES                75
#define CHECK_SQLTABLES(con)        (con->functions[75].func!=NULL)
#define SQLTABLES(con,stmt,cn,nl1,sn,nl2,tn,nl3,tt,nl4)\
                                    (con->functions[75].func)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,tt,nl4)
#define CHECK_SQLTABLESW(con)        (con->functions[75].funcW!=NULL)
#define SQLTABLESW(con,stmt,cn,nl1,sn,nl2,tn,nl3,tt,nl4)\
                                    (con->functions[75].funcW)\
                                        (stmt,cn,nl1,sn,nl2,tn,nl3,tt,nl4)

#define DM_SQLTRANSACT              76
#define CHECK_SQLTRANSACT(con)      (con->functions[76].func!=NULL)
#define SQLTRANSACT(con,eh,ch,op)\
                                    (con->functions[76].func)(eh,ch,op)


#define DM_SQLGETDIAGREC            77
#define CHECK_SQLGETDIAGREC(con)    (con->functions[77].func!=NULL)
#define SQLGETDIAGREC(con,typ,han,rn,st,nat,msg,bl,tlp)\
                                    (con->functions[77].func)\
                                        (typ,han,rn,st,nat,msg,bl,tlp)
#define CHECK_SQLGETDIAGRECW(con)    (con->functions[77].funcW!=NULL)
#define SQLGETDIAGRECW(con,typ,han,rn,st,nat,msg,bl,tlp)\
                                    (con->functions[77].funcW)\
                                        (typ,han,rn,st,nat,msg,bl,tlp)

#define DM_SQLCANCELHANDLE          78
#define CHECK_SQLCANCELHANDLE(con)  (con->functions[78].func!=NULL)
#define SQLCANCELHANDLE(con,typ,han)\
                                    (con->functions[78].func)\
                                        (typ,han)

#endif