LCOV - code coverage report
Current view: top level - clients/odbc/driver - SQLSetStmtAttr.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 17 150 11.3 %
Date: 2024-10-07 21:21:43 Functions: 1 1 100.0 %

          Line data    Source code
       1             : /*
       2             :  * SPDX-License-Identifier: MPL-2.0
       3             :  *
       4             :  * This Source Code Form is subject to the terms of the Mozilla Public
       5             :  * License, v. 2.0.  If a copy of the MPL was not distributed with this
       6             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       7             :  *
       8             :  * Copyright 2024 MonetDB Foundation;
       9             :  * Copyright August 2008 - 2023 MonetDB B.V.;
      10             :  * Copyright 1997 - July 2008 CWI.
      11             :  */
      12             : 
      13             : /*
      14             :  * This code was created by Peter Harvey (mostly during Christmas 98/99).
      15             :  * This code is LGPL. Please ensure that this message remains in future
      16             :  * distributions and uses of this code (that's about all I get out of it).
      17             :  * - Peter Harvey pharvey@codebydesign.com
      18             :  *
      19             :  * This file has been modified for the MonetDB project.  See the file
      20             :  * Copyright in this directory for more information.
      21             :  */
      22             : 
      23             : /**********************************************************************
      24             :  * SQLSetStmtAttr()
      25             :  * CLI Compliance: ISO 92
      26             :  *
      27             :  * Author: Martin van Dinther, Sjoerd Mullender
      28             :  * Date  : 30 aug 2002
      29             :  *
      30             :  **********************************************************************/
      31             : 
      32             : #include "ODBCGlobal.h"
      33             : #include "ODBCStmt.h"
      34             : 
      35             : 
      36             : SQLRETURN
      37          12 : MNDBSetStmtAttr(ODBCStmt *stmt,
      38             :                 SQLINTEGER Attribute,
      39             :                 SQLPOINTER ValuePtr,
      40             :                 SQLINTEGER StringLength)
      41             : {
      42             :         /* TODO: check parameters: ValuePtr and StringLength */
      43             : 
      44          12 :         if (Attribute == SQL_ATTR_CONCURRENCY ||
      45          12 :             Attribute == SQL_ATTR_CURSOR_SCROLLABLE ||
      46             :             Attribute == SQL_ATTR_CURSOR_SENSITIVITY ||
      47             :             Attribute == SQL_ATTR_CURSOR_TYPE ||
      48             :             Attribute == SQL_ATTR_USE_BOOKMARKS) {
      49           0 :                 if (stmt->State >= EXECUTED0) {
      50             :                         /* Invalid cursor state */
      51           0 :                         addStmtError(stmt, "24000", NULL, 0);
      52           0 :                         return SQL_ERROR;
      53             :                 }
      54           0 :                 if (stmt->State > INITED) {
      55             :                         /* Attribute cannot be set now */
      56           0 :                         addStmtError(stmt, "HY011", NULL, 0);
      57           0 :                         return SQL_ERROR;
      58             :                 }
      59             :         }
      60             : 
      61          12 :         switch (Attribute) {
      62             : #define desc ((ODBCDesc *) ValuePtr)    /* abbrev. */
      63           0 :         case SQL_ATTR_APP_PARAM_DESC:           /* SQLHANDLE */
      64           0 :                 if (ValuePtr == SQL_NULL_HDESC ||
      65           0 :                     desc == stmt->AutoApplParamDescr) {
      66           0 :                         stmt->ApplParamDescr = stmt->AutoApplParamDescr;
      67           0 :                         return SQL_SUCCESS;
      68             :                 }
      69           0 :                 if (!isValidDesc(desc)) {
      70             :                         /* Invalid attribute value */
      71           0 :                         addStmtError(stmt, "HY024", NULL, 0);
      72           0 :                         return SQL_ERROR;
      73             :                 }
      74           0 :                 if (desc->sql_desc_alloc_type == SQL_DESC_ALLOC_AUTO) {
      75             :                         /* Invalid use of an automatically allocated
      76             :                            descriptor handle */
      77           0 :                         addStmtError(stmt, "HY017", NULL, 0);
      78           0 :                         return SQL_ERROR;
      79             :                 }
      80           0 :                 stmt->ApplParamDescr = desc;
      81           0 :                 break;
      82           0 :         case SQL_ATTR_APP_ROW_DESC:             /* SQLHANDLE */
      83           0 :                 if (ValuePtr == SQL_NULL_HDESC ||
      84           0 :                     desc == stmt->AutoApplRowDescr) {
      85           0 :                         stmt->ApplRowDescr = stmt->AutoApplRowDescr;
      86           0 :                         return SQL_SUCCESS;
      87             :                 }
      88           0 :                 if (!isValidDesc(desc)) {
      89             :                         /* Invalid attribute value */
      90           0 :                         addStmtError(stmt, "HY024", NULL, 0);
      91           0 :                         return SQL_ERROR;
      92             :                 }
      93           0 :                 if (desc->sql_desc_alloc_type == SQL_DESC_ALLOC_AUTO) {
      94             :                         /* Invalid use of an automatically allocated
      95             :                            descriptor handle */
      96           0 :                         addStmtError(stmt, "HY017", NULL, 0);
      97           0 :                         return SQL_ERROR;
      98             :                 }
      99           0 :                 stmt->ApplRowDescr = desc;
     100           0 :                 break;
     101             : #undef desc
     102           0 :         case SQL_ATTR_CURSOR_SCROLLABLE:        /* SQLULEN */
     103           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     104           0 :                 case SQL_NONSCROLLABLE:
     105           0 :                         stmt->cursorType = SQL_CURSOR_FORWARD_ONLY;
     106           0 :                         break;
     107           0 :                 case SQL_SCROLLABLE:
     108           0 :                         stmt->cursorType = SQL_CURSOR_STATIC;
     109           0 :                         break;
     110           0 :                 default:
     111             :                         /* Invalid attribute value */
     112           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     113           0 :                         return SQL_ERROR;
     114             :                 }
     115           0 :                 stmt->cursorScrollable = (SQLULEN) (uintptr_t) ValuePtr;
     116           0 :                 break;
     117           0 :         case SQL_ATTR_CURSOR_TYPE:              /* SQLULEN */
     118           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     119           0 :                 case SQL_CURSOR_KEYSET_DRIVEN:
     120             :                 case SQL_CURSOR_DYNAMIC:
     121             :                         /* Option value changed */
     122           0 :                         addStmtError(stmt, "01S02", NULL, 0);
     123             : 
     124             :                         /* fall through */
     125           0 :                 case SQL_CURSOR_STATIC:
     126           0 :                         stmt->cursorScrollable = SQL_SCROLLABLE;
     127           0 :                         stmt->cursorType = SQL_CURSOR_STATIC;
     128           0 :                         break;
     129           0 :                 case SQL_CURSOR_FORWARD_ONLY:
     130           0 :                         stmt->cursorScrollable = SQL_NONSCROLLABLE;
     131           0 :                         stmt->cursorType = SQL_CURSOR_FORWARD_ONLY;
     132           0 :                         break;
     133           0 :                 default:
     134             :                         /* Invalid attribute value */
     135           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     136           0 :                         return SQL_ERROR;
     137             :                 }
     138             :                 break;
     139           0 :         case SQL_ATTR_ENABLE_AUTO_IPD:          /* SQLULEN */
     140           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     141             :                 case SQL_TRUE:
     142             :                 case SQL_FALSE:
     143             :                         break;
     144           0 :                 default:
     145             :                         /* Invalid attribute value */
     146           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     147           0 :                         return SQL_ERROR;
     148             :                 }
     149             :                 /* ignore value, always treat as SQL_TRUE */
     150             :                 break;
     151           0 :         case SQL_ATTR_IMP_PARAM_DESC:           /* SQLHANDLE */
     152             :         case SQL_ATTR_IMP_ROW_DESC:             /* SQLHANDLE */
     153             :                 /* Invalid use of an automatically allocated
     154             :                    descriptor handle */
     155           0 :                 addStmtError(stmt, "HY017", NULL, 0);
     156           0 :                 return SQL_ERROR;
     157           8 :         case SQL_ATTR_MAX_LENGTH:               /* SQLULEN */
     158             :         case SQL_ATTR_MAX_ROWS:                 /* SQLULEN */
     159           8 :                 if ((SQLULEN) (uintptr_t) ValuePtr != 0 &&
     160           8 :                     (SQLULEN) (uintptr_t) ValuePtr != 2147483647)
     161           8 :                         addStmtError(stmt, "01S02", NULL, 0);
     162             :                 break;
     163           0 :         case SQL_ATTR_NOSCAN:                   /* SQLULEN */
     164           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     165             :                 case SQL_NOSCAN_ON:
     166             :                 case SQL_NOSCAN_OFF:
     167           0 :                         break;
     168           0 :                 default:
     169             :                         /* Invalid attribute value */
     170           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     171           0 :                         return SQL_ERROR;
     172             :                 }
     173           0 :                 stmt->noScan = (SQLULEN) (uintptr_t) ValuePtr;
     174           0 :                 break;
     175           0 :         case SQL_ATTR_PARAM_BIND_OFFSET_PTR:    /* SQLULEN* */
     176           0 :                 return MNDBSetDescField(stmt->ApplParamDescr, 0,
     177             :                                         SQL_DESC_BIND_OFFSET_PTR, ValuePtr,
     178             :                                         StringLength);
     179           0 :         case SQL_ATTR_PARAM_BIND_TYPE:          /* SQLULEN */
     180             :         {
     181           0 :                 SQLUINTEGER v = (SQLUINTEGER) (SQLULEN) (uintptr_t) ValuePtr;
     182           0 :                 return MNDBSetDescField(stmt->ApplParamDescr, 0,
     183             :                                         SQL_DESC_BIND_TYPE, (SQLPOINTER) (uintptr_t) v,
     184             :                                         StringLength);
     185             :         }
     186           0 :         case SQL_ATTR_PARAM_OPERATION_PTR:      /* SQLUSMALLINT* */
     187           0 :                 return MNDBSetDescField(stmt->ApplParamDescr, 0,
     188             :                                         SQL_DESC_ARRAY_STATUS_PTR, ValuePtr,
     189             :                                         StringLength);
     190           0 :         case SQL_ATTR_PARAM_STATUS_PTR:         /* SQLUSMALLINT* */
     191           0 :                 return MNDBSetDescField(stmt->ImplParamDescr, 0,
     192             :                                         SQL_DESC_ARRAY_STATUS_PTR, ValuePtr,
     193             :                                         StringLength);
     194           0 :         case SQL_ATTR_PARAMS_PROCESSED_PTR:     /* SQLULEN* */
     195           0 :                 return MNDBSetDescField(stmt->ImplParamDescr, 0,
     196             :                                         SQL_DESC_ROWS_PROCESSED_PTR, ValuePtr,
     197             :                                         StringLength);
     198           0 :         case SQL_ATTR_PARAMSET_SIZE:            /* SQLULEN */
     199           0 :                 return MNDBSetDescField(stmt->ApplParamDescr, 0,
     200             :                                         SQL_DESC_ARRAY_SIZE, ValuePtr,
     201             :                                         StringLength);
     202           4 :         case SQL_ATTR_QUERY_TIMEOUT:            /* SQLULEN */
     203           4 :                 if ((uintptr_t) ValuePtr > 0x7FFFFFFF) {
     204           4 :                         stmt->qtimeout = 0x7FFFFFFF;
     205           4 :                         addStmtError(stmt, "01S02", NULL, 0);
     206             :                 } else {
     207           0 :                         stmt->qtimeout = (SQLULEN) (uintptr_t) ValuePtr;
     208             :                 }
     209             :                 break;
     210           0 :         case SQL_ATTR_RETRIEVE_DATA:            /* SQLULEN */
     211           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     212             :                 case SQL_RD_ON:
     213             :                 case SQL_RD_OFF:
     214           0 :                         break;
     215           0 :                 default:
     216             :                         /* Invalid attribute value */
     217           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     218           0 :                         return SQL_ERROR;
     219             :                 }
     220           0 :                 stmt->retrieveData = (SQLULEN) (uintptr_t) ValuePtr;
     221           0 :                 break;
     222           0 :         case SQL_ATTR_ROW_ARRAY_SIZE:           /* SQLULEN */
     223             :         case SQL_ROWSET_SIZE:
     224           0 :                 return MNDBSetDescField(stmt->ApplRowDescr, 0,
     225             :                                         SQL_DESC_ARRAY_SIZE, ValuePtr,
     226             :                                         StringLength);
     227           0 :         case SQL_ATTR_ROW_BIND_OFFSET_PTR:      /* SQLULEN* */
     228           0 :                 return MNDBSetDescField(stmt->ApplRowDescr, 0,
     229             :                                         SQL_DESC_BIND_OFFSET_PTR, ValuePtr,
     230             :                                         StringLength);
     231           0 :         case SQL_ATTR_ROW_BIND_TYPE:            /* SQLULEN */
     232           0 :                 return MNDBSetDescField(stmt->ApplRowDescr, 0,
     233             :                                         SQL_DESC_BIND_TYPE, ValuePtr,
     234             :                                         StringLength);
     235           0 :         case SQL_ATTR_ROW_OPERATION_PTR:        /* SQLUSMALLINT* */
     236           0 :                 return MNDBSetDescField(stmt->ApplRowDescr, 0,
     237             :                                         SQL_DESC_ARRAY_STATUS_PTR, ValuePtr,
     238             :                                         StringLength);
     239           0 :         case SQL_ATTR_ROW_STATUS_PTR:           /* SQLUSMALLINT* */
     240           0 :                 return MNDBSetDescField(stmt->ImplRowDescr, 0,
     241             :                                         SQL_DESC_ARRAY_STATUS_PTR, ValuePtr,
     242             :                                         StringLength);
     243           0 :         case SQL_ATTR_ROWS_FETCHED_PTR:         /* SQLULEN* */
     244           0 :                 return MNDBSetDescField(stmt->ImplRowDescr, 0,
     245             :                                         SQL_DESC_ROWS_PROCESSED_PTR, ValuePtr,
     246             :                                         StringLength);
     247           0 :         case SQL_ATTR_METADATA_ID:              /* SQLULEN */
     248           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     249             :                 case SQL_TRUE:
     250             :                 case SQL_FALSE:
     251           0 :                         break;
     252           0 :                 default:
     253             :                         /* Invalid attribute value */
     254           0 :                         addStmtError(stmt, "HY024", NULL, 0);
     255           0 :                         return SQL_ERROR;
     256             :                 }
     257           0 :                 stmt->Dbc->sql_attr_metadata_id = (SQLUINTEGER) (SQLULEN) (uintptr_t) ValuePtr;
     258           0 :                 break;
     259             : 
     260           0 :         case SQL_ATTR_CONCURRENCY:              /* SQLULEN */
     261           0 :                 switch ((SQLULEN) (uintptr_t) ValuePtr) {
     262             :                 case SQL_CONCUR_READ_ONLY:
     263             :                         /* the only value we support */
     264             :                         break;
     265           0 :                 case SQL_CONCUR_LOCK:
     266             :                 case SQL_CONCUR_ROWVER:
     267             :                 case SQL_CONCUR_VALUES:
     268             :                         /* Optional feature not implemented */
     269           0 :                         addStmtError(stmt, "HYC00", NULL, 0);
     270           0 :                         return SQL_ERROR;
     271             :                 }
     272             :                 break;
     273             : 
     274             :         /* TODO: implement requested behavior */
     275           0 :         case SQL_ATTR_ASYNC_ENABLE:             /* SQLULEN */
     276             : #ifdef SQL_ATTR_ASYNC_STMT_EVENT
     277             :         case SQL_ATTR_ASYNC_STMT_EVENT:         /* SQLPOINTER */
     278             : #endif
     279             : #ifdef SQL_ATTR_ASYNC_STMT_PCALLBACK
     280             :         case SQL_ATTR_ASYNC_PCALLBACK:          /* SQLPOINTER */
     281             : #endif
     282             : #ifdef SQL_ATTR_ASYNC_STMT_PCONTEXT
     283             :         case SQL_ATTR_ASYNC_PCONTEXT:           /* SQLPOINTER */
     284             : #endif
     285             :         case SQL_ATTR_CURSOR_SENSITIVITY:       /* SQLULEN */
     286             :         case SQL_ATTR_FETCH_BOOKMARK_PTR:       /* SQLLEN* */
     287             :         case SQL_ATTR_KEYSET_SIZE:              /* SQLULEN */
     288             :         case SQL_ATTR_SIMULATE_CURSOR:          /* SQLULEN */
     289             :         case SQL_ATTR_USE_BOOKMARKS:            /* SQLULEN */
     290             :                 /* Optional feature not implemented */
     291           0 :                 addStmtError(stmt, "HYC00", NULL, 0);
     292           0 :                 return SQL_ERROR;
     293             : 
     294           0 :         case SQL_ATTR_ROW_NUMBER:            /* SQLULEN */
     295             :                 /* invalid attribute, can only be used with SQLGetStmtAttr */
     296             :         default:
     297             :                 /* Invalid attribute/option identifier */
     298           0 :                 addStmtError(stmt, "HY092", NULL, 0);
     299           0 :                 return SQL_ERROR;
     300             :         }
     301             : 
     302          12 :         return stmt->Error ? SQL_SUCCESS_WITH_INFO : SQL_SUCCESS;
     303             : }
     304             : 
     305             : SQLRETURN SQL_API
     306             : SQLSetStmtAttr(SQLHSTMT StatementHandle,
     307             :                SQLINTEGER Attribute,
     308             :                SQLPOINTER ValuePtr,
     309             :                SQLINTEGER StringLength)
     310             : {
     311             : #ifdef ODBCDEBUG
     312          12 :         ODBCLOG("SQLSetStmtAttr %p %s %p %d\n",
     313             :                 StatementHandle, translateStmtAttribute(Attribute),
     314             :                 ValuePtr, (int) StringLength);
     315             : #endif
     316             : 
     317          12 :         if (!isValidStmt((ODBCStmt *) StatementHandle))
     318             :                 return SQL_INVALID_HANDLE;
     319             : 
     320          12 :         clearStmtErrors((ODBCStmt *) StatementHandle);
     321             : 
     322          12 :         return MNDBSetStmtAttr((ODBCStmt *) StatementHandle,
     323             :                                Attribute,
     324             :                                ValuePtr,
     325             :                                StringLength);
     326             : }
     327             : 
     328             : SQLRETURN SQL_API
     329             : SQLSetStmtAttrW(SQLHSTMT StatementHandle,
     330             :                 SQLINTEGER Attribute,
     331             :                 SQLPOINTER ValuePtr,
     332             :                 SQLINTEGER StringLength)
     333             : {
     334             : #ifdef ODBCDEBUG
     335           0 :         ODBCLOG("SQLSetStmtAttrW %p %s %p %d\n",
     336             :                 StatementHandle, translateStmtAttribute(Attribute),
     337             :                 ValuePtr, (int) StringLength);
     338             : #endif
     339             : 
     340           0 :         if (!isValidStmt((ODBCStmt *) StatementHandle))
     341             :                 return SQL_INVALID_HANDLE;
     342             : 
     343           0 :         clearStmtErrors((ODBCStmt *) StatementHandle);
     344             : 
     345             :         /* there are no string-valued attributes */
     346             : 
     347           0 :         return MNDBSetStmtAttr((ODBCStmt *) StatementHandle,
     348             :                                Attribute,
     349             :                                ValuePtr,
     350             :                                StringLength);
     351             : }

Generated by: LCOV version 1.14