PageRenderTime 51ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/trunk/DriverManager/SQLFetch.c

#
C | 355 lines | 182 code | 36 blank | 137 comment | 41 complexity | fb354103e923929a8dfebb2da41f3cd6 MD5 | raw file
Possible License(s): LGPL-2.1, AGPL-1.0
  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: SQLFetch.c,v 1.4 2009/02/18 17:59:08 lurcher Exp $
  31. *
  32. * $Log: SQLFetch.c,v $
  33. * Revision 1.4 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.3 2003/10/30 18:20:45 lurcher
  37. *
  38. * Fix broken thread protection
  39. * Remove SQLNumResultCols after execute, lease S4/S% to driver
  40. * Fix string overrun in SQLDriverConnect
  41. * Add initial support for Interix
  42. *
  43. * Revision 1.2 2002/12/05 17:44:30 lurcher
  44. *
  45. * Display unknown return values in return logging
  46. *
  47. * Revision 1.1.1.1 2001/10/17 16:40:05 lurcher
  48. *
  49. * First upload to SourceForge
  50. *
  51. * Revision 1.4 2001/04/12 17:43:36 nick
  52. *
  53. * Change logging and added autotest to odbctest
  54. *
  55. * Revision 1.3 2001/01/14 10:09:39 nick
  56. *
  57. * Add sqi/test to build
  58. *
  59. * Revision 1.2 2001/01/09 22:33:13 nick
  60. *
  61. * Stop passing NULL into SQLExtendedFetch
  62. * Further fixes to unicode to ansi conversions
  63. *
  64. * Revision 1.1.1.1 2000/09/04 16:42:52 nick
  65. * Imported Sources
  66. *
  67. * Revision 1.9 2000/02/11 00:41:46 ngorham
  68. *
  69. * Added a couple of fixes for drivers without SQLExtendedFetch
  70. *
  71. * Revision 1.8 2000/02/02 07:55:21 ngorham
  72. *
  73. * Add flag to disable SQLFetch -> SQLExtendedFetch mapping
  74. *
  75. * Revision 1.7 1999/11/13 23:40:59 ngorham
  76. *
  77. * Alter the way DM logging works
  78. * Upgrade the Postgres driver to 6.4.6
  79. *
  80. * Revision 1.6 1999/10/24 23:54:18 ngorham
  81. *
  82. * First part of the changes to the error reporting
  83. *
  84. * Revision 1.5 1999/09/21 22:34:24 ngorham
  85. *
  86. * Improve performance by removing unneeded logging calls when logging is
  87. * disabled
  88. *
  89. * Revision 1.4 1999/07/10 21:10:16 ngorham
  90. *
  91. * Adjust error sqlstate from driver manager, depending on requested
  92. * version (ODBC2/3)
  93. *
  94. * Revision 1.3 1999/07/04 21:05:07 ngorham
  95. *
  96. * Add LGPL Headers to code
  97. *
  98. * Revision 1.2 1999/06/30 23:56:54 ngorham
  99. *
  100. * Add initial thread safety code
  101. *
  102. * Revision 1.1.1.1 1999/05/29 13:41:06 sShandyb
  103. * first go at it
  104. *
  105. * Revision 1.2 1999/06/02 23:48:45 ngorham
  106. *
  107. * Added more 3-2 mapping
  108. *
  109. * Revision 1.1.1.1 1999/05/27 18:23:17 pharvey
  110. * Imported sources
  111. *
  112. * Revision 1.4 1999/05/03 19:50:43 nick
  113. * Another check point
  114. *
  115. * Revision 1.3 1999/04/30 16:22:47 nick
  116. * Another checkpoint
  117. *
  118. * Revision 1.2 1999/04/29 20:47:37 nick
  119. * Another checkpoint
  120. *
  121. * Revision 1.1 1999/04/25 23:06:11 nick
  122. * Initial revision
  123. *
  124. *
  125. **********************************************************************/
  126. #include <config.h>
  127. #include "drivermanager.h"
  128. static char const rcsid[]= "$RCSfile: SQLFetch.c,v $ $Revision: 1.4 $";
  129. SQLRETURN SQLFetch( SQLHSTMT statement_handle )
  130. {
  131. DMHSTMT statement = (DMHSTMT) statement_handle;
  132. SQLRETURN ret;
  133. SQLCHAR s1[ 100 + LOG_MESSAGE_LEN ];
  134. /*
  135. * check statement
  136. */
  137. if ( !__validate_stmt( statement ))
  138. {
  139. dm_log_write( __FILE__,
  140. __LINE__,
  141. LOG_INFO,
  142. LOG_INFO,
  143. "Error: SQL_INVALID_HANDLE" );
  144. return SQL_INVALID_HANDLE;
  145. }
  146. function_entry( statement );
  147. if ( log_info.log_flag )
  148. {
  149. sprintf( statement -> msg, "\n\t\tEntry:\
  150. \n\t\t\tStatement = %p",
  151. statement );
  152. dm_log_write( __FILE__,
  153. __LINE__,
  154. LOG_INFO,
  155. LOG_INFO,
  156. statement -> msg );
  157. }
  158. /*
  159. * check states
  160. */
  161. thread_protect( SQL_HANDLE_STMT, statement );
  162. if ( statement -> state == STATE_S1 ||
  163. statement -> state == STATE_S2 ||
  164. statement -> state == STATE_S3 )
  165. {
  166. dm_log_write( __FILE__,
  167. __LINE__,
  168. LOG_INFO,
  169. LOG_INFO,
  170. "Error: HY010" );
  171. __post_internal_error( &statement -> error,
  172. ERROR_HY010, NULL,
  173. statement -> connection -> environment -> requested_version );
  174. return function_return( SQL_HANDLE_STMT, statement, SQL_ERROR );
  175. }
  176. if ( statement -> state == STATE_S4 )
  177. {
  178. dm_log_write( __FILE__,
  179. __LINE__,
  180. LOG_INFO,
  181. LOG_INFO,
  182. "Error: 24000" );
  183. __post_internal_error( &statement -> error,
  184. ERROR_24000, NULL,
  185. statement -> connection -> environment -> requested_version );
  186. return function_return( SQL_HANDLE_STMT, statement, SQL_ERROR );
  187. }
  188. if ( statement -> state == STATE_S8 ||
  189. statement -> state == STATE_S9 ||
  190. statement -> state == STATE_S10 )
  191. {
  192. dm_log_write( __FILE__,
  193. __LINE__,
  194. LOG_INFO,
  195. LOG_INFO,
  196. "Error: HY010" );
  197. __post_internal_error( &statement -> error,
  198. ERROR_HY010, NULL,
  199. statement -> connection -> environment -> requested_version );
  200. return function_return( SQL_HANDLE_STMT, statement, SQL_ERROR );
  201. }
  202. if ( statement -> state == STATE_S11 ||
  203. statement -> state == STATE_S12 )
  204. {
  205. if ( statement -> interupted_func != SQL_API_SQLFETCH )
  206. {
  207. dm_log_write( __FILE__,
  208. __LINE__,
  209. LOG_INFO,
  210. LOG_INFO,
  211. "Error: HY010" );
  212. __post_internal_error( &statement -> error,
  213. ERROR_HY010, NULL,
  214. statement -> connection -> environment -> requested_version );
  215. return function_return( SQL_HANDLE_STMT, statement, SQL_ERROR );
  216. }
  217. }
  218. if ( CHECK_SQLFETCH( statement -> connection ))
  219. {
  220. /*
  221. * this is odd, but its in the book
  222. */
  223. if ( statement -> connection -> driver_act_ver == SQL_OV_ODBC2 &&
  224. CHECK_SQLEXTENDEDFETCH( statement -> connection ) &&
  225. statement -> connection -> ex_fetch_mapping )
  226. {
  227. /*
  228. * the row_st_arr can't be null
  229. */
  230. if ( statement -> row_st_arr )
  231. {
  232. ret = SQLEXTENDEDFETCH( statement -> connection,
  233. statement -> driver_stmt,
  234. SQL_FETCH_NEXT,
  235. NULL,
  236. statement -> row_ct_ptr,
  237. statement -> row_st_arr );
  238. }
  239. else
  240. {
  241. SQLUSMALLINT *row_st_arr;
  242. int row_count;
  243. SQLUSMALLINT row_status;
  244. if ( statement -> row_array_size <= 1 )
  245. {
  246. row_count = 1;
  247. row_st_arr = &row_status;
  248. }
  249. else
  250. {
  251. row_count = statement -> row_array_size;
  252. row_st_arr = malloc( sizeof( SQLUSMALLINT ) * row_count );
  253. }
  254. ret = SQLEXTENDEDFETCH( statement -> connection,
  255. statement -> driver_stmt,
  256. SQL_FETCH_NEXT,
  257. NULL,
  258. statement -> row_ct_ptr,
  259. row_st_arr );
  260. if ( row_count > 1 )
  261. {
  262. free( row_st_arr );
  263. }
  264. }
  265. }
  266. else
  267. {
  268. ret = SQLFETCH( statement -> connection,
  269. statement -> driver_stmt );
  270. if( statement -> connection -> driver_act_ver == SQL_OV_ODBC2 &&
  271. statement -> row_ct_ptr ) {
  272. if( ret == SQL_SUCCESS || ret == SQL_SUCCESS_WITH_INFO ) {
  273. *statement -> row_ct_ptr = 1;
  274. } else {
  275. *statement -> row_ct_ptr = 0;
  276. }
  277. }
  278. }
  279. }
  280. else
  281. {
  282. dm_log_write( __FILE__,
  283. __LINE__,
  284. LOG_INFO,
  285. LOG_INFO,
  286. "Error: IM001" );
  287. __post_internal_error( &statement -> error,
  288. ERROR_IM001, NULL,
  289. statement -> connection -> environment -> requested_version );
  290. return function_return( SQL_HANDLE_STMT, statement, SQL_ERROR );
  291. }
  292. if ( ret == SQL_STILL_EXECUTING )
  293. {
  294. statement -> interupted_func = SQL_API_SQLFETCH;
  295. if ( statement -> state != STATE_S11 &&
  296. statement -> state != STATE_S12 )
  297. statement -> state = STATE_S11;
  298. }
  299. else if ( SQL_SUCCEEDED( ret ))
  300. {
  301. statement -> state = STATE_S6;
  302. statement -> eod = 0;
  303. }
  304. else if ( ret == SQL_NO_DATA ) {
  305. statement -> eod = 1;
  306. }
  307. if ( log_info.log_flag )
  308. {
  309. sprintf( statement -> msg,
  310. "\n\t\tExit:[%s]",
  311. __get_return_status( ret, s1 ));
  312. dm_log_write( __FILE__,
  313. __LINE__,
  314. LOG_INFO,
  315. LOG_INFO,
  316. statement -> msg );
  317. }
  318. return function_return( SQL_HANDLE_STMT, statement, ret );
  319. }