root/trunk/sdbo/odbc_etc.d

Revision 14, 17.6 kB (checked in by toaster, 8 years ago)

linux version compiled and running, other changes

Line 
1 /********************************************************
2  *                                                      *
3  * Copyright (c) 2004 Wolfgang Borgsmüller (wb@sapo.pt) *
4  *                                                      *
5  * Usage of the works is permitted provided that this   *
6  * instrument is retained with the works, so that any   *
7  * entity that uses the works is notified of this       *
8  * instrument.                                          *
9  *                                                      *
10  * DISCLAIMER: THE WORKS ARE WITHOUT WARRANTY.          *
11  *                                                      *
12  * [2004, Fair License: rhid.com/fair]                  *
13  ********************************************************/
14
15 /*! \if never
16 */
17
18 module sdbo.odbc_etc;
19
20 private import std.string;
21 private import std.stdio;
22
23 version(linux) {
24     version = bundled_headers;
25 }
26
27 version(bundled_headers) {
28     private import sdbo._odbc_headers.sql;
29     private import sdbo._odbc_headers.sqlext;
30     private import sdbo._odbc_headers.sqltypes;
31     version(Windows) {
32         private import sdbo._odbc_headers.odbc32dll;
33     }
34    
35 } else {
36     private import std.c.windows.sql;
37     private import std.c.windows.sqlext;
38     private import std.c.windows.sqltypes;
39     private import std.c.windows.odbc32dll;
40 }
41
42
43
44 /*! \endif
45 */
46
47
48 /*! \brief Odbc Message with sql states, native errors, text messages
49  *
50  * Records returned from a diagnistic call
51  *
52  */
53
54 public class OdbcMessage {
55    
56     char[5][] sqlStates;
57     int[] nativeErrors;
58     char[][] messages;
59    
60    
61     /*! \brief Returns the number of diag records.
62     */
63     public int recCount()
64     {
65         return sqlStates.length;
66     }
67
68     /*! \brief Returns the sql state for a diag record.
69     */
70     public char[] sqlState(int diagrec = 0)
71     {
72         assert(diagrec < sqlStates.length);
73        
74         char[] state;
75         state.length = 5;
76         state[0..5] = sqlStates[diagrec][0..5];
77         return state;
78     }
79    
80     /*! \brief Returns the native error for a diag record.
81     */
82     public int nativeError(int diagrec = 0)
83     {
84         assert(diagrec < nativeErrors.length);
85         return nativeErrors[diagrec];
86     }
87    
88     /*! \brief Returns the message for a diag record.
89     */
90     public char[] message(int diagrec = 0)
91     {
92         assert(diagrec < messages.length);
93         return messages[diagrec];
94     }
95    
96
97    
98     /*! \brief Returns all informations in a string.
99     */
100     public char[] toString()
101     {
102         char[] msgs;
103         for(int i=0; i < messages.length; i++) {
104             msgs ~= sqlState(i) ~ " " ~ .toString(nativeErrors[i]) ~ " " ~ messages[i] ~ "\n";
105         }
106        
107         return msgs;
108     }
109
110     /*! \brief Resets the message discarting all records.
111     */
112     public void reset()
113     {
114         messages.length = 0;
115         nativeErrors.length = 0;
116         sqlStates.length = 0;
117     }
118    
119
120    
121 }
122
123
124 /*! \brief Single column specification
125  *
126  * A ColumnSpec is returned by the getColumnSpec function of the SqlResult object.
127  *
128  * The struct members describe name, type, size,
129  * digits, if it is nullable, and the numeric sql data type.
130  *
131  *
132  */
133
134 public struct ColumnSpec
135 {
136     /*! \brief Name of the column.
137     */
138     public char[] name;
139     /*! \brief Type of the column.
140     */
141     public char[] type;
142     /*! \brief Size of the column.
143     */
144     public ushort csize;
145     /*! \brief Digits of the column.
146     */
147     public short digits;
148     /*! \brief Nullable
149     */
150     public short nullable;
151     /*! \brief Numeric sql type of the column.
152     */
153     public short numericType;
154     /*! \brief Octet length of the column.
155     */
156     public uint octetLength;
157 }
158
159
160
161 /*! \brief Exception thrown if an odbc call returns with error.
162  *
163  * Each SqlException carries the odbc diagnistics messages.
164  *
165  * toString() and print() return/print the name of the failed odbc call
166  * and available diagnistics messages.
167  *
168  *
169  */
170
171 public class SqlException : Exception
172 {
173    
174     public static RETCODE checkRetcode(RETCODE rc, char[] msg, void* h, int hType, OdbcMessage diag = null)
175     {
176        
177         if(rc == SQL_SUCCESS)
178             return rc;
179        
180         else if(rc == SQL_SUCCESS_WITH_INFO) {
181            
182             /* get info */
183            
184             if(diag)
185                 getMessage(diag, h, hType);
186            
187             return rc;
188            
189         } else if(rc == SQL_ERROR) {
190            
191             throw new SqlException(msg, h, hType);
192         }
193        
194         return rc;
195
196     }
197    
198
199     private static void getMessage(OdbcMessage odbcmessage, void* h, int hType)
200     {
201         short retLen = 0;
202         int record = 1;
203        
204         odbcmessage.messages.length = 1;
205         odbcmessage.nativeErrors.length=1;
206         odbcmessage.sqlStates.length = 1;
207        
208         odbcmessage.messages[0].length = 2048;
209        
210         char[1024] buf;
211        
212         while(SQLGetDiagRec (
213                 hType,
214                 h,
215                 record,
216                 odbcmessage.sqlStates[record-1],
217                 &(odbcmessage.nativeErrors[record-1]),
218                 cast(SQLCHAR*) buf,
219                 buf.length,
220                 &retLen
221                 ) == SQL_SUCCESS)
222         {
223            
224             odbcmessage.messages[record-1].length = retLen;
225             odbcmessage.messages[record-1][0..length] = buf[0..retLen];
226             retLen = 0;
227            
228             record++;
229             odbcmessage.messages.length = record;
230             odbcmessage.nativeErrors.length=record;
231             odbcmessage.sqlStates.length = record;
232
233             odbcmessage.messages[record-1].length = 2048;
234         }
235         odbcmessage.messages.length = odbcmessage.messages.length - 1;
236         odbcmessage.nativeErrors.length=odbcmessage.nativeErrors.length - 1;
237         odbcmessage.sqlStates.length = odbcmessage.sqlStates.length - 1;
238     }
239    
240
241    
242     OdbcMessage odbcmessage;
243    
244     this(char[] msg, void* h, int hType) {
245         super(msg);
246         odbcmessage = new OdbcMessage;
247         getMessage(odbcmessage, h, hType);
248     }
249    
250    
251     /*! \brief Returns the sql state for a diag record.
252     */
253     public char[] sqlState(int diagrec = 0)
254     {
255         return odbcmessage.sqlState(diagrec);
256     }
257    
258     /*! \brief Returns the native error for a diag record.
259     */
260     public int nativeError(int diagrec = 0)
261     {
262         return odbcmessage.nativeError(diagrec);
263     }
264    
265     /*! \brief Returns the message for a diag record.
266     */
267     public char[] message(int diagrec = 0)
268     {
269         return odbcmessage.message(diagrec);
270     }
271    
272     /*! \brief Returns all informations in a string.
273     */
274     public char[] toString()
275     {
276         return msg ~ " failed! Diagnostics records:\n" ~ odbcmessage.toString();
277
278     }
279    
280
281    
282     void print()
283     {
284         fprintf(stderr, toStringz(toString()));
285     }
286    
287 }
288
289
290
291 /*! \if never
292 */
293
294
295 version(Windows) {
296
297 /* odbc */
298
299 package char[]    odbc32dll   = "odbc32.dll";
300 private HINSTANCE hODBC32DLL = null;
301
302 void freeOdbc32dll()
303 {
304     FreeLibrary(hODBC32DLL);
305     throw new Exception("Library free'd!");
306 }
307
308 bit probeOdbc32dll()
309 {
310    
311     if(hODBC32DLL != null)
312         return true;
313    
314     hODBC32DLL = LoadLibraryA( std.string.toStringz( odbc32dll ) );
315    
316     if ( hODBC32DLL <= cast(HINSTANCE)0 )
317     {
318         hODBC32DLL = null;
319
320         return false;
321     }
322    
323     SQLAllocConnect     = cast(pfn_SQLAllocConnect)GetProcAddress(hODBC32DLL, "SQLAllocConnect");
324    
325     SQLAllocEnv         = cast(pfn_SQLAllocEnv)GetProcAddress( hODBC32DLL, "SQLAllocEnv" );
326     SQLAllocHandle      = cast(pfn_SQLAllocHandle)GetProcAddress( hODBC32DLL, "SQLAllocHandle" );
327     SQLAllocStmt        = cast(pfn_SQLAllocStmt)GetProcAddress( hODBC32DLL, "SQLAllocStmt" );
328     SQLBindCol          = cast(pfn_SQLBindCol)GetProcAddress( hODBC32DLL, "SQLBindCol" );
329     SQLBindParam        = cast(pfn_SQLBindParam)GetProcAddress( hODBC32DLL, "SQLBindParam" );
330     SQLBindParameter    = cast(pfn_SQLBindParameter)GetProcAddress( hODBC32DLL, "SQLBindParameter" );
331     SQLBrowseConnect    = cast(pfn_SQLBrowseConnect)GetProcAddress( hODBC32DLL, "SQLBrowseConnect" );
332     SQLBulkOperations   = cast(pfn_SQLBulkOperations)GetProcAddress( hODBC32DLL, "SQLBulkOperations" );
333     SQLCancel           = cast(pfn_SQLCancel)GetProcAddress( hODBC32DLL, "SQLCancel" );   
334     SQLCloseCursor      = cast(pfn_SQLCloseCursor)GetProcAddress( hODBC32DLL, "SQLCloseCursor" );   
335     SQLColAttribute     = cast(pfn_SQLColAttribute)GetProcAddress( hODBC32DLL, "SQLColAttribute" );
336     SQLColAttributes    = cast(pfn_SQLColAttributes)GetProcAddress( hODBC32DLL, "SQLColAttributes" );
337     SQLColumnPrivileges = cast(pfn_SQLColumnPrivileges)GetProcAddress( hODBC32DLL, "SQLColumnPrivileges" );
338     SQLColumns          = cast(pfn_SQLColumns)GetProcAddress( hODBC32DLL, "SQLColumns" );
339     SQLConnect          = cast(pfn_SQLConnect)GetProcAddress( hODBC32DLL, "SQLConnect" );
340     SQLCopyDesc         = cast(pfn_SQLCopyDesc)GetProcAddress( hODBC32DLL, "SQLCopyDesc" );
341     SQLDataSources      = cast(pfn_SQLDataSources)GetProcAddress( hODBC32DLL, "SQLDataSources" );
342     SQLDescribeCol      = cast(pfn_SQLDescribeCol)GetProcAddress( hODBC32DLL, "SQLDescribeCol" );
343     SQLDescribeParam    = cast(pfn_SQLDescribeParam)GetProcAddress( hODBC32DLL, "SQLDescribeParam" );
344     SQLDisconnect       = cast(pfn_SQLDisconnect)GetProcAddress( hODBC32DLL, "SQLDisconnect" );
345     SQLDriverConnect    = cast(pfn_SQLDriverConnect)GetProcAddress( hODBC32DLL, "SQLDriverConnect" );
346     SQLDrivers          = cast(pfn_SQLDrivers)GetProcAddress( hODBC32DLL, "SQLDrivers" );
347     SQLEndTran          = cast(pfn_SQLEndTran)GetProcAddress( hODBC32DLL, "SQLEndTran" );
348     SQLError            = cast(pfn_SQLError)GetProcAddress( hODBC32DLL, "SQLError" );
349     SQLExecDirect       = cast(pfn_SQLExecDirect)GetProcAddress( hODBC32DLL, "SQLExecDirect" );
350     SQLExecute          = cast(pfn_SQLExecute)GetProcAddress( hODBC32DLL, "SQLExecute" );
351     SQLExtendedFetch    = cast(pfn_SQLExtendedFetch)GetProcAddress( hODBC32DLL, "SQLExtendedFetch" );
352     SQLFetch            = cast(pfn_SQLFetch)GetProcAddress( hODBC32DLL, "SQLFetch" );
353     SQLFetchScroll      = cast(pfn_SQLFetchScroll)GetProcAddress( hODBC32DLL, "SQLFetchScroll" );
354     SQLForeignKeys      = cast(pfn_SQLForeignKeys)GetProcAddress( hODBC32DLL, "SQLForeignKeys" );
355     SQLFreeConnect      = cast(pfn_SQLFreeConnect)GetProcAddress( hODBC32DLL, "SQLFreeConnect" );
356     SQLFreeEnv          = cast(pfn_SQLFreeEnv)GetProcAddress( hODBC32DLL, "SQLFreeEnv" );
357     SQLFreeHandle       = cast(pfn_SQLFreeHandle)GetProcAddress( hODBC32DLL, "SQLFreeHandle" );
358     SQLFreeStmt         = cast(pfn_SQLFreeStmt)GetProcAddress( hODBC32DLL, "SQLFreeStmt" );
359     SQLGetConnectAttr   = cast(pfn_SQLGetConnectAttr)GetProcAddress( hODBC32DLL, "SQLGetConnectAttr" );
360     SQLGetConnectOption = cast(pfn_SQLGetConnectOption)GetProcAddress( hODBC32DLL, "SQLGetConnectOption" );
361     SQLGetCursorName    = cast(pfn_SQLGetCursorName)GetProcAddress( hODBC32DLL, "SQLGetCursorName" );
362     SQLGetData          = cast(pfn_SQLGetData)GetProcAddress( hODBC32DLL, "SQLGetData" );
363     SQLGetDescField     = cast(pfn_SQLGetDescField)GetProcAddress( hODBC32DLL, "SQLGetDescField" );
364     SQLGetDescRec       = cast(pfn_SQLGetDescRec)GetProcAddress( hODBC32DLL, "SQLGetDescRec" );
365     SQLGetDiagField     = cast(pfn_SQLGetDiagField)GetProcAddress( hODBC32DLL, "SQLGetDiagField" );
366     SQLGetDiagRec       = cast(pfn_SQLGetDiagRec)GetProcAddress( hODBC32DLL, "SQLGetDiagRec" );
367     SQLGetEnvAttr       = cast(pfn_SQLGetEnvAttr)GetProcAddress( hODBC32DLL, "SQLGetEnvAttr" );
368     SQLGetFunctions     = cast(pfn_SQLGetFunctions)GetProcAddress( hODBC32DLL, "SQLGetFunctions" );
369     SQLGetStmtAttr      = cast(pfn_SQLGetStmtAttr)GetProcAddress( hODBC32DLL, "SQLGetStmtAttr" );
370     SQLGetStmtOption    = cast(pfn_SQLGetStmtOption)GetProcAddress( hODBC32DLL, "SQLGetStmtOption" );
371     SQLGetTypeInfo      = cast(pfn_SQLGetTypeInfo)GetProcAddress( hODBC32DLL, "SQLGetTypeInfo" );
372     SQLMoreResults      = cast(pfn_SQLMoreResults)GetProcAddress( hODBC32DLL, "SQLMoreResults" );
373     SQLNativeSql        = cast(pfn_SQLNativeSql)GetProcAddress( hODBC32DLL, "SQLNativeSql" );
374     SQLNumParams        = cast(pfn_SQLNumParams)GetProcAddress( hODBC32DLL, "SQLNumParams" );
375     SQLNumResultCols    = cast(pfn_SQLNumResultCols)GetProcAddress( hODBC32DLL, "SQLNumResultCols" );
376     SQLParamData        = cast(pfn_SQLParamData)GetProcAddress( hODBC32DLL, "SQLParamData" );
377     SQLParamOptions     = cast(pfn_SQLParamOptions)GetProcAddress( hODBC32DLL, "SQLParamOptions" );
378     SQLPrepare          = cast(pfn_SQLPrepare)GetProcAddress( hODBC32DLL, "SQLPrepare" );
379     SQLPrimaryKeys      = cast(pfn_SQLPrimaryKeys)GetProcAddress( hODBC32DLL, "SQLPrimaryKeys" );
380     SQLProcedureColumns = cast(pfn_SQLProcedureColumns)GetProcAddress( hODBC32DLL, "SQLProcedureColumns" );
381     SQLProcedures       = cast(pfn_SQLProcedures)GetProcAddress( hODBC32DLL, "SQLProcedures" );
382     SQLPutData          = cast(pfn_SQLPutData)GetProcAddress( hODBC32DLL, "SQLPutData" );
383     SQLRowCount         = cast(pfn_SQLRowCount)GetProcAddress( hODBC32DLL, "SQLRowCount" );
384     SQLSetConnectAttr   = cast(pfn_SQLSetConnectAttr)GetProcAddress( hODBC32DLL, "SQLSetConnectAttr" );
385     SQLSetConnectOption = cast(pfn_SQLSetConnectOption)GetProcAddress( hODBC32DLL, "SQLSetConnectOption" );
386     SQLSetCursorName    = cast(pfn_SQLSetCursorName)GetProcAddress( hODBC32DLL, "SQLSetCursorName" );
387     SQLSetDescField     = cast(pfn_SQLSetDescField)GetProcAddress( hODBC32DLL, "SQLSetDescField" );
388     SQLSetDescRec       = cast(pfn_SQLSetDescRec)GetProcAddress( hODBC32DLL, "SQLSetDescRec" );
389     SQLSetEnvAttr       = cast(pfn_SQLSetEnvAttr)GetProcAddress( hODBC32DLL, "SQLSetEnvAttr" );
390     SQLSetParam         = cast(pfn_SQLSetParam)GetProcAddress( hODBC32DLL, "SQLSetParam" );
391     SQLSetPos           = cast(pfn_SQLSetPos)GetProcAddress( hODBC32DLL, "SQLSetPos" );
392     SQLSetStmtAttr      = cast(pfn_SQLSetStmtAttr)GetProcAddress( hODBC32DLL, "SQLSetStmtAttr" );
393     SQLSetStmtOption    = cast(pfn_SQLSetStmtOption)GetProcAddress( hODBC32DLL, "SQLSetStmtOption" );
394     SQLSpecialColumns   = cast(pfn_SQLSpecialColumns)GetProcAddress( hODBC32DLL, "SQLSpecialColumns" );
395     SQLStatistics       = cast(pfn_SQLStatistics)GetProcAddress( hODBC32DLL, "SQLStatistics" );
396     SQLTablePrivileges  = cast(pfn_SQLTablePrivileges)GetProcAddress( hODBC32DLL, "SQLTablePrivileges" );
397     SQLTables           = cast(pfn_SQLTables)GetProcAddress( hODBC32DLL, "SQLTables" );
398     SQLTransact         = cast(pfn_SQLTransact)GetProcAddress( hODBC32DLL, "SQLTransact" );
399
400    
401     return true;
402 }
403
404
405 /*! \endif
406 */
407
408     pfn_SQLAllocConnect     SQLAllocConnect     ;
409     pfn_SQLAllocEnv         SQLAllocEnv         ;
410     pfn_SQLAllocHandle      SQLAllocHandle      ;
411     pfn_SQLAllocStmt        SQLAllocStmt        ;
412     pfn_SQLBindCol          SQLBindCol          ;
413     pfn_SQLBindParam        SQLBindParam        ;
414     pfn_SQLBindParameter    SQLBindParameter    ;
415     pfn_SQLBrowseConnect    SQLBrowseConnect    ;
416     pfn_SQLBulkOperations   SQLBulkOperations   ;
417     pfn_SQLCancel           SQLCancel           ;   
418     pfn_SQLCloseCursor      SQLCloseCursor      ;   
419     pfn_SQLColAttribute     SQLColAttribute     ;
420     pfn_SQLColAttributes    SQLColAttributes    ;
421     pfn_SQLColumnPrivileges SQLColumnPrivileges ;
422     pfn_SQLColumns          SQLColumns          ;
423     pfn_SQLConnect          SQLConnect          ;
424     pfn_SQLCopyDesc         SQLCopyDesc         ;
425     pfn_SQLDataSources      SQLDataSources      ;
426     pfn_SQLDescribeCol      SQLDescribeCol      ;
427     pfn_SQLDescribeParam    SQLDescribeParam    ;
428     pfn_SQLDisconnect       SQLDisconnect       ;
429     pfn_SQLDriverConnect    SQLDriverConnect    ;
430     pfn_SQLDrivers          SQLDrivers          ;
431     pfn_SQLEndTran          SQLEndTran          ;
432     pfn_SQLError            SQLError            ;
433     pfn_SQLExecDirect       SQLExecDirect       ;
434     pfn_SQLExecute          SQLExecute          ;
435     pfn_SQLExtendedFetch    SQLExtendedFetch    ;
436     pfn_SQLFetch            SQLFetch            ;
437     pfn_SQLFetchScroll      SQLFetchScroll      ;
438     pfn_SQLForeignKeys      SQLForeignKeys      ;
439     pfn_SQLFreeConnect      SQLFreeConnect      ;
440     pfn_SQLFreeEnv          SQLFreeEnv          ;
441     pfn_SQLFreeHandle       SQLFreeHandle       ;
442     pfn_SQLFreeStmt         SQLFreeStmt         ;
443     pfn_SQLGetConnectAttr   SQLGetConnectAttr   ;
444     pfn_SQLGetConnectOption SQLGetConnectOption ;
445     pfn_SQLGetCursorName    SQLGetCursorName    ;
446     pfn_SQLGetData          SQLGetData          ;
447     pfn_SQLGetDescField     SQLGetDescField     ;
448     pfn_SQLGetDescRec       SQLGetDescRec       ;
449     pfn_SQLGetDiagField     SQLGetDiagField     ;
450     pfn_SQLGetDiagRec       SQLGetDiagRec       ;
451     pfn_SQLGetEnvAttr       SQLGetEnvAttr       ;
452     pfn_SQLGetFunctions     SQLGetFunctions     ;
453     pfn_SQLGetStmtAttr      SQLGetStmtAttr      ;
454     pfn_SQLGetStmtOption    SQLGetStmtOption    ;
455     pfn_SQLGetTypeInfo      SQLGetTypeInfo      ;
456     pfn_SQLMoreResults      SQLMoreResults      ;
457     pfn_SQLNativeSql        SQLNativeSql        ;
458     pfn_SQLNumParams        SQLNumParams        ;
459     pfn_SQLNumResultCols    SQLNumResultCols    ;
460     pfn_SQLParamData        SQLParamData        ;
461     pfn_SQLParamOptions     SQLParamOptions     ;
462     pfn_SQLPrepare          SQLPrepare          ;
463     pfn_SQLPrimaryKeys      SQLPrimaryKeys      ;
464     pfn_SQLProcedureColumns SQLProcedureColumns ;
465     pfn_SQLProcedures       SQLProcedures       ;
466     pfn_SQLPutData          SQLPutData          ;
467     pfn_SQLRowCount         SQLRowCount         ;
468     pfn_SQLSetConnectAttr   SQLSetConnectAttr   ;
469     pfn_SQLSetConnectOption SQLSetConnectOption ;
470     pfn_SQLSetCursorName    SQLSetCursorName    ;
471     pfn_SQLSetDescField     SQLSetDescField     ;
472     pfn_SQLSetDescRec       SQLSetDescRec       ;
473     pfn_SQLSetEnvAttr       SQLSetEnvAttr       ;
474     pfn_SQLSetParam         SQLSetParam         ;
475     pfn_SQLSetPos           SQLSetPos           ;
476     pfn_SQLSetStmtAttr      SQLSetStmtAttr      ;
477     pfn_SQLSetStmtOption    SQLSetStmtOption    ;
478     pfn_SQLSpecialColumns   SQLSpecialColumns   ;
479     pfn_SQLStatistics       SQLStatistics       ;
480     pfn_SQLTablePrivileges  SQLTablePrivileges  ;
481     pfn_SQLTables           SQLTables           ;
482     pfn_SQLTransact         SQLTransact         ;
483
484
485 } // version(Windows)
Note: See TracBrowser for help on using the browser.