OdbcData.cpp
上传用户:romrleung
上传日期:2022-05-23
资源大小:18897k
文件大小:11k
源码类别:

MySQL数据库

开发平台:

Visual C++

  1. /* Copyright (C) 2003 MySQL AB
  2.    This program is free software; you can redistribute it and/or modify
  3.    it under the terms of the GNU General Public License as published by
  4.    the Free Software Foundation; either version 2 of the License, or
  5.    (at your option) any later version.
  6.    This program is distributed in the hope that it will be useful,
  7.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  8.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  9.    GNU General Public License for more details.
  10.    You should have received a copy of the GNU General Public License
  11.    along with this program; if not, write to the Free Software
  12.    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
  13. #include "OdbcData.hpp"
  14. OdbcData::OdbcData() :
  15.     m_type(Undef)
  16. {
  17. }
  18. OdbcData::OdbcData(Type type) :
  19.     m_type(type)
  20. {
  21.     switch (m_type) {
  22.     case Smallint:
  23. m_smallint = 0;
  24. break;
  25.     case Usmallint:
  26. m_usmallint = 0;
  27. break;
  28.     case Integer:
  29. m_integer = 0;
  30. break;
  31.     case Uinteger:
  32. m_uinteger = 0;
  33. break;
  34.     case Pointer:
  35. m_pointer = 0;
  36. break;
  37.     case SmallintPtr:
  38. m_smallintPtr = 0;
  39. break;
  40.     case UsmallintPtr:
  41. m_usmallintPtr = 0;
  42. break;
  43.     case IntegerPtr:
  44. m_integerPtr = 0;
  45. break;
  46.     case UintegerPtr:
  47. m_uintegerPtr = 0;
  48. break;
  49.     case PointerPtr:
  50. m_pointerPtr = 0;
  51. break;
  52.     case Sqlchar:
  53. m_sqlchar = 0;
  54. break;
  55.     case Sqlstate:
  56. m_sqlstate = 0;
  57. break;
  58.     default:
  59. ctx_assert(false);
  60. break;
  61.     };
  62. }
  63. OdbcData::OdbcData(const OdbcData& odbcData) :
  64.     m_type(odbcData.m_type)
  65. {
  66.     switch (m_type) {
  67.     case Smallint:
  68. m_smallint = odbcData.m_smallint;
  69. break;
  70.     case Usmallint:
  71. m_usmallint = odbcData.m_usmallint;
  72. break;
  73.     case Integer:
  74. m_integer = odbcData.m_integer;
  75. break;
  76.     case Uinteger:
  77. m_uinteger = odbcData.m_uinteger;
  78. break;
  79.     case Pointer:
  80. m_pointer = odbcData.m_pointer;
  81. break;
  82.     case SmallintPtr:
  83. m_smallintPtr = odbcData.m_smallintPtr;
  84. break;
  85.     case UsmallintPtr:
  86. m_usmallintPtr = odbcData.m_usmallintPtr;
  87. break;
  88.     case IntegerPtr:
  89. m_integerPtr = odbcData.m_integerPtr;
  90. break;
  91.     case UintegerPtr:
  92. m_uintegerPtr = odbcData.m_uintegerPtr;
  93. break;
  94.     case PointerPtr:
  95. m_pointerPtr = odbcData.m_pointerPtr;
  96. break;
  97.     case Sqlchar: {
  98. unsigned n = strlen(odbcData.m_sqlchar);
  99. m_sqlchar = new char[n + 1];
  100. memcpy(m_sqlchar, odbcData.m_sqlchar, n + 1);
  101. break;
  102. }
  103.     case Sqlstate:
  104. m_sqlstate = odbcData.m_sqlstate;
  105. break;
  106.     default:
  107. ctx_assert(false);
  108. break;
  109.     };
  110. }
  111. OdbcData::~OdbcData()
  112. {
  113.     switch (m_type) {
  114.     case Sqlchar:
  115. delete[] m_sqlchar;
  116. break;
  117.     default:
  118. break;
  119.     }
  120. }
  121. void
  122. OdbcData::setValue()
  123. {
  124.     m_type = Undef;
  125. }
  126. void
  127. OdbcData::setValue(Type type)
  128. {
  129.     if (m_type == Sqlchar) {
  130. delete[] m_sqlchar;
  131. m_sqlchar = 0;
  132.     }
  133.     switch (m_type) {
  134.     case Smallint:
  135. m_smallint = 0;
  136. break;
  137.     case Usmallint:
  138. m_usmallint = 0;
  139. break;
  140.     case Integer:
  141. m_integer = 0;
  142. break;
  143.     case Uinteger:
  144. m_uinteger = 0;
  145. break;
  146.     case Pointer:
  147. m_pointer = 0;
  148. break;
  149.     case SmallintPtr:
  150. m_smallintPtr = 0;
  151. break;
  152.     case UsmallintPtr:
  153. m_usmallintPtr = 0;
  154. break;
  155.     case IntegerPtr:
  156. m_integerPtr = 0;
  157. break;
  158.     case UintegerPtr:
  159. m_uintegerPtr = 0;
  160. break;
  161.     case PointerPtr:
  162. m_pointerPtr = 0;
  163. break;
  164.     case Sqlchar:
  165. m_sqlchar = 0;
  166. break;
  167.     case Sqlstate:
  168. m_sqlstate = 0;
  169. break;
  170.     default:
  171. ctx_assert(false);
  172. break;
  173.     };
  174. }
  175. void
  176. OdbcData::setValue(const OdbcData odbcData)
  177. {
  178.     if (m_type == Sqlchar) {
  179. delete[] m_sqlchar;
  180. m_sqlchar = 0;
  181.     }
  182.     m_type = odbcData.m_type;
  183.     switch (m_type) {
  184.     case Smallint:
  185. m_smallint = odbcData.m_smallint;
  186. break;
  187.     case Usmallint:
  188. m_usmallint = odbcData.m_usmallint;
  189. break;
  190.     case Integer:
  191. m_integer = odbcData.m_integer;
  192. break;
  193.     case Uinteger:
  194. m_uinteger = odbcData.m_uinteger;
  195. break;
  196.     case Pointer:
  197. m_pointer = odbcData.m_pointer;
  198. break;
  199.     case SmallintPtr:
  200. m_smallintPtr = odbcData.m_smallintPtr;
  201. break;
  202.     case UsmallintPtr:
  203. m_usmallintPtr = odbcData.m_usmallintPtr;
  204. break;
  205.     case IntegerPtr:
  206. m_integerPtr = odbcData.m_integerPtr;
  207. break;
  208.     case UintegerPtr:
  209. m_uintegerPtr = odbcData.m_uintegerPtr;
  210. break;
  211.     case PointerPtr:
  212. m_pointerPtr = odbcData.m_pointerPtr;
  213. break;
  214.     case Sqlchar: {
  215. unsigned n = strlen(odbcData.m_sqlchar);
  216. m_sqlchar = new char[n + 1];
  217. memcpy(m_sqlchar, odbcData.m_sqlchar, n + 1);
  218. break;
  219. }
  220.     case Sqlstate:
  221. m_sqlstate = odbcData.m_sqlstate;
  222. break;
  223.     default:
  224. ctx_assert(false);
  225. break;
  226.     };
  227. }
  228. // copy in from user buffer
  229. void
  230. OdbcData::copyin(Ctx& ctx, Type type, SQLPOINTER buf, SQLINTEGER length)
  231. {
  232.     if (m_type == Sqlchar) {
  233. delete[] m_sqlchar;
  234. m_sqlchar = 0;
  235.     }
  236.     m_type = type;
  237.     switch (m_type) {
  238.     case Smallint: {
  239. SQLSMALLINT val = 0;
  240. switch (length) {
  241. case 0:
  242. case SQL_IS_SMALLINT:
  243.     val = (SQLSMALLINT)(SQLINTEGER)buf;
  244.     break;
  245. case SQL_IS_USMALLINT:
  246.     val = (SQLUSMALLINT)(SQLUINTEGER)buf;
  247.     break;
  248. case SQL_IS_INTEGER:
  249.     val = (SQLINTEGER)buf;
  250.     break;
  251. case SQL_IS_UINTEGER:
  252.     val = (SQLUINTEGER)buf;
  253.     break;
  254. default:
  255.     ctx.pushStatus(Error::Gen, "smallint input - invalid length %d", (int)length);
  256.     return;
  257. }
  258. m_smallint = val;
  259. break;
  260. }
  261.     case Usmallint: {
  262. SQLUSMALLINT val = 0;
  263. switch (length) {
  264. case SQL_IS_SMALLINT:
  265.     val = (SQLSMALLINT)(SQLINTEGER)buf;
  266.     break;
  267. case 0:
  268. case SQL_IS_USMALLINT:
  269.     val = (SQLUSMALLINT)(SQLUINTEGER)buf;
  270.     break;
  271. case SQL_IS_INTEGER:
  272.     val = (SQLINTEGER)buf;
  273.     break;
  274. case SQL_IS_UINTEGER:
  275.     val = (SQLUINTEGER)buf;
  276.     break;
  277. default:
  278.     ctx.pushStatus(Error::Gen, "unsigned smallint input - invalid length %d", (int)length);
  279.     return;
  280. }
  281. m_usmallint = val;
  282. break;
  283. }
  284.     case Integer: {
  285. SQLINTEGER val = 0;
  286. switch (length) {
  287. case SQL_IS_SMALLINT:
  288.     val = (SQLSMALLINT)(SQLINTEGER)buf;
  289.     break;
  290. case SQL_IS_USMALLINT:
  291.     val = (SQLUSMALLINT)(SQLUINTEGER)buf;
  292.     break;
  293. case 0:
  294. case SQL_IS_INTEGER:
  295.     val = (SQLINTEGER)buf;
  296.     break;
  297. case SQL_IS_UINTEGER:
  298.     val = (SQLUINTEGER)buf;
  299.     break;
  300. default:
  301.     ctx.pushStatus(Error::Gen, "integer input - invalid length %d", (int)length);
  302.     return;
  303. }
  304. m_integer = val;
  305. break;
  306. }
  307.     case Uinteger: {
  308. SQLUINTEGER val = 0;
  309. switch (length) {
  310. case SQL_IS_SMALLINT:
  311.     val = (SQLSMALLINT)(SQLINTEGER)buf;
  312.     break;
  313. case SQL_IS_USMALLINT:
  314.     val = (SQLUSMALLINT)(SQLUINTEGER)buf;
  315.     break;
  316. case SQL_IS_INTEGER:
  317.     val = (SQLINTEGER)buf;
  318.     break;
  319. case 0:
  320. case SQL_IS_UINTEGER:
  321.     val = (SQLUINTEGER)buf;
  322.     break;
  323. default:
  324.     ctx.pushStatus(Error::Gen, "unsigned integer input - invalid length %d", (int)length);
  325.     return;
  326. }
  327. m_uinteger = val;
  328. break;
  329. }
  330.     case Pointer: {
  331. SQLPOINTER val = 0;
  332. switch (length) {
  333. case 0:
  334. case SQL_IS_POINTER:
  335.     val = (SQLPOINTER)buf;
  336.     break;
  337. default:
  338.     ctx.pushStatus(Error::Gen, "pointer input - invalid length %d", (int)length);
  339.     return;
  340. }
  341. m_pointer = val;
  342. break;
  343. }
  344.     case SmallintPtr: {
  345. SQLSMALLINT* val = 0;
  346. switch (length) {
  347. case 0:
  348. case SQL_IS_POINTER:
  349.     val = (SQLSMALLINT*)buf;
  350.     break;
  351. default:
  352.     ctx.pushStatus(Error::Gen, "smallint pointer input - invalid length %d", (int)length);
  353.     return;
  354. }
  355. m_smallintPtr = val;
  356. break;
  357. }
  358.     case UsmallintPtr: {
  359. SQLUSMALLINT* val = 0;
  360. switch (length) {
  361. case 0:
  362. case SQL_IS_POINTER:
  363.     val = (SQLUSMALLINT*)buf;
  364.     break;
  365. default:
  366.     ctx.pushStatus(Error::Gen, "unsigned smallint pointer input - invalid length %d", (int)length);
  367.     return;
  368. }
  369. m_usmallintPtr = val;
  370. break;
  371. }
  372.     case IntegerPtr: {
  373. SQLINTEGER* val = 0;
  374. switch (length) {
  375. case 0:
  376. case SQL_IS_POINTER:
  377.     val = (SQLINTEGER*)buf;
  378.     break;
  379. default:
  380.     ctx.pushStatus(Error::Gen, "integer pointer input - invalid length %d", (int)length);
  381.     return;
  382. }
  383. m_integerPtr = val;
  384. break;
  385. }
  386.     case UintegerPtr: {
  387. SQLUINTEGER* val = 0;
  388. switch (length) {
  389. case 0:
  390. case SQL_IS_POINTER:
  391.     val = (SQLUINTEGER*)buf;
  392.     break;
  393. default:
  394.     ctx.pushStatus(Error::Gen, "unsigned integer pointer input - invalid length %d", (int)length);
  395.     return;
  396. }
  397. m_uintegerPtr = val;
  398. break;
  399. }
  400.     case Sqlchar: {
  401. const char* val = (char*)buf;
  402. if (val == 0) {
  403.     ctx.pushStatus(Sqlstate::_HY009, Error::Gen, "null string input");
  404.     return;
  405. }
  406. if (length < 0 && length != SQL_NTS) {
  407.     ctx.pushStatus(Error::Gen, "string input - invalid length %d", (int)length);
  408.     return;
  409. }
  410. if (length == SQL_NTS) {
  411.     m_sqlchar = strcpy(new char[strlen(val) + 1], val);
  412. } else {
  413.     m_sqlchar = (char*)memcpy(new char[length + 1], val, length);
  414.     m_sqlchar[length] = 0;
  415. }
  416. break;
  417. }
  418.     default:
  419. ctx_assert(false);
  420. break;
  421.     }
  422. }
  423. // copy out to user buffer
  424. void
  425. OdbcData::copyout(Ctx& ctx, SQLPOINTER buf, SQLINTEGER length, SQLINTEGER* total, SQLSMALLINT* total2)
  426. {
  427.     if (buf == 0) {
  428. ctx.setCode(SQL_ERROR);
  429. return;
  430.     }
  431.     switch (m_type) {
  432.     case Smallint: {
  433. SQLSMALLINT* ptr = static_cast<SQLSMALLINT*>(buf);
  434. *ptr = m_smallint;
  435. break;
  436. }
  437.     case Usmallint: {
  438. SQLUSMALLINT* ptr = static_cast<SQLUSMALLINT*>(buf);
  439. *ptr = m_usmallint;
  440. break;
  441. }
  442.     case Integer: {
  443. SQLINTEGER* ptr = static_cast<SQLINTEGER*>(buf);
  444. *ptr = m_integer;
  445. break;
  446. }
  447.     case Uinteger: {
  448. SQLUINTEGER* ptr = static_cast<SQLUINTEGER*>(buf);
  449. *ptr = m_uinteger;
  450. break;
  451. }
  452.     case Pointer: {
  453. SQLPOINTER* ptr = static_cast<SQLPOINTER*>(buf);
  454. *ptr = m_pointer;
  455. break;
  456. }
  457.     case Sqlchar: {
  458. char* ptr = static_cast<char*>(buf);
  459. if (length < 0 && length != SQL_NTS) {
  460.     ctx.setCode(SQL_ERROR);
  461.     return;
  462. }
  463. if (length == SQL_NTS) {
  464.     strcpy(ptr, m_sqlchar);
  465. } else {
  466.     strncpy(ptr, m_sqlchar, length);
  467. }
  468. if (total != 0)
  469.     *total = strlen(m_sqlchar);
  470. if (total2 != 0)
  471.     *total2 = strlen(m_sqlchar);
  472. break;
  473. }
  474.     case Sqlstate: {
  475. char* ptr = static_cast<char*>(buf);
  476. const char* state = m_sqlstate->state();
  477. if (length < 0 && length != SQL_NTS) {
  478.     ctx.setCode(SQL_ERROR);
  479.     return;
  480. }
  481. if (length == SQL_NTS) {
  482.     strcpy(ptr, state);
  483. } else {
  484.     strncpy(ptr, state, length);
  485. }
  486. if (total != 0)
  487.     *total = strlen(state);
  488. if (total2 != 0)
  489.     *total2 = strlen(state);
  490. break;
  491. }
  492.     default:
  493. ctx_assert(false);
  494. break;
  495.     }
  496. }
  497. void
  498. OdbcData::print(char* buf, unsigned size) const
  499. {
  500.     switch (m_type) {
  501.     case Undef:
  502. snprintf(buf, size, "undef");
  503. break;
  504.     case Smallint:
  505. snprintf(buf, size, "%d", (int)m_smallint);
  506. break;
  507.     case Usmallint:
  508. snprintf(buf, size, "%u", (unsigned)m_usmallint);
  509. break;
  510.     case Integer:
  511. snprintf(buf, size, "%ld", (long)m_integer);
  512. break;
  513.     case Uinteger:
  514. snprintf(buf, size, "%lu", (unsigned long)m_uinteger);
  515. break;
  516.     case Pointer:
  517. snprintf(buf, size, "0x%lx", (unsigned long)m_pointer);
  518. break;
  519.     case SmallintPtr:
  520. snprintf(buf, size, "0x%lx", (unsigned long)m_smallintPtr);
  521. break;
  522.     case UsmallintPtr:
  523. snprintf(buf, size, "0x%lx", (unsigned long)m_usmallintPtr);
  524. break;
  525.     case IntegerPtr:
  526. snprintf(buf, size, "0x%lx", (unsigned long)m_integerPtr);
  527. break;
  528.     case UintegerPtr:
  529. snprintf(buf, size, "0x%lx", (unsigned long)m_uintegerPtr);
  530. break;
  531.     case PointerPtr:
  532. snprintf(buf, size, "0x%lx", (unsigned long)m_pointerPtr);
  533. break;
  534.     case Sqlchar:
  535. snprintf(buf, size, "%s", m_sqlchar);
  536. break;
  537.     case Sqlstate:
  538. snprintf(buf, size, "%s", m_sqlstate->state());
  539. break;
  540.     default:
  541. snprintf(buf, size, "data(%d)", (int)m_type);
  542. break;
  543.     };
  544. }