C ODBC未经治疗的异常 /访问违规写作位置

C++ ODBC Unhandled exception / Access violation writing location

本文关键字:访问 位置 异常 ODBC      更新时间:2023-10-16

我正在编写一个ODBC数据库类,该类包含一个成员函数,用于从给定查询中获取一系列属性和元组。

我在下面的语句中有一行代码,这会导致此运行时错误处于调试模式:

Unhandled exception at <mem loc> in <prog name>: 0xC0000005: Access violation writing location <mem loc>.

这是ERROR指出有问题的行的代码:

SQLINTEGER length = 0;
vector<vector<string>> data;
this->sReturn = SQLFetch(this->sHandle);
while (this->sReturn == SQL_SUCCESS) {
  vector<string> tuple;
for (int i = 0; i < columnCount; i++) {
  SQLPOINTER value = "";
  switch (info[i].columnType) {
    case 0 : //SQL_UNKNOWN_TYPE
      throw DatabaseAttributeTypeUnknown("The database returned an attribute of an unknown type.");
      break;
    case 1 : //SQL_CHAR
      this->sReturn = SQLGetData(this->sHandle, i + 1, info[i].columnType, value,
        info[i].columnSize*sizeof(SQLCHAR),
ERROR   &length);
        break;
     //Some more cases
  }
}

关于为什么要丢弃此错误的任何想法?这是sqlgetData()上的MSDN文档,该文档将值分配给length

谢谢您的时间。

编译器将可执行的代码映射到源中的代码行时,它们通常无法区分分为多行的语句中的行。因此,如果调试器说在特定行上发生错误,则实际上可以在整个语句中的任何地方,因此在以下位置:

this->sReturn = SQLGetData(this->sHandle, i + 1, info[i].columnType, value,
    info[i].columnSize*sizeof(SQLCHAR),
    &length);

这里唯一摇摇欲坠的指针是 value,它指向一个空静态字符串,因此,对于一个包含null字节的一个字符长数组。同样,根据编译器选项,此数组可以在仅读取的数据段中。虽然SQLGetData()认为它指向至少info[i].columnSize*sizeof(SQLCHAR)字节的位置,并且在SQL列中写入(不读取)数据的位置。

我可能会错过其他细节,但我的第一个猜测是导致内存访问的原因。

除了弗雷德里克所说的话。您是否正在编译代码64位?如果这样

SQLRETURN  SQL_API SQLGetData(SQLHSTMT StatementHandle,
                              SQLUSMALLINT ColumnNumber, SQLSMALLINT TargetType,
                              SQLPOINTER TargetValue, SQLLEN BufferLength,
                              SQLLEN *StrLen_or_Ind);

sqllen是64位Windows中的8个字节,而不是4个字节,因为SQLinteger是。