NCBI C++ ToolKit
result.cpp
Go to the documentation of this file.

Go to the SVN repository for this file.

1 /* $Id: result.cpp 100656 2023-08-23 18:21:57Z ucko $
2  * ===========================================================================
3  *
4  * PUBLIC DOMAIN NOTICE
5  * National Center for Biotechnology Information
6  *
7  * This software/database is a "United States Government Work" under the
8  * terms of the United States Copyright Act. It was written as part of
9  * the author's official duties as a United States Government employee and
10  * thus cannot be copyrighted. This software/database is freely available
11  * to the public for use. The National Library of Medicine and the U.S.
12  * Government have not placed any restriction on its use or reproduction.
13  *
14  * Although all reasonable efforts have been taken to ensure the accuracy
15  * and reliability of the software and data, the NLM and the U.S.
16  * Government do not and cannot warrant the performance or results that
17  * may be obtained by using this software or data. The NLM and the U.S.
18  * Government disclaim all warranties, express or implied, including
19  * warranties of performance, merchantability or fitness for any particular
20  * purpose.
21  *
22  * Please cite the author in any work or product based on this material.
23  *
24  * ===========================================================================
25  *
26  * Author: Vladimir Soussov
27  *
28  * File Description: ODBC Results
29  *
30  */
31 
32 #include <ncbi_pch.hpp>
35 #include <dbapi/error_codes.hpp>
36 
37 #include "odbc_utils.hpp"
38 
39 
40 #define NCBI_USE_ERRCODE_X Dbapi_Odbc_Results
41 
42 #undef NCBI_DATABASE_THROW
43 #undef NCBI_DATABASE_RETHROW
44 
45 #define NCBI_DATABASE_THROW(ex_class, message, err_code, severity) \
46  NCBI_ODBC_THROW(ex_class, message, err_code, severity)
47 #define NCBI_DATABASE_RETHROW(prev_ex, ex_class, message, err_code, severity) \
48  NCBI_ODBC_RETHROW(prev_ex, ex_class, message, err_code, severity)
49 
50 // Accommodate all the code of the form
51 // string err_message = "..." + GetDbgInfo();
52 // DATABASE_DRIVER_ERROR(err_message, ...);
53 // which will still pick up the desired context due to
54 // NCBI_DATABASE_(RE)THROW's above redefinitions.
55 #define GetDbgInfo() 0
56 
57 
59 
60 /////////////////////////////////////////////////////////////////////////////
61 static const char* wrong_type = "Wrong type of CDB_Object.";
62 
63 /////////////////////////////////////////////////////////////////////////////
64 
66  SQLULEN prec)
67 {
68  switch (t) {
69  case SQL_WCHAR:
70  case SQL_CHAR: return (prec < 256)? eDB_Char : eDB_LongChar;
71  case SQL_WVARCHAR:
72  case SQL_VARCHAR: return eDB_VarChar;
73  case SQL_LONGVARCHAR: return eDB_Text;
74  case SQL_LONGVARBINARY:
75  case SQL_WLONGVARCHAR:
76  return eDB_Image;
77  case SQL_DECIMAL:
78  case SQL_NUMERIC: if(prec > 20 || dec_digits > 0) return eDB_Numeric;
79  case SQL_BIGINT: return eDB_BigInt;
80  case SQL_SMALLINT: return eDB_SmallInt;
81  case SQL_INTEGER: return eDB_Int;
82  case SQL_FLOAT: return eDB_Double;
83  case SQL_REAL: return eDB_Float;
84  case SQL_DOUBLE: return eDB_Double;
85  case SQL_BINARY: return (prec < 256)? eDB_Binary : eDB_LongBinary;
86  case SQL_BIT: return eDB_Bit;
87  case SQL_TINYINT: return eDB_TinyInt;
88  case SQL_VARBINARY: return (prec < 256)? eDB_VarBinary : eDB_LongBinary;
89  case SQL_TYPE_TIMESTAMP:
90  if (prec <= 16 && dec_digits <= 0) {
91  return eDB_SmallDateTime;
92  } else if (prec <= 23 && dec_digits <= 3) {
93  return eDB_DateTime;
94  } else {
95  return eDB_BigDateTime;
96  }
97  default: return eDB_UnsupportedType;
98  }
99 }
100 
101 
102 /////////////////////////////////////////////////////////////////////////////
103 //
104 // CODBC_RowResult::
105 //
106 
107 
110  SQLSMALLINT nof_cols,
111  SQLLEN* row_count
112  )
113  : m_Stmt(stmt)
114  , m_CurrItem(-1)
115  , m_EOR(false)
116  , m_RowCountPtr( row_count )
117  , m_HasMoreData(false)
118 {
119  odbc::TSqlChar column_name_buff[eODBC_Column_Name_Size];
120 
121  if(m_RowCountPtr) *m_RowCountPtr = 0;
122 
123  SQLSMALLINT actual_name_size;
124  SQLSMALLINT nullable;
125 
126  m_ColFmt = new SODBC_ColDescr[nof_cols];
127  for (unsigned int n = 0; n < (unsigned int)nof_cols; ++n) {
128  // SQLDescribeCol takes a pointer to a buffer.
129  switch(SQLDescribeCol(GetHandle(),
130  n + 1,
131  column_name_buff,
133  &actual_name_size,
134  &m_ColFmt[n].DataType,
135  &m_ColFmt[n].ColumnSize,
136  &m_ColFmt[n].DecimalDigits,
137  &nullable)) {
139  ReportErrors();
140  case SQL_SUCCESS:
142  CODBCString(column_name_buff,
143  actual_name_size).ConvertTo(GetClientEncoding());
144  break;
145  case SQL_ERROR:
146  ReportErrors();
147  {
148  string err_message = "SQLDescribeCol failed." + GetDbgInfo();
149  DATABASE_DRIVER_ERROR( err_message, 420020 );
150  }
151  default:
152  {
153  string err_message = "SQLDescribeCol failed (memory corruption suspected)." + GetDbgInfo();
154  DATABASE_DRIVER_ERROR( err_message, 420021 );
155  }
156  }
157 
159  m_ColFmt[n].ColumnName,
160  m_ColFmt[n].ColumnSize,
161  s_GetDataType(m_ColFmt[n].DataType,
162  m_ColFmt[n].DecimalDigits,
163  m_ColFmt[n].ColumnSize)
164  );
165  }
166 }
167 
168 
170 {
171  return eDB_RowResult;
172 }
173 
174 
176 {
177  m_CurrItem = -1;
178  m_LastReadData.resize(0);
179  m_HasMoreData = false;
180  if (!m_EOR) {
181  switch (SQLFetch(GetHandle())) {
183  ReportErrors();
184  case SQL_SUCCESS:
185  m_CurrItem = 0;
186  m_HasMoreData = true;
187  if ( m_RowCountPtr != NULL ) {
188  ++(*m_RowCountPtr);
189  }
190  return true;
191  case SQL_NO_DATA:
192  m_EOR = true;
193  break;
194  case SQL_ERROR:
195  ReportErrors();
196  {
197  string err_message = "SQLFetch failed." + GetDbgInfo();
198  DATABASE_DRIVER_ERROR( err_message, 430003 );
199  }
200  default:
201  {
202  string err_message = "SQLFetch failed (memory corruption suspected)." + GetDbgInfo();
203  DATABASE_DRIVER_ERROR( err_message, 430004 );
204  }
205  }
206  }
207  return false;
208 }
209 
210 
212 {
213  return m_CurrItem;
214 }
215 
217 {
218  return static_cast<int>(GetDefineParams().GetNum());
219 }
220 
222  SQLINTEGER buffer_size, bool* more)
223 {
224  SQLLEN f;
225  bool fake_more;
226  if (more == NULL) {
227  more = &fake_more;
228  } else {
229  *more = false;
230  }
231 
232  switch(SQLGetData(GetHandle(), m_CurrItem+1, target_type, buffer, buffer_size, &f)) {
234  switch(f) {
235  case SQL_NO_TOTAL:
236  *more = true;
237  return buffer_size;
238  case SQL_NULL_DATA:
239  return 0;
240  default:
241  if (f < 0) {
242  ReportErrors();
243  } else {
244  *more = true;
245  }
246  return (int)f;
247  }
248  case SQL_SUCCESS:
249  if(target_type == SQL_C_CHAR) buffer_size--;
250  return (f > buffer_size)? buffer_size : (int)f;
251  case SQL_NO_DATA:
252  return 0;
253  case SQL_ERROR:
254  ReportErrors();
255  default:
256  {
257  string err_message = "SQLGetData failed." + GetDbgInfo();
258  DATABASE_DRIVER_ERROR( err_message, 430027 );
259  }
260  }
261 }
262 
266 {
267  list<string> extra_buffers;
268  char * current_buffer = buffer.get();
269  SQLINTEGER current_size = buffer_size;
270  ssize_t n;
271  int nul_size;
272  bool more;
273  switch (target_type) {
274  case SQL_C_CHAR: nul_size = 1; break;
275  case SQL_C_WCHAR: nul_size = sizeof(wchar_t); break;
276  default: nul_size = 0; break;
277  }
278  while ((n = xGetData(target_type, current_buffer, current_size, &more))
279  >= current_size && more) {
280  if (n > current_size) {
281  // Add margin for (possibly wide) NUL-related complications.
282  current_size = static_cast<int>(n) + 2 * nul_size - current_size;
283  }
284  extra_buffers.emplace_back(string(current_size, '\0'));
285  current_buffer = const_cast<char*>(extra_buffers.back().data());
286  }
287  if (extra_buffers.empty()) {
288  return n;
289  }
290 
291  const char * orig_buffer = buffer.get();
292  int elided = 0;
293  extra_buffers.back().resize(n);
294  n = buffer_size;
295  for (const auto & it : extra_buffers) {
296  n += it.size();
297  }
298  buffer.reset(new char[n + nul_size]);
299  memcpy(buffer.get(), orig_buffer, buffer_size);
300  ssize_t pos = buffer_size;
301  for (const auto & it : extra_buffers) {
302  if (nul_size > 0 && pos >= nul_size) {
303  bool elide = true;
304  for (int i = 1; i <= nul_size; ++i) {
305  if (buffer.get()[pos - i] != '\0') {
306  elide = false;
307  break;
308  }
309  }
310  if (elide) {
311  pos -= nul_size;
312  elided += nul_size;
313  }
314  }
315  memcpy(buffer.get() + pos, it.data(), it.size());
316  pos += it.size();
317  }
318  memset(buffer.get() + pos, '\0', nul_size);
319  _ASSERT(pos + elided == n);
320  return pos;
321 }
322 
324 {
325  swap_numeric_endian((unsigned int)s.precision, s.val);
326  d->Assign((unsigned int)s.precision, (unsigned int)s.scale,
327  s.sign == 0, s.val);
328 }
329 
331 {
332  int rc = 0;
333  SQLLEN f = 0;
334 
335  char buffer[8*1024];
336 
337  rc = SQLGetData(GetHandle(), m_CurrItem + 1, SQL_C_CHAR, buffer, sizeof(buffer), &f);
338 
339  switch( rc ) {
341  if(f == SQL_NO_TOTAL) {
342  f = sizeof(buffer) - 1;
343  } else if(f < 0) {
344  ReportErrors();
345  }
346  case SQL_SUCCESS:
347  if(f > 0) {
348  if(f > SQLLEN(sizeof(buffer) - 1)) {
349  f = sizeof(buffer)-1;
350  }
351 
352  val->Append(buffer, f);
353  }
354  return true;
355  case SQL_NO_DATA:
356  break;
357  case SQL_ERROR:
358  ReportErrors();
359  default:
360  {
362  string("SQLGetData failed while retrieving BLOB into C") +
363  CDB_Object::GetTypeName(val->GetType()) + '.',
364  430021);
365  }
366  }
367 
368  return false;
369 }
370 
371 #ifdef HAVE_WSTRING
373 {
374  int rc = 0;
375  SQLLEN f = 0;
376 
377  wchar_t buffer[4*1024];
378 
379  rc = SQLGetData(GetHandle(), m_CurrItem + 1, SQL_C_WCHAR, buffer, sizeof(buffer), &f);
380 
381  switch( rc ) {
383  if(f == SQL_NO_TOTAL) {
384  f = sizeof(buffer) - 1;
385  } else if(f < 0) {
386  ReportErrors();
387  }
388  case SQL_SUCCESS:
389  if(f > 0) {
390  if(f > SQLLEN(sizeof(buffer) - 1)) {
391  f = sizeof(buffer)-1;
392  }
393 
394  f = f / sizeof(wchar_t);
395 
396  string encoded_value = CODBCString(buffer, f).ConvertTo(GetClientEncoding());
397  val->Append(encoded_value.data(), encoded_value.size());
398  }
399  return true;
400  case SQL_NO_DATA:
401  break;
402  case SQL_ERROR:
403  ReportErrors();
404  default:
405  {
407  string("SQLGetData failed while retrieving BLOB into C") +
408  CDB_Object::GetTypeName(val->GetType()) + '.',
409  430021);
410  }
411  }
412 
413  return false;
414 }
415 #endif
416 
418 {
419  SQLLEN f = 0;
420  char buffer[8*1024];
421 
422  switch(SQLGetData(GetHandle(), m_CurrItem+1, SQL_C_BINARY, buffer, sizeof(buffer), &f)) {
424  if(f == SQL_NO_TOTAL || f > SQLLEN(sizeof(buffer))) f = sizeof(buffer);
425  else ReportErrors();
426  case SQL_SUCCESS:
427  if(f > 0) {
428  if(f > SQLLEN(sizeof(buffer))) f = sizeof(buffer);
429  val->Append(buffer, f);
430  }
431  return true;
432  case SQL_NO_DATA:
433  break;
434  case SQL_ERROR:
435  ReportErrors();
436  default:
437  {
439  string("SQLGetData failed while retrieving BLOB into C") +
440  CDB_Object::GetTypeName(val->GetType()) + '.',
441  430022);
442  }
443  }
444 
445  return false;
446 }
447 
449 {
450  char base_buf[8*1024];
451  TItemBuffer buffer(base_buf, eNoOwnership);
452  ssize_t outlen;
453 
454  switch(m_ColFmt[m_CurrItem].DataType) {
455  case SQL_WCHAR:
456  case SQL_WVARCHAR:
457  switch (item_buf->GetType()) {
458  case eDB_VarBinary:
459  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
460  if ( outlen <= 0) item_buf->AssignNULL();
461  else ((CDB_VarBinary*)item_buf)->SetValue(buffer.get(), outlen);
462  break;
463  case eDB_Binary:
464  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
465  if ( outlen <= 0) item_buf->AssignNULL();
466  else ((CDB_Binary*)item_buf)->SetValue(buffer.get(), outlen);
467  break;
468  case eDB_LongBinary:
469  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
470  if ( outlen <= 0) item_buf->AssignNULL();
471  else ((CDB_LongBinary*)item_buf)->SetValue(buffer.get(), outlen);
472  break;
473 #ifdef HAVE_WSTRING
474  case eDB_VarChar:
475  outlen = x_GetVarLenData(SQL_C_WCHAR, buffer, sizeof(base_buf));
476  if ( outlen <= 0) item_buf->AssignNULL();
477  else *((CDB_VarChar*)item_buf)
478  = CODBCString((wchar_t*)buffer.get())
480  break;
481  case eDB_Char:
482  outlen = x_GetVarLenData(SQL_C_WCHAR, buffer, sizeof(base_buf));
483  if ( outlen <= 0) item_buf->AssignNULL();
484  else *((CDB_Char*)item_buf)
485  = CODBCString((wchar_t*)buffer.get())
487  break;
488  case eDB_LongChar:
489  outlen = x_GetVarLenData(SQL_C_WCHAR, buffer, sizeof(base_buf));
490  if ( outlen <= 0) item_buf->AssignNULL();
491  else *((CDB_LongChar*)item_buf)
492  = CODBCString((wchar_t*)buffer.get())
494  break;
495 #endif
496  default:
497  {
498  string err_message = wrong_type + GetDbgInfo();
499  DATABASE_DRIVER_ERROR( err_message, 430020 );
500  }
501  }
502  break;
503  case SQL_VARCHAR:
504  case SQL_CHAR: {
505  switch (item_buf->GetType()) {
506  case eDB_VarBinary:
507  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
508  if ( outlen <= 0) item_buf->AssignNULL();
509  else ((CDB_VarBinary*) item_buf)->SetValue(buffer.get(), outlen);
510  break;
511  case eDB_Binary:
512  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
513  if ( outlen <= 0) item_buf->AssignNULL();
514  else ((CDB_Binary*) item_buf)->SetValue(buffer.get(), outlen);
515  break;
516  case eDB_LongBinary:
517  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
518  if ( outlen <= 0) item_buf->AssignNULL();
519  else ((CDB_LongBinary*) item_buf)->SetValue(buffer.get(), outlen);
520  break;
521  case eDB_VarChar:
522  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
523  if ( outlen < 0) item_buf->AssignNULL();
524  else *((CDB_VarChar*) item_buf) = buffer.get();
525  break;
526  case eDB_Char:
527  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
528  if ( outlen < 0) item_buf->AssignNULL();
529  else *((CDB_Char*) item_buf) = buffer.get();
530  break;
531  case eDB_LongChar:
532  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
533  if ( outlen < 0) item_buf->AssignNULL();
534  else *((CDB_LongChar*) item_buf) = buffer.get();
535  break;
536  default:
537  {
538  string err_message = wrong_type + GetDbgInfo();
539  DATABASE_DRIVER_ERROR( err_message, 430020 );
540  }
541  }
542  break;
543  }
544 
545  case SQL_BINARY:
546  case SQL_VARBINARY: {
547  switch ( item_buf->GetType() ) {
548  case eDB_VarBinary:
549  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
550  if ( outlen <= 0) item_buf->AssignNULL();
551  else ((CDB_VarBinary*) item_buf)->SetValue(buffer.get(), outlen);
552  break;
553  case eDB_Binary:
554  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
555  if ( outlen <= 0) item_buf->AssignNULL();
556  else ((CDB_Binary*) item_buf)->SetValue(buffer.get(), outlen);
557  break;
558  case eDB_LongBinary:
559  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
560  if ( outlen <= 0) item_buf->AssignNULL();
561  else ((CDB_LongBinary*) item_buf)->SetValue(buffer.get(), outlen);
562  break;
563  case eDB_VarChar:
564  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
565  if (outlen < 0) item_buf->AssignNULL();
566  else *((CDB_VarChar*) item_buf) = buffer.get();
567  break;
568  case eDB_Char:
569  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
570  if (outlen < 0) item_buf->AssignNULL();
571  else *((CDB_Char*) item_buf) = buffer.get();
572  break;
573  case eDB_LongChar:
574  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
575  if (outlen < 0) item_buf->AssignNULL();
576  else *((CDB_LongChar*) item_buf) = buffer.get();
577  break;
578  default:
579  {
580  string err_message = wrong_type + GetDbgInfo();
581  DATABASE_DRIVER_ERROR( err_message, 430020 );
582  }
583  }
584 
585  break;
586  }
587 
588  case SQL_BIT: {
589  SQLCHAR v;
590  switch ( item_buf->GetType() ) {
591  case eDB_Bit:
592  outlen = xGetData(SQL_C_BIT, &v, sizeof(SQLCHAR));
593  if (outlen <= 0) item_buf->AssignNULL();
594  else *((CDB_Bit*) item_buf) = (int) v;
595  break;
596  case eDB_TinyInt:
597  outlen = xGetData(SQL_C_BIT, &v, sizeof(SQLCHAR));
598  if (outlen <= 0) item_buf->AssignNULL();
599  else *((CDB_TinyInt*) item_buf) = v ? 1 : 0;
600  break;
601  case eDB_SmallInt:
602  outlen = xGetData(SQL_C_BIT, &v, sizeof(SQLCHAR));
603  if (outlen <= 0) item_buf->AssignNULL();
604  else *((CDB_SmallInt*) item_buf) = v ? 1 : 0;
605  break;
606  case eDB_Int:
607  outlen = xGetData(SQL_C_BIT, &v, sizeof(SQLCHAR));
608  if (outlen <= 0) item_buf->AssignNULL();
609  else *((CDB_Int*) item_buf) = v ? 1 : 0;
610  break;
611  default:
612  {
613  string err_message = wrong_type + GetDbgInfo();
614  DATABASE_DRIVER_ERROR( err_message, 430020 );
615  }
616  }
617  break;
618  }
619 
620  case SQL_TYPE_TIMESTAMP: {
622  switch ( item_buf->GetType() ) {
623  case eDB_SmallDateTime:
624  case eDB_DateTime:
625  case eDB_BigDateTime:
626  {
627  outlen = xGetData(SQL_C_TYPE_TIMESTAMP, &v, sizeof(SQL_TIMESTAMP_STRUCT));
628  if (outlen <= 0) item_buf->AssignNULL();
629  else {
630  CTime t((int)v.year, (int)v.month, (int)v.day,
631  (int)v.hour, (int)v.minute, (int)v.second,
632  (long)v.fraction);
633 
634  switch (item_buf->GetType()) {
635  case eDB_SmallDateTime:
636  *((CDB_SmallDateTime*) item_buf) = t;
637  break;
638  case eDB_DateTime:
639  *((CDB_DateTime*) item_buf) = t;
640  break;
641  case eDB_BigDateTime:
642  // TODO - try to distinguish specific types?
643  *((CDB_BigDateTime*) item_buf) = t;
644  break;
645  default:
646  _TROUBLE;
647  }
648  }
649  break;
650  }
651  default:
652  {
653  string err_message = wrong_type + GetDbgInfo();
654  DATABASE_DRIVER_ERROR( err_message, 430020 );
655  }
656  }
657  break;
658  }
659 
660  case SQL_TINYINT: {
661  SQLCHAR v;
662  switch ( item_buf->GetType() ) {
663  case eDB_TinyInt:
664  outlen = xGetData(SQL_C_UTINYINT, &v, sizeof(SQLCHAR));
665  if (outlen <= 0) item_buf->AssignNULL();
666  else *((CDB_TinyInt*) item_buf) = (Uint1) v;
667  break;
668  case eDB_SmallInt:
669  outlen = xGetData(SQL_C_UTINYINT, &v, sizeof(SQLCHAR));
670  if (outlen <= 0) item_buf->AssignNULL();
671  else *((CDB_SmallInt*) item_buf) = (Int2) v;
672  break;
673  case eDB_Int:
674  outlen = xGetData(SQL_C_UTINYINT, &v, sizeof(SQLCHAR));
675  if (outlen <= 0) item_buf->AssignNULL();
676  else *((CDB_Int*) item_buf) = (Int4) v;
677  break;
678  default:
679  {
680  string err_message = wrong_type + GetDbgInfo();
681  DATABASE_DRIVER_ERROR( err_message, 430020 );
682  }
683  }
684  break;
685  }
686 
687  case SQL_SMALLINT: {
688  SQLSMALLINT v;
689  switch ( item_buf->GetType() ) {
690  case eDB_SmallInt:
691  outlen = xGetData(SQL_C_SSHORT, &v, sizeof(SQLSMALLINT));
692  if (outlen <= 0) item_buf->AssignNULL();
693  else *((CDB_SmallInt*) item_buf) = (Int2) v;
694  break;
695  case eDB_Int:
696  outlen = xGetData(SQL_C_SSHORT, &v, sizeof(SQLSMALLINT));
697  if (outlen <= 0) item_buf->AssignNULL();
698  else *((CDB_Int*) item_buf) = (Int4) v;
699  break;
700  default:
701  {
702  string err_message = wrong_type + GetDbgInfo();
703  DATABASE_DRIVER_ERROR( err_message, 430020 );
704  }
705  }
706  break;
707  }
708 
709  case SQL_INTEGER: {
710  SQLINTEGER v;
711  switch ( item_buf->GetType() ) {
712  case eDB_Int:
713  outlen = xGetData(SQL_C_SLONG, &v, sizeof(SQLINTEGER));
714  if (outlen <= 0) item_buf->AssignNULL();
715  else *((CDB_Int*) item_buf) = (Int4) v;
716  break;
717  default:
718  {
719  string err_message = wrong_type + GetDbgInfo();
720  DATABASE_DRIVER_ERROR( err_message, 430020 );
721  }
722  }
723  break;
724  }
725 
726  case SQL_DOUBLE:
727  case SQL_FLOAT: {
728  SQLDOUBLE v;
729  switch ( item_buf->GetType() ) {
730  case eDB_Double:
731  outlen = xGetData(SQL_C_DOUBLE, &v, sizeof(SQLDOUBLE));
732  if (outlen <= 0) item_buf->AssignNULL();
733  else *((CDB_Double*) item_buf) = v;
734  break;
735  default:
736  {
737  string err_message = wrong_type + GetDbgInfo();
738  DATABASE_DRIVER_ERROR( err_message, 430020 );
739  }
740  }
741  break;
742  }
743 
744  case SQL_REAL: {
745  SQLREAL v;
746  switch ( item_buf->GetType() ) {
747  case eDB_Float:
748  outlen = xGetData(SQL_C_FLOAT, &v, sizeof(SQLREAL));
749  if (outlen <= 0) item_buf->AssignNULL();
750  else *((CDB_Float*) item_buf) = v;
751  break;
752  default:
753  {
754  string err_message = wrong_type + GetDbgInfo();
755  DATABASE_DRIVER_ERROR( err_message, 430020 );
756  }
757  }
758  break;
759  }
760 
761  case SQL_BIGINT:
762  case SQL_DECIMAL:
763  case SQL_NUMERIC: {
764  switch ( item_buf->GetType() ) {
765  case eDB_Numeric: {
767  SQLHDESC hdesc;
769  SQLSetDescField(hdesc, m_CurrItem + 1, SQL_DESC_TYPE, (VOID*)SQL_C_NUMERIC, 0);
771  (VOID*)(m_ColFmt[m_CurrItem].ColumnSize), 0);
773  reinterpret_cast<VOID*>(m_ColFmt[m_CurrItem].DecimalDigits), 0);
774 
775  // outlen = xGetData(SQL_ARD_TYPE, &v, sizeof(SQL_NUMERIC_STRUCT));
776  outlen = xGetData(SQL_C_NUMERIC, &v, sizeof(SQL_NUMERIC_STRUCT));
777  if (outlen <= 0) item_buf->AssignNULL();
778  else xConvert2CDB_Numeric((CDB_Numeric*)item_buf, v);
779  break;
780  }
781  case eDB_BigInt: {
782  SQLBIGINT v;
783  outlen = xGetData(SQL_C_SBIGINT, &v, sizeof(SQLBIGINT));
784  if (outlen <= 0) item_buf->AssignNULL();
785  else *((CDB_BigInt*) item_buf) = (Int8) v;
786  break;
787  }
788  default:
789  {
790  string err_message = wrong_type + GetDbgInfo();
791  DATABASE_DRIVER_ERROR( err_message, 430020 );
792  }
793  }
794  break;
795  }
796 
797  case SQL_WLONGVARCHAR:
798  switch(item_buf->GetType()) {
799 #ifdef HAVE_WSTRING
800  case eDB_Text: {
801  if (policy == I_Result::eAssignLOB) {
802  static_cast<CDB_Stream*>(item_buf)->Truncate();
803  }
804 
805  while (CheckSIENoD_WText((CDB_Stream*)item_buf)) {
806  continue;
807  }
808  break;
809  }
810 #endif
811  case eDB_Image: {
812  if (policy == I_Result::eAssignLOB) {
813  static_cast<CDB_Stream*>(item_buf)->Truncate();
814  }
815 
816  while (CheckSIENoD_Binary((CDB_Stream*)item_buf)) {
817  continue;
818  }
819  break;
820  }
821  default:
822  {
823  string err_message = wrong_type + GetDbgInfo();
824  DATABASE_DRIVER_ERROR( err_message, 430020 );
825  }
826  }
827  break;
828  case SQL_LONGVARBINARY:
829  case SQL_LONGVARCHAR:
830  switch(item_buf->GetType()) {
831  case eDB_Text:
832  case eDB_VarCharMax: {
833  if (policy == I_Result::eAssignLOB) {
834  static_cast<CDB_Stream*>(item_buf)->Truncate();
835  }
836 
837  while (CheckSIENoD_Text((CDB_Stream*)item_buf)) {
838  continue;
839  }
840  break;
841  }
842  case eDB_Image:
843  case eDB_VarBinaryMax: {
844  if (policy == I_Result::eAssignLOB) {
845  static_cast<CDB_Stream*>(item_buf)->Truncate();
846  }
847 
848  while (CheckSIENoD_Binary((CDB_Stream*)item_buf)) {
849  continue;
850  }
851  break;
852  }
853  default:
854  {
855  string err_message = wrong_type + GetDbgInfo();
856  DATABASE_DRIVER_ERROR( err_message, 430020 );
857  }
858  }
859  break;
860  default:
861  {
862  string err_message = "Unsupported column type." + GetDbgInfo();
863  DATABASE_DRIVER_ERROR( err_message, 430025 );
864  }
865 
866  }
867  return item_buf;
868 }
869 
871 {
872  char base_buf[8*1024];
873  TItemBuffer buffer(base_buf, eNoOwnership);
874  ssize_t outlen;
875 
876  switch(m_ColFmt[m_CurrItem].DataType) {
877  case SQL_WCHAR:
878  case SQL_WVARCHAR:
879 #ifdef HAVE_WSTRING
880  {
881  outlen = x_GetVarLenData(SQL_C_WCHAR, buffer, sizeof(base_buf));
882  CODBCString odbc_str(reinterpret_cast<wchar_t*>(buffer.get()), outlen);
883 
884  if(m_ColFmt[m_CurrItem].ColumnSize < 256) {
885  CDB_VarChar* val = (outlen < 0)
886  ? new CDB_VarChar() : new CDB_VarChar(odbc_str.ConvertTo(GetClientEncoding()));
887 
888  return val;
889  }
890  else {
891  CDB_LongChar* val = (outlen < 0)
892  ? new CDB_LongChar(m_ColFmt[m_CurrItem].ColumnSize) :
893  new CDB_LongChar(m_ColFmt[m_CurrItem].ColumnSize,
894  odbc_str.ConvertTo(GetClientEncoding()));
895 
896  return val;
897  }
898  }
899 #endif
900 
901  case SQL_VARCHAR:
902  case SQL_CHAR: {
903  outlen = x_GetVarLenData(SQL_C_CHAR, buffer, sizeof(base_buf));
904  if(m_ColFmt[m_CurrItem].ColumnSize < 256) {
905  CDB_VarChar* val = (outlen < 0)
906  ? new CDB_VarChar() : new CDB_VarChar(buffer.get(),
907  (size_t) outlen);
908 
909  return val;
910  }
911  else {
912  CDB_LongChar* val = (outlen < 0)
913  ? new CDB_LongChar(m_ColFmt[m_CurrItem].ColumnSize) :
914  new CDB_LongChar(m_ColFmt[m_CurrItem].ColumnSize,
915  buffer.get());
916 
917  return val;
918  }
919  }
920 
921  case SQL_BINARY:
922  case SQL_VARBINARY: {
923  outlen = x_GetVarLenData(SQL_C_BINARY, buffer, sizeof(base_buf));
924  if(m_ColFmt[m_CurrItem].ColumnSize < 256) {
925  CDB_VarBinary* val = (outlen <= 0)
926  ? new CDB_VarBinary() : new CDB_VarBinary(buffer.get(),
927  (size_t)outlen);
928 
929  return val;
930  }
931  else {
932  CDB_LongBinary* val = (outlen < 0)
933  ? new CDB_LongBinary(m_ColFmt[m_CurrItem].ColumnSize) :
934  new CDB_LongBinary(m_ColFmt[m_CurrItem].ColumnSize,
935  buffer.get(), (size_t) outlen);
936 
937  return val;
938  }
939  }
940 
941  case SQL_BIT: {
942  SQLCHAR v;
943  outlen = xGetData(SQL_C_BIT, &v, sizeof(SQLCHAR));
944  return (outlen <= 0) ? new CDB_Bit() : new CDB_Bit((int) v);
945  }
946 
947  case SQL_TYPE_TIMESTAMP: {
949  outlen = xGetData(SQL_C_TYPE_TIMESTAMP, &v, sizeof(SQL_TIMESTAMP_STRUCT));
951  m_ColFmt[m_CurrItem].DecimalDigits,
952  m_ColFmt[m_CurrItem].ColumnSize);
953  if (outlen <= 0) {
954  return CDB_Object::Create(type);
955  } else {
956  CTime t((int)v.year, (int)v.month, (int)v.day,
957  (int)v.hour, (int)v.minute, (int)v.second,
958  (long)v.fraction);
959  switch (type) {
960  case eDB_SmallDateTime: return new CDB_SmallDateTime(t);
961  case eDB_DateTime: return new CDB_DateTime(t);
962  case eDB_BigDateTime: return new CDB_BigDateTime(t);
963  default: _TROUBLE;
964  }
965  }
966  }
967 
968  case SQL_TINYINT: {
969  SQLCHAR v;
970  outlen = xGetData(SQL_C_UTINYINT, &v, sizeof(SQLCHAR));
971  return (outlen <= 0) ? new CDB_TinyInt() : new CDB_TinyInt((Uint1) v);
972  }
973 
974  case SQL_SMALLINT: {
975  SQLSMALLINT v;
976  outlen = xGetData(SQL_C_SSHORT, &v, sizeof(SQLSMALLINT));
977  return (outlen <= 0) ? new CDB_SmallInt() : new CDB_SmallInt((Int2) v);
978  }
979 
980  case SQL_INTEGER: {
981  SQLINTEGER v;
982  outlen = xGetData(SQL_C_SLONG, &v, sizeof(SQLINTEGER));
983  return (outlen <= 0) ? new CDB_Int() : new CDB_Int((Int4) v);
984  }
985 
986  case SQL_DOUBLE:
987  case SQL_FLOAT: {
988  SQLDOUBLE v;
989  outlen = xGetData(SQL_C_DOUBLE, &v, sizeof(SQLDOUBLE));
990  return (outlen <= 0) ? new CDB_Double() : new CDB_Double(v);
991  }
992  case SQL_REAL: {
993  SQLREAL v;
994  outlen = xGetData(SQL_C_FLOAT, &v, sizeof(SQLREAL));
995  return (outlen <= 0) ? new CDB_Float() : new CDB_Float(v);
996  }
997 
998  case SQL_DECIMAL:
999  case SQL_NUMERIC: {
1000  if((m_ColFmt[m_CurrItem].DecimalDigits > 0) ||
1001  (m_ColFmt[m_CurrItem].ColumnSize > 20)) { // It should be numeric
1003  outlen = xGetData(SQL_C_NUMERIC, &v, sizeof(SQL_NUMERIC_STRUCT));
1004  CDB_Numeric* r= new CDB_Numeric;
1005  if(outlen > 0) {
1006  xConvert2CDB_Numeric(r, v);
1007  }
1008  return r;
1009  }
1010  else { // It should be bigint
1011  SQLBIGINT v;
1012  outlen = xGetData(SQL_C_SBIGINT, &v, sizeof(SQLBIGINT));
1013  return (outlen <= 0) ? new CDB_BigInt() : new CDB_BigInt((Int8) v);
1014  }
1015  }
1016 
1017  case SQL_WLONGVARCHAR:
1018 #ifdef HAVE_WSTRING
1019  {
1020  CDB_Text* val = new CDB_Text;
1021 
1022  // Code below looks strange, but it completely matches original logic.
1023  for(;;) {
1025  }
1026  return val;
1027  }
1028 #endif
1029 
1030  case SQL_LONGVARCHAR: {
1031  CDB_Text* val = new CDB_Text;
1032 
1033  // Code below looks strange, but it completely matches original logic.
1034  for(;;) {
1036  }
1037  return val;
1038  }
1039 
1040  case SQL_LONGVARBINARY: {
1041  CDB_Image* val = new CDB_Image;
1042 
1043  // Code below looks strange, but it completely matches original logic.
1044  for(;;) {
1046  }
1047  return val;
1048  }
1049  default:
1050  {
1051  string err_message = "Unsupported column type." + GetDbgInfo();
1052  DATABASE_DRIVER_ERROR( err_message, 430025 );
1053  }
1054 
1055  }
1056 }
1057 
1058 
1060 {
1061  if ((unsigned int) m_CurrItem >= GetDefineParams().GetNum() || m_CurrItem == -1) {
1062  return 0;
1063  }
1064 
1065  CDB_Object* item = item_buf? x_LoadItem(policy, item_buf) : x_MakeItem();
1066 
1067  ++m_CurrItem;
1068  return item;
1069 }
1070 
1071 
1072 size_t CODBC_RowResult::ReadItem(void* buffer,size_t buffer_size,bool* is_null)
1073 {
1074  if ((unsigned int) m_CurrItem >= GetDefineParams().GetNum() || m_CurrItem == -1 ||
1075  buffer == 0 || buffer_size == 0) {
1076  return 0;
1077  }
1078 
1079  SQLLEN f = 0;
1080 
1081  if(is_null) *is_null= false;
1082 
1083  SQLSMALLINT data_type = m_ColFmt[m_CurrItem].DataType;
1084 
1085  while (m_HasMoreData && m_LastReadData.size() < buffer_size) {
1086  m_HasMoreData = false;
1087 
1088  string next_data;
1089  size_t next_len = 0;
1090 
1092  case SQL_SUCCESS_WITH_INFO:
1093  switch(f) {
1094  case SQL_NO_TOTAL:
1095  next_data.append((char*) buffer, buffer_size);
1096  m_HasMoreData = true;
1097  break;
1098  case SQL_NULL_DATA:
1099  if(is_null) *is_null= true;
1100  break;
1101  default:
1102  if ( f < 0 ) {
1103  ReportErrors();
1104  return 0;
1105  }
1106  m_HasMoreData = true;
1107  next_len = static_cast<size_t>(f);
1108  if (next_len >= buffer_size) {
1109  next_len = buffer_size;
1110  }
1111  next_data.append((char*) buffer, next_len);
1112  break;
1113  }
1114  break;
1115  case SQL_SUCCESS:
1116  if(f == SQL_NULL_DATA) {
1117  if(is_null) *is_null= true;
1118  }
1119  else {
1120  next_len = (f >= 0)? ((size_t)f) : 0;
1121  next_data.append((char*) buffer, next_len);
1122  }
1123  break;
1124  case SQL_NO_DATA:
1125  if(f == SQL_NULL_DATA) {
1126  if(is_null) *is_null= true;
1127  }
1128  break;
1129  case SQL_ERROR:
1130  ReportErrors();
1131  return 0;
1132  default:
1133  {
1134  string err_message = "SQLGetData failed." + GetDbgInfo();
1135  DATABASE_DRIVER_ERROR( err_message, 430026 );
1136  }
1137  }
1138 
1139 #ifdef HAVE_WSTRING
1140  if (data_type == SQL_WCHAR || data_type == SQL_WVARCHAR || data_type == SQL_WLONGVARCHAR) {
1141  string conv_data
1142  = (CODBCString((wchar_t*) next_data.data(),
1143  next_data.size() / sizeof(wchar_t))
1145  m_LastReadData += conv_data;
1146  }
1147  else
1148 #endif
1149  {
1150  m_LastReadData += next_data;
1151  }
1152  }
1153 
1154  size_t return_len = m_LastReadData.size();
1155  if (return_len > buffer_size) {
1156  return_len = buffer_size;
1157  }
1158  memcpy(buffer, m_LastReadData.data(), return_len);
1159  m_LastReadData = m_LastReadData.substr(return_len);
1160  if (!m_HasMoreData && return_len <= buffer_size) {
1161  ++m_CurrItem;
1162  m_HasMoreData = true;
1163  }
1164 
1165  return return_len;
1166 }
1167 
1168 
1170  const string& cond)
1171 {
1172  enum {eNameStrLen = 128};
1173  SQLSMALLINT slp;
1174 
1175  odbc::TSqlChar buffer[eNameStrLen];
1176 
1177  switch(SQLColAttribute(GetHandle(), item_no + 1,
1179  (SQLPOINTER)buffer, sizeof(buffer),
1180  &slp, 0)) {
1181  case SQL_SUCCESS_WITH_INFO:
1182  ReportErrors();
1183  case SQL_SUCCESS:
1184  break;
1185  case SQL_ERROR:
1186  ReportErrors();
1187  return 0;
1188  default:
1189  {
1190  string err_message = "SQLColAttribute failed." + GetDbgInfo();
1191  DATABASE_DRIVER_ERROR( err_message, 430027 );
1192  }
1193  }
1194 
1195  string base_table = CODBCString(buffer, GetClientEncoding()).ConvertTo(GetClientEncoding());
1196 
1197  switch(SQLColAttribute(GetHandle(), item_no + 1,
1199  (SQLPOINTER)buffer, sizeof(buffer),
1200  &slp, 0)) {
1201  case SQL_SUCCESS_WITH_INFO:
1202  ReportErrors();
1203  case SQL_SUCCESS:
1204  break;
1205  case SQL_ERROR:
1206  ReportErrors();
1207  return 0;
1208  default:
1209  {
1210  string err_message = "SQLColAttribute failed." + GetDbgInfo();
1211  DATABASE_DRIVER_ERROR( err_message, 430027 );
1212  }
1213  }
1214 
1215  string base_column = CODBCString(buffer, GetClientEncoding()).ConvertTo(GetClientEncoding());
1216 
1217  SQLLEN column_type = 0;
1218  switch(SQLColAttribute(GetHandle(), item_no + 1,
1220  NULL, sizeof(column_type),
1221  &slp, &column_type)) {
1222  case SQL_SUCCESS_WITH_INFO:
1223  ReportErrors();
1224  case SQL_SUCCESS:
1225  break;
1226  case SQL_ERROR:
1227  ReportErrors();
1228  return 0;
1229  default:
1230  {
1231  string err_message = "SQLColAttribute failed." + GetDbgInfo();
1232  DATABASE_DRIVER_ERROR( err_message, 430027 );
1233  }
1234  }
1235 
1237  switch (column_type) {
1238  case SQL_BINARY:
1239  case SQL_VARBINARY:
1240  case SQL_LONGVARBINARY:
1242  break;
1243  case SQL_LONGVARCHAR:
1245  break;
1246  };
1247 
1248  return new CDB_BlobDescriptor(base_table, base_column, cond, type);
1249 }
1250 
1252 {
1253  return (I_BlobDescriptor*) GetBlobDescriptor(m_CurrItem, "don't use me");
1254 }
1255 
1257 {
1258  if ((unsigned int) m_CurrItem < GetDefineParams().GetNum()) {
1259  ++m_CurrItem;
1260  return true;
1261  }
1262  return false;
1263 }
1264 
1265 
1267 {
1268  try {
1269  if (m_ColFmt) {
1270  delete[] m_ColFmt;
1271  m_ColFmt = 0;
1272  }
1273  if (!m_EOR) {
1274  Close();
1275  }
1276  }
1278 }
1279 
1280 
1281 /////////////////////////////////////////////////////////////////////////////
1282 //
1283 // CTL_ParamResult::
1284 // CTL_StatusResult::
1285 // CTL_CursorResult::
1286 //
1287 
1289 : CODBC_RowResult(stmt, 1, NULL)
1290 {
1291 }
1292 
1294 {
1295 }
1296 
1298 {
1299  return eDB_StatusResult;
1300 }
1301 
1302 /////////////////////////////////////////////////////////////////////////////
1305  SQLSMALLINT nof_cols)
1306 : CODBC_RowResult(stmt, nof_cols, NULL)
1307 {
1308 }
1309 
1311 {
1312 }
1313 
1315 {
1316  return eDB_ParamResult;
1317 }
1318 
1319 
1320 /////////////////////////////////////////////////////////////////////////////
1321 //
1322 // CODBC_CursorResult::
1323 //
1324 
1326 : m_Cmd(cmd)
1327 , m_Res(NULL)
1328 , m_EOR(false)
1329 {
1330  try {
1331  m_Cmd->Send();
1332  m_EOR = true;
1333 
1334  while (m_Cmd->HasMoreResults()) {
1335  m_Res = m_Cmd->Result();
1336 
1337  if (m_Res && m_Res->ResultType() == eDB_RowResult) {
1338  m_EOR = false;
1339  return;
1340  }
1341 
1342  if (m_Res) {
1343  while (m_Res->Fetch())
1344  ;
1345  delete m_Res;
1346  m_Res = 0;
1347  }
1348  }
1349  } catch (const CDB_Exception& e) {
1350  string err_message = "Failed to get the results." + GetDbgInfo();
1351  DATABASE_DRIVER_ERROR_EX( e, err_message, 422010 );
1352  }
1353 }
1354 
1355 
1357 {
1358  return eDB_CursorResult;
1359 }
1360 
1361 
1363 {
1364  _ASSERT(m_Res);
1365  return m_Res->GetDefineParams();
1366 }
1367 
1368 
1370 {
1371 
1372  if( m_EOR ) {
1373  return false;
1374  }
1375 
1376  try {
1377  if (m_Res && m_Res->Fetch()) {
1378  return true;
1379  }
1380  } catch ( const CDB_Exception& ) {
1381  delete m_Res;
1382  m_Res = 0;
1383  }
1384 
1385  try {
1386  // finish this command
1387  m_EOR = true;
1388  if( m_Res ) {
1389  delete m_Res;
1390  m_Res = 0;
1391  while (m_Cmd->HasMoreResults()) {
1392  m_Res = m_Cmd->Result();
1393  if (m_Res) {
1394  while (m_Res->Fetch()) {
1395  continue;
1396  }
1397  delete m_Res;
1398  m_Res = 0;
1399  }
1400  }
1401  }
1402  } catch (const CDB_Exception& e) {
1403  string err_message = "Failed to fetch the results." + GetDbgInfo();
1404  DATABASE_DRIVER_ERROR_EX( e, err_message, 422011 );
1405  }
1406  return false;
1407 }
1408 
1409 
1411 {
1412  return m_Res ? m_Res->CurrentItemNo() : -1;
1413 }
1414 
1415 
1417 {
1418  return m_Res ? m_Res->GetColumnNum() : -1;
1419 }
1420 
1421 
1423 {
1424  return m_Res ? m_Res->GetItem(item_buff, policy) : 0;
1425 }
1426 
1427 
1429  bool* is_null)
1430 {
1431  if (m_Res) {
1432  return m_Res->ReadItem(buffer, buffer_size, is_null);
1433  }
1434  if (is_null)
1435  *is_null = true;
1436  return 0;
1437 }
1438 
1439 
1441 {
1442  return m_Res ? m_Res->GetBlobDescriptor() : 0;
1443 }
1444 
1445 
1447 {
1448  return m_Res ? m_Res->SkipItem() : false;
1449 }
1450 
1451 
1453 {
1454  try {
1455  if (m_Res) {
1456  delete m_Res;
1457  m_Res = 0;
1458  }
1459  }
1461 }
1462 
1463 
1464 ///////////////////////////////////////////////////////////////////////////////
1467 {
1468 }
1469 
1471 {
1472 }
1473 
1474 
1476 {
1477 
1478  if( m_EOR ) {
1479  return false;
1480  }
1481 
1482  try {
1483  if (m_Res && m_Res->Fetch()) {
1484  return true;
1485  }
1486  } catch ( const CDB_Exception& ) {
1487  delete m_Res;
1488  m_Res = 0;
1489  }
1490 
1491  try {
1492  // finish this command
1493  m_EOR = true;
1494  if( m_Res ) {
1495  delete m_Res;
1496  m_Res = 0;
1497  while (m_Cmd->HasMoreResults()) {
1498  m_Res = m_Cmd->Result();
1499  if (m_Res) {
1500  while (m_Res->Fetch()) {
1501  continue;
1502  }
1503  delete m_Res;
1504  m_Res = 0;
1505  }
1506  }
1507  }
1508 
1509  // send the another "fetch cursor_name" command
1510  m_Cmd->Send();
1511  while (m_Cmd->HasMoreResults()) {
1512  m_Res = m_Cmd->Result();
1513  if (m_Res && m_Res->ResultType() == eDB_RowResult) {
1514  m_EOR = false;
1515  return m_Res->Fetch();
1516  }
1517  if ( m_Res ) {
1518  while (m_Res->Fetch()) {
1519  continue;
1520  }
1521  delete m_Res;
1522  m_Res = 0;
1523  }
1524  }
1525  } catch (const CDB_Exception& e) {
1526  string err_message = "Failed to fetch the results." + GetDbgInfo();
1527  DATABASE_DRIVER_ERROR_EX( e, err_message, 422011 );
1528  }
1529  return false;
1530 }
1531 
1532 
1534 
1535 
#define false
Definition: bool.h:36
CDBParams.
Definition: interfaces.hpp:154
CDB_Exception –.
Definition: exception.hpp:118
virtual ~CODBC_CursorResultExpl(void)
Definition: result.cpp:1470
virtual bool Fetch(void)
Fetch next row.
Definition: result.cpp:1475
CODBC_CursorResultExpl(CODBC_LangCmd *cmd)
Definition: result.cpp:1465
virtual I_BlobDescriptor * GetBlobDescriptor(void)
Get a descriptor for a BLOB column (for SendData).
Definition: result.cpp:1440
virtual int CurrentItemNo(void) const
Return current item number we can retrieve (0,1,...) Return "-1" if no more items left (or available)...
Definition: result.cpp:1410
virtual bool SkipItem(void)
Skip result item.
Definition: result.cpp:1446
virtual bool Fetch(void)
Fetch next row.
Definition: result.cpp:1369
virtual ~CODBC_CursorResult(void)
Definition: result.cpp:1452
CDB_Result * m_Res
Definition: interfaces.hpp:929
CODBC_LangCmd * m_Cmd
Definition: interfaces.hpp:928
virtual EDB_ResType ResultType(void) const
Get type of the result.
Definition: result.cpp:1356
virtual const CDBParams & GetDefineParams(void) const
Definition: result.cpp:1362
const CODBC_Connection::TDbgInfo & GetDbgInfo(void) const
Definition: interfaces.hpp:900
virtual int GetColumnNum(void) const
Return number of columns in the recordset.
Definition: result.cpp:1416
CODBC_CursorResult(CODBC_LangCmd *cmd)
Definition: result.cpp:1325
virtual CDB_Object * GetItem(CDB_Object *item_buff=0, I_Result::EGetItem policy=I_Result::eAppendLOB)
Get a result item (you can use either GetItem or ReadItem).
Definition: result.cpp:1422
virtual size_t ReadItem(void *buffer, size_t buffer_size, bool *is_null=0)
Read a result item body (for BLOB columns, mostly).
Definition: result.cpp:1428
virtual bool HasMoreResults(void) const
Definition: lang_cmd.cpp:236
virtual CDB_Result * Result(void)
Get result set.
Definition: lang_cmd.cpp:192
virtual bool Send(void)
Send command to the server.
Definition: lang_cmd.cpp:80
virtual EDB_ResType ResultType(void) const
Get type of the result.
Definition: result.cpp:1314
CODBC_ParamResult(CStatementBase &stmt, SQLSMALLINT nof_cols)
Definition: result.cpp:1303
virtual ~CODBC_ParamResult(void)
Definition: result.cpp:1310
virtual ~CODBC_RowResult(void)
Definition: result.cpp:1266
SQLLEN *const m_RowCountPtr
Definition: interfaces.hpp:833
int xGetData(SQLSMALLINT target_type, SQLPOINTER buffer, SQLINTEGER buffer_size, bool *more=NULL)
Definition: result.cpp:221
const CODBC_Connection::TDbgInfo & GetDbgInfo(void) const
Definition: interfaces.hpp:795
virtual EDB_ResType ResultType(void) const
Get type of the result.
Definition: result.cpp:169
SQLHSTMT GetHandle(void) const
Definition: interfaces.hpp:780
CDB_Object * x_LoadItem(I_Result::EGetItem policy, CDB_Object *item_buf)
Definition: result.cpp:448
bool CheckSIENoD_Binary(CDB_Stream *val)
Definition: result.cpp:417
virtual bool SkipItem(void)
Skip result item.
Definition: result.cpp:1256
virtual int GetColumnNum(void) const
Return number of columns in the recordset.
Definition: result.cpp:216
ssize_t x_GetVarLenData(SQLSMALLINT target_type, TItemBuffer &buffer, SQLINTEGER buffer_size)
Definition: result.cpp:263
virtual bool Fetch(void)
Fetch next row.
Definition: result.cpp:175
virtual size_t ReadItem(void *buffer, size_t buffer_size, bool *is_null=0)
Read a result item body (for BLOB columns, mostly).
Definition: result.cpp:1072
EEncoding GetClientEncoding(void) const
Definition: interfaces.hpp:744
virtual CDB_Object * GetItem(CDB_Object *item_buf=0, I_Result::EGetItem policy=I_Result::eAppendLOB)
Get a result item (you can use either GetItem or ReadItem).
Definition: result.cpp:1059
virtual I_BlobDescriptor * GetBlobDescriptor(void)
Get a descriptor for a BLOB column (for SendData).
Definition: result.cpp:1251
void Close(void)
Definition: interfaces.hpp:808
virtual int CurrentItemNo(void) const
Return current item number we can retrieve (0,1,...) Return "-1" if no more items left (or available)...
Definition: result.cpp:211
CODBC_RowResult(CStatementBase &stmt, SQLSMALLINT nof_cols, SQLLEN *row_count)
Definition: result.cpp:108
bool CheckSIENoD_WText(CDB_Stream *val)
Definition: result.cpp:372
bool CheckSIENoD_Text(CDB_Stream *val)
Definition: result.cpp:330
CDB_Object * x_MakeItem(void)
Definition: result.cpp:870
void ReportErrors(void)
Definition: interfaces.hpp:784
string m_LastReadData
Definition: interfaces.hpp:835
SODBC_ColDescr * m_ColFmt
Definition: interfaces.hpp:832
virtual ~CODBC_StatusResult(void)
Definition: result.cpp:1293
virtual EDB_ResType ResultType(void) const
Get type of the result.
Definition: result.cpp:1297
CODBC_StatusResult(CStatementBase &stmt)
Definition: result.cpp:1288
CTime –.
Definition: ncbitime.hpp:296
I_BlobDescriptor::
Definition: interfaces.hpp:369
void Add(const string &name, size_t max_size, EDB_Type data_type=eDB_UnsupportedType, EDirection direction=eOut) const
virtual const CDBParams & GetDefineParams(void) const
CCachedRowInfo m_CachedRowInfo
static CS_COMMAND * cmd
Definition: ct_dynamic.c:26
SQLCHAR TSqlChar
Definition: interfaces.hpp:76
@ eNoOwnership
No ownership is assumed.
Definition: ncbi_types.h:135
#define NULL
Definition: ncbistd.hpp:225
#define DATABASE_DRIVER_ERROR(message, err_code)
Definition: exception.hpp:740
#define DATABASE_DRIVER_ERROR_EX(prev_exception, message, err_code)
Definition: exception.hpp:742
virtual unsigned int GetNum(void) const =0
Get total number of columns in resultset.
EDB_ResType
EDB_ResType::
Definition: interfaces.hpp:386
@ eDB_CursorResult
Definition: interfaces.hpp:391
@ eDB_ParamResult
Definition: interfaces.hpp:388
@ eDB_StatusResult
Definition: interfaces.hpp:390
@ eDB_RowResult
Definition: interfaces.hpp:387
virtual EDB_ResType ResultType() const
Get type of the result.
Definition: public.cpp:603
virtual int GetColumnNum(void) const
Return number of columns in the recordset.
Definition: public.cpp:666
virtual int CurrentItemNo() const
Return current item number we can retrieve (0,1,...)
Definition: public.cpp:660
virtual bool SkipItem()
Skip result item.
Definition: public.cpp:690
virtual size_t ReadItem(void *buffer, size_t buffer_size, bool *is_null=0)
Read a result item body (for BLOB columns, mostly).
Definition: public.cpp:678
virtual CDB_Object * GetItem(CDB_Object *item_buf=0, EGetItem policy=eAppendLOB)
Get a result item (you can use either GetItem or ReadItem).
Definition: public.cpp:672
virtual I_BlobDescriptor * GetBlobDescriptor()
Get a descriptor for a BLOB column (for SendData).
Definition: public.cpp:684
virtual const CDBParams & GetDefineParams(void) const
Get meta-information about rows in resultset.
Definition: public.cpp:610
virtual bool Fetch()
Fetch next row.
Definition: public.cpp:649
EDB_Type
Definition: types.hpp:52
virtual void AssignNULL()
Definition: types.cpp:550
const string & ConvertTo(EEncoding to_enc, EEncoding from_enc=eEncoding_Unknown) const
Definition: types.hpp:223
CDB_Numeric & Assign(unsigned int precision, unsigned int scale, const unsigned char *arr)
Definition: types.cpp:2839
static CDB_Object * Create(EDB_Type type, size_t size=1)
Definition: types.cpp:556
virtual EDB_Type GetType() const =0
static const char * GetTypeName(EDB_Type db_type, bool throw_on_unknown=true)
Definition: types.cpp:586
@ eDB_Bit
Definition: types.hpp:68
@ eDB_Char
Definition: types.hpp:58
@ eDB_UnsupportedType
Definition: types.hpp:75
@ eDB_SmallDateTime
Definition: types.hpp:65
@ eDB_VarChar
Definition: types.hpp:57
@ eDB_TinyInt
Definition: types.hpp:55
@ eDB_LongChar
Definition: types.hpp:70
@ eDB_Double
Definition: types.hpp:62
@ eDB_Image
Definition: types.hpp:67
@ eDB_Float
Definition: types.hpp:61
@ eDB_Int
Definition: types.hpp:53
@ eDB_VarCharMax
Definition: types.hpp:72
@ eDB_Numeric
Definition: types.hpp:69
@ eDB_BigInt
Definition: types.hpp:56
@ eDB_BigDateTime
Definition: types.hpp:64
@ eDB_Binary
Definition: types.hpp:60
@ eDB_Text
Definition: types.hpp:66
@ eDB_SmallInt
Definition: types.hpp:54
@ eDB_DateTime
Definition: types.hpp:63
@ eDB_LongBinary
Definition: types.hpp:71
@ eDB_VarBinary
Definition: types.hpp:59
@ eDB_VarBinaryMax
Definition: types.hpp:73
#define NCBI_CURRENT_FUNCTION
Get current function name.
Definition: ncbidiag.hpp:142
#define NCBI_CATCH_ALL_X(err_subcode, message)
Definition: ncbiexpt.hpp:619
uint8_t Uint1
1-byte (8-bit) unsigned integer
Definition: ncbitype.h:99
int16_t Int2
2-byte (16-bit) signed integer
Definition: ncbitype.h:100
int32_t Int4
4-byte (32-bit) signed integer
Definition: ncbitype.h:102
int64_t Int8
8-byte (64-bit) signed integer
Definition: ncbitype.h:104
#define END_NCBI_SCOPE
End previously defined NCBI scope.
Definition: ncbistl.hpp:103
#define BEGIN_NCBI_SCOPE
Define ncbi namespace.
Definition: ncbistl.hpp:100
CTime Truncate(const CTime &t)
Definition: ncbitime.hpp:2195
unsigned int
A callback function used to compare two keys in a database.
Definition: types.hpp:1210
Definition of all error codes used in dbapi libraries (dbapi_driver.lib and others).
int i
yy_size_t n
EIPRangeType t
Definition: ncbi_localip.c:101
int ssize_t
Definition: ncbiconf_msvc.h:92
double r(size_t dimension_, const Int4 *score_, const double *prob_, double theta_)
double f(double x_, const double &y_)
Definition: njn_root.hpp:188
void swap_numeric_endian(unsigned int precision, unsigned char *num)
static EDB_Type s_GetDataType(SQLSMALLINT t, SQLSMALLINT dec_digits, SQLULEN prec)
Definition: result.cpp:65
static void xConvert2CDB_Numeric(CDB_Numeric *d, SQL_NUMERIC_STRUCT &s)
Definition: result.cpp:323
static const char * wrong_type
Definition: result.cpp:61
#define SQLULEN
Definition: odbc.h:49
#define SQLLEN
Definition: odbc.h:52
static pcre_uint8 * buffer
Definition: pcretest.c:1051
static int buffer_size
Definition: pcretest.c:1050
static HSTMT stmt
Definition: rebindpar.c:12
#define SQL_ATTR_APP_ROW_DESC
Definition: sql.h:83
#define SQL_REAL
Definition: sql.h:173
#define SQL_FLOAT
Definition: sql.h:172
SQLRETURN SQLFetch(SQLHSTMT StatementHandle)
Definition: odbc.c:3997
#define SQL_CHAR
Definition: sql.h:167
#define SQL_SUCCESS
Definition: sql.h:31
#define SQL_TYPE_TIMESTAMP
Definition: sql.h:184
#define SQL_DESC_TYPE
Definition: sql.h:100
#define SQL_SMALLINT
Definition: sql.h:171
#define SQL_NUMERIC
Definition: sql.h:168
#define SQL_DESC_PRECISION
Definition: sql.h:103
#define SQL_DECIMAL
Definition: sql.h:169
#define SQL_INTEGER
Definition: sql.h:170
SQLRETURN SQLDescribeCol(SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLCHAR *ColumnName, SQLSMALLINT BufferLength, SQLSMALLINT *NameLength, SQLSMALLINT *DataType, SQLUINTEGER *ColumnSize, SQLSMALLINT *DecimalDigits, SQLSMALLINT *Nullable)
#define SQL_DESC_SCALE
Definition: sql.h:104
#define SQL_SUCCESS_WITH_INFO
Definition: sql.h:32
SQLRETURN SQLGetStmtAttr(SQLHSTMT StatementHandle, SQLINTEGER Attribute, SQLPOINTER Value, SQLINTEGER BufferLength, SQLINTEGER *StringLength)
SQLRETURN SQLGetData(SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLSMALLINT TargetType, SQLPOINTER TargetValue, SQLINTEGER BufferLength, SQLINTEGER *StrLen_or_Ind)
#define SQL_NULL_DATA
Definition: sql.h:29
#define SQL_DOUBLE
Definition: sql.h:174
#define SQL_VARCHAR
Definition: sql.h:178
SQLRETURN SQLColAttribute(SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber, SQLUSMALLINT FieldIdentifier, SQLPOINTER CharacterAttribute, SQLSMALLINT BufferLength, SQLSMALLINT *StringLength, SQLINTEGER *NumericAttribute)
SQLRETURN SQLSetDescField(SQLHDESC DescriptorHandle, SQLSMALLINT RecNumber, SQLSMALLINT FieldIdentifier, SQLPOINTER Value, SQLINTEGER BufferLength)
Definition: odbc_export.h:764
#define SQL_ERROR
Definition: sql.h:36
#define SQL_NO_DATA
Definition: sql.h:34
#define SQL_C_DOUBLE
Definition: sqlext.h:515
#define SQL_C_TYPE_TIMESTAMP
Definition: sqlext.h:531
#define SQL_LONGVARBINARY
Definition: sqlext.h:435
#define SQL_LONGVARCHAR
Definition: sqlext.h:432
#define SQL_C_SLONG
Definition: sqlext.h:553
#define SQL_C_BINARY
Definition: sqlext.h:546
#define SQL_DESC_BASE_COLUMN_NAME
Definition: sqlext.h:387
#define SQL_C_FLOAT
Definition: sqlext.h:514
#define SQL_TINYINT
Definition: sqlext.h:437
#define SQL_DESC_BASE_TABLE_NAME
Definition: sqlext.h:388
#define SQL_BINARY
Definition: sqlext.h:433
#define SQL_C_SSHORT
Definition: sqlext.h:554
#define SQL_VARBINARY
Definition: sqlext.h:434
#define SQL_C_BIT
Definition: sqlext.h:547
#define SQL_C_UTINYINT
Definition: sqlext.h:558
#define SQL_BIT
Definition: sqlext.h:438
#define SQL_NO_TOTAL
Definition: sqlext.h:671
#define SQL_C_SBIGINT
Definition: sqlext.h:549
#define SQL_C_NUMERIC
Definition: sqlext.h:517
#define SQL_COLUMN_TYPE
Definition: sqlext.h:632
#define SQL_BIGINT
Definition: sqlext.h:436
#define SQL_C_CHAR
Definition: sqlext.h:511
float SQLREAL
Definition: sqltypes.h:198
void * SQLPOINTER
Definition: sqltypes.h:195
double SQLDOUBLE
Definition: sqltypes.h:130
long SQLINTEGER
Definition: sqltypes.h:176
unsigned char SQLCHAR
Definition: sqltypes.h:125
signed short int SQLSMALLINT
Definition: sqltypes.h:201
SQLHANDLE SQLHDESC
Definition: sqltypes.h:217
#define SQL_WCHAR
Definition: sqlucode.h:14
#define SQL_WVARCHAR
Definition: sqlucode.h:15
#define SQL_C_WCHAR
Definition: sqlucode.h:17
#define SQL_WLONGVARCHAR
Definition: sqlucode.h:16
SQLCHAR val[16]
Definition: sqltypes.h:428
SQLUSMALLINT hour
Definition: sqltypes.h:309
SQLUINTEGER fraction
Definition: sqltypes.h:312
SQLUSMALLINT second
Definition: sqltypes.h:311
SQLSMALLINT year
Definition: sqltypes.h:306
SQLUSMALLINT month
Definition: sqltypes.h:307
SQLUSMALLINT day
Definition: sqltypes.h:308
SQLUSMALLINT minute
Definition: sqltypes.h:310
Definition: type.c:6
#define _TROUBLE
#define _ASSERT
Modified on Sat Dec 02 09:19:40 2023 by modify_doxy.py rev. 669887