ODBC 64-Bit Information

Beginning with Windows Server 2003, Microsoft operating systems have supported the 64-bit ODBC libraries. The ODBC headers and libraries first shipped with MDAC 2.7 SDK contain changes to allow programmers to easily write code for the new 64 bit platforms. By ensuring that your code uses the ODBC defined types listed below, you can compile the same source code both for 64-bit and 32-bit platforms based on the _WIN64 or WIN32 macros.

There are several points to keep in mind when programming for a 64-bit processor:

  • Although the size of a pointer has changed from 4 bytes to 8 bytes, integers and longs are still 4 byte values. The types INT64 and UINT64 have been defined for 8 byte integers. The new ODBC types SQLLEN and SQLULEN are defined in the ODBC header file as INT64 and UINT64 when _WIN64 has been defined.

  • Several functions in ODBC are declared as taking a pointer parameter. In 32-bit ODBC, parameters defined as pointers were frequently used to pass either an integer value or a pointer to a buffer depending on the context of the call. This was, of course, possible due to the fact that pointers and integers had the same size. In 64-bit Windows, this is not the case.

  • Some ODBC functions that were previously defined with SQLINTEGER and SQLUINTEGER parameters have been changed where appropriate to use the new SQLLEN and SQLULEN typedefs. These changes are listed in the next section, Function Declaration Changes.

  • Some of the descriptor fields that can be set through the various SQLSet and SQLGet functions have been changed to accommodate 64-bit values while others are still 32-bit values. Make sure that you use the appropriate sized variable when setting and retrieving these fields. Specifics of which descriptor fields have changed are listed under Function Declaration Changes.

Function Declaration Changes

The following function signatures have changed for 64-bit programming. The items in bold text are the specific parameters that are different.

SQLBindCol (SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber,  
   SQLSMALLINT TargetType, SQLPOINTER TargetValuePtr, SQLLEN BufferLength,   SQLLEN * StrLen_or_Ind);  
  
SQLBindParam (SQLHSTMT StatementHandle, SQLUSMALLINT ParameterNumber,  
   SQLSMALLINT ValueType, SQLSMALLINT ParameterType,   
   SQLULEN ColumnSize, SQLSMALLINT DecimalDigits,   
   SQLPOINTER ParameterValuePtr, SQLLEN *StrLen_or_Ind);  
  
SQLBindParameter (SQLHSTMT StatementHandle, SQLUSMALLINT ParameterNumber,   
   SQLSMALLINT InputOutputType, SQLSMALLINT ValueType,   
   SQLSMALLINT ParameterType, SQLULEN ColumnSize, SQLSMALLINT DecimalDigits,   
   SQLPOINTER ParameterValuePtr, SQLLEN BufferLength, SQLLEN *StrLen_or_IndPtr);  
  
SQLColAttribute (SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber,  
    SQLUSMALLINT FieldIdentifier, SQLPOINTER CharacterAttributePtr,   
   SQLSMALLINT BufferLength, SQLSMALLINT * StringLengthPtr,   
   SQLLEN* NumericAttributePtr)  
  
SQLColAttributes (SQLHSTMT hstmt, SQLUSMALLINT icol,   
   SQLUSMALLINT fDescType, SQLPOINTER rgbDesc,   
   SQLSMALLINT cbDescMax, SQLSMALLINT *pcbDesc, SQLLEN * pfDesc);  
  
SQLDescribeCol (SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber,   
   SQLCHAR *ColumnName, SQLSMALLINT BufferLength,   
   SQLSMALLINT *NameLengthPtr, SQLSMALLINT *DataTypePtr, SQLULEN *ColumnSizePtr,   
   SQLSMALLINT *DecimalDigitsPtr, SQLSMALLINT *NullablePtr);  
  
SQLDescribeParam (SQLHSTMT StatementHandle, SQLUSMALLINT ParameterNumber,   
   SQLSMALLINT *DataTypePtr, SQLULEN *ParameterSizePtr, SQLSMALLINT *DecimalDigitsPtr,   
   SQLSMALLINT *NullablePtr);  
  
SQLExtendedFetch(SQLHSTMT StatementHandle, SQLUSMALLINT FetchOrientation, SQLLEN FetchOffset,   
   SQLULEN * RowCountPtr, SQLUSMALLINT * RowStatusArray);  
  
SQLFetchScroll (SQLHSTMT StatementHandle, SQLSMALLINT FetchOrientation,   
   SQLLEN FetchOffset);  
  
SQLGetData (SQLHSTMT StatementHandle, SQLUSMALLINT ColumnNumber,   
   SQLSMALLINT TargetType, SQLPOINTER TargetValuePtr, SQLLEN BufferLength,    SQLLEN *StrLen_or_Ind);  
  
SQLGetDescRec (SQLHDESC DescriptorHandle, SQLSMALLINT RecNumber,   
   SQLCHAR *Name, SQLSMALLINT BufferLength,   
   SQLSMALLINT *StringLengthPtr, SQLSMALLINT *TypePtr,   
   SQLSMALLINT *SubTypePtr, SQLLEN *LengthPtr,   
   SQLSMALLINT *PrecisionPtr, SQLSMALLINT *ScalePtr,   
   SQLSMALLINT *NullablePtr);  
  
SQLParamOptions(SQLHSTMT hstmt, SQLULEN crow, SQLULEN * pirow);  
  
SQLPutData (SQLHSTMT StatementHandle, SQLPOINTER DataPtr,   
   SQLLEN StrLen_or_Ind);  
  
SQLRowCount (SQLHSTMT StatementHandle, SQLLEN* RowCountPtr);  
  
SQLSetConnectOption(SQLHDBC ConnectHandle, SQLUSMALLINT Option,   
   SQLULEN Value);  
  
SQLSetPos (SQLHSTMT StatementHandle, SQLSETPOSIROW RowNumber, SQLUSMALLINT Operation,  
   SQLUSMALLINT LockType);  
  
SQLSetParam (SQLHSTMT StatementHandle, SQLUSMALLINT ParameterNumber,   
   SQLSMALLINT ValueType, SQLSMALLINT ParameterType,   
   SQLULEN LengthPrecision, SQLSMALLINT ParameterScale,   
   SQLPOINTER ParameterValue, SQLLEN *StrLen_or_Ind);  
  
SQLSetDescRec (SQLHDESC DescriptorHandle, SQLSMALLINT RecNumber,   
   SQLSMALLINT Type, SQLSMALLINT SubType, SQLLEN Length,   
   SQLSMALLINT Precision, SQLSMALLINT Scale, SQLPOINTER DataPtr,   
   SQLLEN *StringLengthPtr, SQLLEN *IndicatorPtr);  
  
SQLSetScrollOptions (SQLHSTMT hstmt, SQLUSMALLINT fConcurrency,   
   SQLLEN crowKeyset, SQLUSMALLINT crowRowset);  
  
SQLSetStmtOption (SQLHSTMT StatementHandle, SQLUSMALLINT Option,   
   SQLULEN Value);  

Changes in SQL Data Types

The following four SQL types are still supported on 32-bit only; they are not defined for 64-bit compilers. These types are no longer used for any parameters in MDAC 2.7; use of these types will cause compiler failures on 64-bit platforms.

#ifdef WIN32   
typedef SQLULEN SQLROWCOUNT;   
typedef SQLULEN SQLROWSETSIZE;   
typedef SQLULEN SQLTRANSID;   
typedef SQLLEN SQLROWOFFSET;   
#endif  

The definition of SQLSETPOSIROW has changed for both 32-bit and 64-bit compilers:

#ifdef _WIN64   
typedef UINT64 SQLSETPOSIROW;   
#else   
#define SQLSETPOSIROW SQLUSMALLINT   
#endif  

The definitions of SQLLEN and SQLULEN have changed for 64-bit compilers:

#ifdef _WIN64   
typedef INT64 SQLLEN;   
typedef UINT64 SQLULEN;   
#else   
#define SQLLEN SQLINTEGER   
#define SQLULEN SQLUINTEGER   
#endif  

Although SQL_C_BOOKMARK is deprecated in ODBC 3.0, for 64-bit compilers on 2.0 clients, this value has changed:

#ifdef _WIN64   
#define SQL_C_BOOKMARK SQL_C_UBIGINT   
#else   
#define SQL_C_BOOKMARK SQL_C_ULONG   
#endif  

The BOOKMARK type is defined differently in the newer headers:

typedef SQLULEN BOOKMARK;  

Values Returned from ODBC API Calls Through Pointers

The following ODBC function calls take as an input parameter a pointer to a buffer in which data is returned from the driver. The context and meaning of the data returned is determined by other input parameters for the functions. In some cases, these methods may now return 64-bit (8-byte integer) values instead of the typical 32-bit (4-byte) integer values. These cases are as follows:

SQLColAttribute

When the FieldIdentifier parameter has one of the following values, a 64-bit value is returned in *NumericAttribute:

SQL_DESC_AUTO_UNIQUE_VALUE

SQL_DESC_CASE_SENSITIVE

SQL_DESC_CONCISE_TYPE

SQL_DESC_COUNT

SQL_DESC_DISPLAY_SIZE

SQL_DESC_FIXED_PREC_SCALE

SQL_DESC_LENGTH

SQL_DESC_NULLABLE

SQL_DESC_NUM_PREC_RADIX

SQL_DESC_OCTET_LENGTH

SQL_DESC_PRECISION

SQL_DESC_SCALE

SQL_DESC_SEARCHABLE

SQL_DESC_TYPE

SQL_DESC_UNNAMED

SQL_DESC_UNSIGNED

SQL_DESC_UPDATABLE

SQLColAttributes

When the fDescType parameter has one of the following values, a 64-bit value is returned in *pfDesc:

SQL_COLUMN_COUNT

SQL_COLUMN_DISPLAY_SIZE

SQL_COLUMN_LENGTH

SQL_DESC_AUTO_UNIQUE_VALUE

SQL_DESC_CASE_SENSITIVE

SQL_DESC_CONCISE_TYPE

SQL_DESC_FIXED_PREC_SCALE

SQL_DESC_SEARCHABLE

SQL_DESC_UNSIGNED

SQL_DESC_UPDATABLE

SQLGetConnectAttr

When the Attribute parameter has one of the following values, a 64-bit value is returned in Value:

SQL_ATTR_ASYNC_ENABLE

SQL_ATTR_ENLIST_IN_DTC

SQL_ATTR_ODBC_CURSORS

SQL_ATTR_QUIET_MODE

SQLGetConnectOption

When the Attribute parameter has one of the following values, a 64-bit value is returned in Value:

SQL_ATTR_QUIET_MODE

SQLGetDescField

When the FieldIdentifier parameter has one of the following values, a 64-bit value is returned in *ValuePtr:

SQL_DESC_ARRAY_SIZE

SQL_DESC_ARRAY_STATUS_PTR

SQL_DESC_BIND_OFFSET_PTR

SQL_DESC_DATA_PTR

SQL_DESC_DISPLAY_SIZE

SQL_DESC_INDICATOR_PTR

SQL_DESC_LENGTH

SQL_DESC_OCTET_LENGTH

SQL_DESC_OCTET_LENGTH_PTR

SQL_DESC_ROWS_PROCESSED_PTR

SQLGetDiagField

When the DiagIdentifier parameter has one of the following values, a 64-bit value is returned in *DiagInfoPtr:

SQL_DIAG_CURSOR_ROW_COUNT

SQL_DIAG_ROW_COUNT

SQL_DIAG_ROW_NUMBER

SQLGetInfo

When the InfoType parameter has one of the following values, a 64-bit value is returned in *InfoValuePtr:

SQL_DRIVER_HDBC

SQL_DRIVER_HENV

SQL_DRIVER_HLIB

When InfoType has either of the following 2 values *InfoValuePtr is 64-bits on both input and output:

SQL_DRIVER_HDESC

SQL_DRIVER_HSTMT

SQLGetStmtAttr

When the Attribute parameter has one of the following values, a 64-bit value is returned in *ValuePtr:

SQL_ATTR_APP_PARAM_DESC

SQL_ATTR_APP_ROW_DESC

SQL_ATTR_ASYNC_ENABLE

SQL_ATTR_CONCURRENCY

SQL_ATTR_CURSOR_SCROLLABLE

SQL_ATTR_CURSOR_SENSITIVITY

SQL_ATTR_CURSOR_TYPE

SQL_ATTR_ENABLE_AUTO_IPD

SQL_ATTR_FETCH_BOOKMARK_PTR

SQL_ATTR_ROWS_FETCHED_PTR

SQL_ATTR_IMP_PARAM_DESC

SQL_ATTR_IMP_ROW_DESC

SQL_ATTR_KEYSET_SIZE

SQL_ATTR_MAX_LENGTH

SQL_ATTR_MAX_ROWS

SQL_ATTR_METADATA_ID

SQL_ATTR_NOSCAN

SQL_ATTR_PARAM_BIND_OFFSET_PTR

SQL_ATTR_PARAM_BIND_TYPE

SQL_ATTR_PARAM_OPERATION_PTR

SQL_ATTR_PARAM_STATUS_PTR

SQL_ATTR_PARAMS_PROCESSED_PTR

SQL_ATTR_PARAMSET_SIZE

SQL_ATTR_QUERY_TIMEOUT

SQL_ATTR_RETRIEVE_DATA

SQL_ATTR_ROW_ARRAY_SIZE

SQL_ATTR_ROW_BIND_OFFSET_PTR

SQL_ATTR_ROW_NUMBER

SQL_ATTR_ROW_OPERATION_PTR

SQL_ATTR_ROW_STATUS_PTR

SQL_ATTR_SIMULATE_CURSOR

SQL_ATTR_USE_BOOKMARKS

SQLGetStmtOption

When the Option parameter has one of the following values, a 64-bit value is returned in *Value:

SQL_KEYSET_SIZE

SQL_MAX_LENGTH

SQL_MAX_ROWS

SQL_ROWSET_SIZE

SQLSetConnectAttr

When the Attribute parameter has one of the following values, a 64-bit value is passed in Value:

SQL_ATTR_ASYNC_ENABLE

SQL_ATTR_ENLIST_IN_DTC

SQL_ATTR_ODBC_CURSORS

SQL_ATTR_QUIET_MODE

SQLSetConnectOption

When the Attribute parameter has one of the following values, a 64-bit value is passed in Value:

SQL_ATTR_QUIET_MODE

SQLSetDescField

When the FieldIdentifier parameter has one of the following values, a 64-bit value is passed in ValuePtr:

SQL_DESC_ARRAY_SIZE

SQL_DESC_ARRAY_STATUS_PTR

SQL_DESC_BIND_OFFSET_PTR

SQL_DESC_DATA_PTR

SQL_DESC_DISPLAY_SIZE

SQL_DESC_INDICATOR_PTR

SQL_DESC_LENGTH

SQL_DESC_OCTET_LENGTH

SQL_DESC_OCTET_LENGTH_PTR

SQL_DESC_ROWS_PROCESSED_PTR

SQLSetStmtAttr

When the Attribute parameter has one of the following values, a 64-bit value is passed in ValuePtr:

SQL_ATTR_APP_PARAM_DESC

SQL_ATTR_APP_ROW_DESC

SQL_ATTR_ASYNC_ENABLE

SQL_ATTR_CONCURRENCY

SQL_ATTR_CURSOR_SCROLLABLE

SQL_ATTR_CURSOR_SENSITIVITY

SQL_ATTR_CURSOR_TYPE

SQL_ATTR_ENABLE_AUTO_IPD

SQL_ATTR_FETCH_BOOKMARK_PTR

SQL_ATTR_IMP_PARAM_DESC

SQL_ATTR_IMP_ROW_DESC

SQL_ATTR_KEYSET_SIZE

SQL_ATTR_MAX_LENGTH

SQL_ATTR_MAX_ROWS

SQL_ATTR_METADATA_ID

SQL_ATTR_NOSCAN

SQL_ATTR_PARAM_BIND_OFFSET_PTR

SQL_ATTR_PARAM_BIND_TYPE

SQL_ATTR_PARAM_OPERATION_PTR

SQL_ATTR_PARAM_STATUS_PTR

SQL_ATTR_PARAMS_PROCESSED_PTR

SQL_ATTR_PARAMSET_SIZE

SQL_ATTR_QUERY_TIMEOUT

SQL_ATTR_RETRIEVE_DATA

SQL_ATTR_ROW_ARRAY_SIZE

SQL_ATTR_ROW_BIND_OFFSET_PTR

SQL_ATTR_ROW_NUMBER

SQL_ATTR_ROW_OPERATION_PTR

SQL_ATTR_ROW_STATUS_PTR

SQL_ATTR_ROWS_FETCHED_PTR

SQL_ATTR_SIMULATE_CURSOR

SQL_ATTR_USE_BOOKMARKS

SQLSetStmtOption

When the Option parameter has one of the following values, a 64-bit value is passed in Value:

SQL_KEYSET_SIZE

SQL_MAX_LENGTH

SQL_MAX_ROWS

SQL_ROWSET_SIZE

See Also

Introduction to ODBC