II_EXTERN II_VOID II_FAR II_EXPORT IIapi_scroll( IIAPI_SCROLLPARM II_FAR *scrollParm ) { IIAPI_STMTHNDL *stmtHndl; IIAPI_CONNHNDL *connHndl; bool valid; IIAPI_TRACE( IIAPI_TR_TRACE )( "IIapi_scroll: scroll cursor\n" ); /* ** Validate Input parameters */ if ( ! scrollParm ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: null scrollParms parameters\n" ); return; } scrollParm->sl_genParm.gp_completed = FALSE; scrollParm->sl_genParm.gp_status = IIAPI_ST_SUCCESS; scrollParm->sl_genParm.gp_errorHandle = NULL; stmtHndl = (IIAPI_STMTHNDL *)scrollParm->sl_stmtHandle; /* ** Make sure API is initialized */ if ( ! IIapi_initialized() ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: API is not initialized\n" ); IIapi_appCallback( &scrollParm->sl_genParm, NULL, IIAPI_ST_NOT_INITIALIZED ); return; } if ( ! IIapi_isStmtHndl( stmtHndl ) || IIAPI_STALE_HANDLE( stmtHndl ) || ! (connHndl = IIapi_getConnHndl( (IIAPI_HNDL *)stmtHndl)) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: invalid handle %p\n", stmtHndl ); IIapi_appCallback( &scrollParm->sl_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_scroll: handle = %p\n", stmtHndl ); IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_scroll: orientation = %d, offset = %d\n", scrollParm->sl_orientation, scrollParm->sl_offset ); IIapi_clearAllErrors( (IIAPI_HNDL *)stmtHndl ); /* ** Validate parameters. */ switch( scrollParm->sl_orientation ) { case IIAPI_SCROLL_NEXT : valid = TRUE; break; case IIAPI_SCROLL_BEFORE : case IIAPI_SCROLL_FIRST : case IIAPI_SCROLL_PRIOR : case IIAPI_SCROLL_CURRENT : case IIAPI_SCROLL_LAST : case IIAPI_SCROLL_AFTER : case IIAPI_SCROLL_ABSOLUTE : case IIAPI_SCROLL_RELATIVE : if ( connHndl->ch_partnerProtocol >= GCA_PROTOCOL_LEVEL_67 ) valid = TRUE; else { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: scrolling not supported\n" ); valid = FALSE; } break; default : IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: invalid orientation: %d\n", (II_LONG)scrollParm->sl_orientation ); valid = FALSE; break; } if ( ! valid ) { if ( ! IIapi_localError( (IIAPI_HNDL *)stmtHndl, E_AP0011_INVALID_PARAM_VALUE, II_SS22003_NUM_VAL_OUT_OF_RANGE, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &scrollParm->sl_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &scrollParm->sl_genParm, (IIAPI_HNDL *)stmtHndl, IIAPI_ST_FAILURE ); return; } IIapi_uiDispatch( IIAPI_EV_SCROLL_FUNC, (IIAPI_HNDL *)stmtHndl, (II_PTR)scrollParm ); return; }
II_EXTERN II_VOID II_FAR II_EXPORT IIapi_position( IIAPI_POSPARM II_FAR *posParm ) { IIAPI_STMTHNDL *stmtHndl; IIAPI_CONNHNDL *connHndl; bool valid; IIAPI_TRACE( IIAPI_TR_TRACE )( "IIapi_position: position cursor\n" ); /* ** Validate Input parameters */ if ( ! posParm ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_position: null posParms parameters\n" ); return; } posParm->po_genParm.gp_completed = FALSE; posParm->po_genParm.gp_status = IIAPI_ST_SUCCESS; posParm->po_genParm.gp_errorHandle = NULL; stmtHndl = (IIAPI_STMTHNDL *)posParm->po_stmtHandle; /* ** Make sure API is initialized */ if ( ! IIapi_initialized() ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_position: API is not initialized\n" ); IIapi_appCallback( &posParm->po_genParm, NULL, IIAPI_ST_NOT_INITIALIZED ); return; } if ( ! IIapi_isStmtHndl( stmtHndl ) || IIAPI_STALE_HANDLE( stmtHndl ) || ! (connHndl = IIapi_getConnHndl( (IIAPI_HNDL *)stmtHndl )) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_position: invalid handle %p\n", stmtHndl ); IIapi_appCallback( &posParm->po_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_position: handle = %p\n", stmtHndl ); IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_position: reference = %d, offset = %d, rows = %d\n", posParm->po_reference, posParm->po_offset, posParm->po_rowCount ); IIapi_clearAllErrors( (IIAPI_HNDL *)stmtHndl ); /* ** Validate parameters. */ switch( posParm->po_reference ) { case IIAPI_POS_BEGIN : case IIAPI_POS_END : if ( connHndl->ch_partnerProtocol >= GCA_PROTOCOL_LEVEL_67 ) valid = TRUE; else { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: scrolling not supported\n" ); valid = FALSE; } break; case IIAPI_POS_CURRENT : if ( connHndl->ch_partnerProtocol >= GCA_PROTOCOL_LEVEL_67 || posParm->po_offset == 1 ) valid = TRUE; else { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_scroll: scrolling not supported\n" ); valid = FALSE; } break; default : IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_position: invalid reference: %d\n", (II_LONG)posParm->po_reference ); valid = FALSE; break; } if ( posParm->po_rowCount < ((connHndl->ch_partnerProtocol >= GCA_PROTOCOL_LEVEL_67) ? 0 : 1) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_position: invalid row count: %d\n", (II_LONG)posParm->po_rowCount ); valid = FALSE; } if ( ! valid ) { if ( ! IIapi_localError( (IIAPI_HNDL *)stmtHndl, E_AP0011_INVALID_PARAM_VALUE, II_SS22003_NUM_VAL_OUT_OF_RANGE, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &posParm->po_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &posParm->po_genParm, (IIAPI_HNDL *)stmtHndl, IIAPI_ST_FAILURE); return; } IIapi_uiDispatch( IIAPI_EV_POSITION_FUNC, (IIAPI_HNDL *) stmtHndl, (II_PTR)posParm ); return; }
II_EXTERN II_VOID II_FAR II_EXPORT IIapi_batch( IIAPI_BATCHPARM II_FAR *batchParm ) { IIAPI_CONNHNDL *connHndl; IIAPI_TRANHNDL *tranHndl; IIAPI_STMTHNDL *stmtHndl; IIAPI_HNDL *handle; IIAPI_TRACE( IIAPI_TR_TRACE )( "IIapi_batch: adding a batch query\n" ); /* ** Validate Input parameters */ if ( ! batchParm ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: null batch parameters\n" ); return; } batchParm->ba_genParm.gp_completed = FALSE; batchParm->ba_genParm.gp_status = IIAPI_ST_SUCCESS; batchParm->ba_genParm.gp_errorHandle = NULL; connHndl = (IIAPI_CONNHNDL *)batchParm->ba_connHandle; handle = (IIAPI_HNDL *)batchParm->ba_tranHandle; stmtHndl = (IIAPI_STMTHNDL *)batchParm->ba_stmtHandle; /* ** Make sure API is initialized */ if ( ! IIapi_initialized() ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: API is not initialized\n" ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_NOT_INITIALIZED ); return; } /* ** Validate connection handle. */ if ( ! IIapi_isConnHndl( connHndl ) || IIAPI_STALE_HANDLE( connHndl ) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: invalid connHndl %p\n", connHndl ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } /* ** Validate transaction handle. */ if ( handle && ! IIapi_isTranName( (IIAPI_TRANNAME *)handle ) && (! IIapi_isTranHndl( (IIAPI_TRANHNDL *)handle ) || IIAPI_STALE_HANDLE( handle )) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: invalid tranHndl %p\n", handle ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } /* ** Validate statement handle. */ if ( stmtHndl ) { if ( ! IIapi_isStmtHndl( (IIAPI_STMTHNDL *)stmtHndl ) || IIAPI_STALE_HANDLE( stmtHndl ) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: invalid stmtHndl %p\n", stmtHndl ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } if ( ! handle || IIapi_isTranName( (IIAPI_TRANNAME *)handle) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: transaction handle required\n" ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } if ( handle != (IIAPI_HNDL *)stmtHndl->sh_tranHndl ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: wrong tranHndl %p for stmtHndl %p\n", handle, stmtHndl ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } if ( connHndl != IIapi_getConnHndl( (IIAPI_HNDL *)stmtHndl ) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: wrong connHndl %p for stmtHndl %p\n", connHndl, stmtHndl ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_INVALID_HANDLE ); return; } } IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_batch: connHndl = %p, tranHndl = %p, stmtHndl = %p, queryType = %d\n", batchParm->ba_connHandle, batchParm->ba_tranHandle, batchParm->ba_stmtHandle, batchParm->ba_queryType ); IIAPI_TRACE( IIAPI_TR_INFO ) ( "IIapi_batch: queryText = %s\n", batchParm->ba_queryText ? batchParm->ba_queryText : "<NULL>" ); IIapi_clearAllErrors( stmtHndl ? (IIAPI_HNDL *)stmtHndl : ( (handle && IIapi_isTranHndl( (IIAPI_TRANHNDL *)handle )) ? handle : (IIAPI_HNDL *)connHndl ) ); /* ** Check that batch processing is supported on the connection. */ if ( connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_68 ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: batch not supported at protocol level %d\n", connHndl->ch_partnerProtocol ); if ( ! IIapi_localError( (IIAPI_HNDL *)connHndl, E_AP001F_BATCH_UNSUPPORTED, II_SS50008_UNSUPPORTED_STMT, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &batchParm->ba_genParm, (IIAPI_HNDL *)connHndl, IIAPI_ST_FAILURE ); return; } /* ** Check restrictions on query type and associated info. */ if ( connHndl->ch_type != IIAPI_SMT_SQL || (batchParm->ba_queryType != IIAPI_QT_QUERY && batchParm->ba_queryType != IIAPI_QT_EXEC && batchParm->ba_queryType != IIAPI_QT_EXEC_PROCEDURE) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: invalid query type %d for connection type %d\n", batchParm->ba_queryType, connHndl->ch_type ); if ( ! IIapi_localError( (IIAPI_HNDL *)connHndl, E_AP0011_INVALID_PARAM_VALUE, II_SS50008_UNSUPPORTED_STMT, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &batchParm->ba_genParm, (IIAPI_HNDL *)connHndl, IIAPI_ST_FAILURE ); return; } if ( batchParm->ba_queryType != IIAPI_QT_EXEC_PROCEDURE && ! batchParm->ba_queryText ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: query requires query text\n" ); if ( ! IIapi_localError( (IIAPI_HNDL *)connHndl, E_AP0011_INVALID_PARAM_VALUE, II_SS5000R_RUN_TIME_LOGICAL_ERROR, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &batchParm->ba_genParm, (IIAPI_HNDL *)connHndl, IIAPI_ST_FAILURE ); return; } if ( batchParm->ba_queryType == IIAPI_QT_EXEC_PROCEDURE && ! batchParm->ba_parameters ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: query requires parameters, none indicated\n" ); if ( ! IIapi_localError( (IIAPI_HNDL *)connHndl, E_AP0011_INVALID_PARAM_VALUE, II_SS5000R_RUN_TIME_LOGICAL_ERROR, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &batchParm->ba_genParm, (IIAPI_HNDL *)connHndl, IIAPI_ST_FAILURE ); return; } /* ** Allocate a transaction handle if one was not provided. */ if ( ! handle || IIapi_isTranName( (IIAPI_TRANNAME *)handle ) ) { /* ** Check to see if there is an active transaction. */ if ( ! IIapi_isQueEmpty( (QUEUE *)&connHndl->ch_tranHndlList ) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ("IIapi_batch: connection has active transaction.\n"); if ( ! IIapi_localError( (IIAPI_HNDL *)connHndl, E_AP0003_ACTIVE_TRANSACTIONS, II_SS25000_INV_XACT_STATE, IIAPI_ST_FAILURE ) ) IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); else IIapi_appCallback( &batchParm->ba_genParm, (IIAPI_HNDL *)connHndl, IIAPI_ST_FAILURE ); return; } if ( ! ( tranHndl = IIapi_createTranHndl( (IIAPI_TRANNAME *)batchParm->ba_tranHandle, (IIAPI_CONNHNDL *)batchParm->ba_connHandle ) ) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: createTranHndl failed\n" ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); return; } } else { /* ** Use existing transaction handle. */ tranHndl = (IIAPI_TRANHNDL *)handle; IIapi_clearAllErrors( (IIAPI_HNDL *)tranHndl ); } /* ** Allocate a new statement handle or initialize existing handle. */ if ( stmtHndl ) initStmtHndl( stmtHndl ); else if ( ! (stmtHndl = IIapi_createStmtHndl( connHndl, tranHndl )) ) { IIAPI_TRACE( IIAPI_TR_ERROR ) ( "IIapi_batch: createStmtHndl failed\n" ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); goto freeTranHandle; } /* ** Update statement handle with batch query information. */ if ( batchParm->ba_queryText && ! (stmtHndl->sh_queryText = STalloc( batchParm->ba_queryText )) ) { IIAPI_TRACE( IIAPI_TR_FATAL ) ( "IIapi_batch: can't alloc query text\n" ); IIapi_appCallback( &batchParm->ba_genParm, NULL, IIAPI_ST_OUT_OF_MEMORY ); goto freeStmtHandle; } stmtHndl->sh_queryType = batchParm->ba_queryType; if ( batchParm->ba_parameters ) stmtHndl->sh_flags |= IIAPI_SH_PARAMETERS; /* ** The current set of external batch/query flags ** are not applicable to batch processing, but ** we pass them along anyway. */ stmtHndl->sh_flags |= batchParm->ba_flags & IIAPI_QF_ALL_FLAGS; batchParm->ba_stmtHandle = (II_PTR)stmtHndl; batchParm->ba_tranHandle = (II_PTR)tranHndl; IIapi_uiDispatch( IIAPI_EV_BATCH_FUNC, (IIAPI_HNDL *)stmtHndl, (II_PTR)batchParm ); return; freeStmtHandle: /* ** If the statement handle is not the input handle, ** then we allocated a new handle above and we must ** now delete it. */ if ( stmtHndl != (IIAPI_STMTHNDL *)batchParm->ba_stmtHandle ) IIapi_deleteStmtHndl( stmtHndl ); freeTranHandle: /* ** If the transaction handle is not the input handle, ** then we allocated a new handle above and we must ** now delete it. */ if ( tranHndl != (IIAPI_TRANHNDL *)batchParm->ba_tranHandle ) IIapi_deleteTranHndl( tranHndl ); return; }
II_EXTERN IIAPI_MSG_BUFF * IIapi_createGCNOper( IIAPI_STMTHNDL *stmtHndl ) { IIAPI_MSG_BUFF *msgBuff; u_i1 *msg; char *str, temp[ 512 ]; i4 val; IIAPI_CONNHNDL *connHndl = IIapi_getConnHndl((IIAPI_HNDL *)stmtHndl); API_PARSE *parse = (API_PARSE *)stmtHndl->sh_queryText; IIAPI_TRACE( IIAPI_TR_VERBOSE ) ( "IIapi_createGCNOper: creating GCN Oper message\n" ); if ( ! connHndl ) { IIAPI_TRACE( IIAPI_TR_FATAL ) ( "IIapi_createGCNOper: can't get connHndl from stmtHnd\n" ); return( NULL ); } if ( ! (msgBuff = IIapi_allocMsgBuffer( (IIAPI_HNDL *)connHndl )) ) return( NULL ); msgBuff->msgType = GCN_NS_OPER; msg = msgBuff->data + msgBuff->length; /* ** Set the operations flags. ** ** Netutil always sets the merge flag when adding ** nodes, so we will too. ** ** The user ID flag is set if a username was given ** for IIapi_connect() but no password. The Name ** Server will reject the request if current user ** not authorized. ** ** The public flag is set for global values. ** ** The network database flag is set for non-server ** requests. ** ** We currently don't support the sole server flag. ** The merge flag is only marginally supported. ** These flags are mostly used for adding servers, ** which is currently only supported as an ** undocumented feature. */ val = GCN_DEF_FLAG; /* gcn_flag */ if ( parse->opcode == API_KW_ADD && ( parse->object == API_KW_NODE || parse->object == API_KW_ATTR ) ) val |= GCN_MRG_FLAG; if ( connHndl->ch_username && ! connHndl->ch_password ) val |= GCN_UID_FLAG; if ( parse->type == API_KW_GLOBAL ) val |= GCN_PUB_FLAG; if ( parse->object != API_KW_SERVER ) val |= GCN_NET_FLAG; I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); switch( parse->opcode ) /* gcn_opcode */ { case API_KW_ADD : val = GCN_ADD; break; case API_KW_DEL : val = GCN_DEL; break; case API_KW_GET : val = GCN_RET; break; default : /* This should not happen! */ IIAPI_TRACE( IIAPI_TR_FATAL ) ( "IIapi_createGCNOper: invalid operations code.\n" ); val = GCN_RET; break; } I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); /* ** Installation ID is currently ignored. */ val = STlength( install_id ) + 1; /* gcn_install.gcn_l_item */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); MEcopy( install_id, val, msg ); /* gcn_install.gcn_value */ msg += val; msgBuff->length += val; val = 1; /* gcn_tup_cnt */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); /* ** Node and connection operations have fixed types ** defined by GCN. For server operations, the server ** class is used as provided by the application. */ switch( parse->object ) { case API_KW_NODE : str = GCN_NODE; break; case API_KW_LOGIN : str = GCN_LOGIN; break; case API_KW_ATTR : str = GCN_ATTR; break; case API_KW_SERVER : str = ns_resolve_param( parse, API_FIELD_OBJ, FALSE ); break; default : /* Should not happen! */ IIAPI_TRACE( IIAPI_TR_TRACE ) ( "IIapi_createGCNOper: invalid object.\n" ); str = empty; break; } /* ** Build the GCN tuple. */ val = STlength( str ) + 1; /* gcn_type.gcn_l_item */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); MEcopy( str, val, msg ); /* gcn_type.gcn_value */ msg += val; msgBuff->length += val; /* ** Use username if specified. This will ** either be the username we are connected ** with (if password also provided) or it ** will be the username for the GCN_UID_FLAG ** which requires special privileges for the ** current user. Otherwise, we use the user ** ID of the current process. */ if ( connHndl->ch_username ) str = connHndl->ch_username; else { if ( ! uid[0] ) { IDname( &puid ); STzapblank( uid, uid ); } str = uid; } val = STlength( str ) + 1; /* gcn_uid.gcn_l_item */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); MEcopy( str, val, msg ); /* gcn_uid.gcn_value */ msg += val; msgBuff->length += val; str = ns_resolve_param( parse, API_FIELD_VNODE, (parse->opcode != API_KW_ADD) ); val = STlength( str ) + 1; /* gcn_obj.gcn_l_item */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); MEcopy( str, val, msg ); /* gcn_obj.gcn_value */ msg += val; msgBuff->length += val; /* ** The tuple value must be built up from various parameters ** and can be function and object dependent. Call appropriate ** function for the current request to process the parameters. ** ** Pass in our temp buffer. It will be used if large enough ** or a different buffer will be allocated and returned. Check ** for memory allocation failures and free the returned buffer ** if it is not the one passed in (after copying the value). */ if ( ! (str = (*parse->parms->parms)( parse, sizeof( temp ), temp )) ) { IIapi_freeMsgBuffer( msgBuff ); return( NULL ); } val = STlength( str ) + 1; /* gcn_val.gcn_l_item */ I4ASSIGN_MACRO( val, *msg ); msg += sizeof( i4 ); msgBuff->length += sizeof( i4 ); MEcopy( str, val, msg ); /* gcn_val.gcn_value */ msgBuff->length += val; if ( str != temp ) MEfree( (PTR)str ); msgBuff->flags = IIAPI_MSG_EOD; return( msgBuff ); }
II_EXTERN II_ULONG IIapi_validDescriptor( IIAPI_STMTHNDL *stmtHndl, II_LONG descCount, IIAPI_DESCRIPTOR *descriptor ) { IIAPI_CONNHNDL *connHndl = IIapi_getConnHndl((IIAPI_HNDL *)stmtHndl); II_LONG i, svcparms = 0; /* ** Must have at least 1 descriptor. */ if ( descCount < 1 || ! descriptor ) return( E_AP0010_INVALID_COLUMN_COUNT ); switch( stmtHndl->sh_queryType ) { case IIAPI_QT_OPEN : /* ** 1 optional parameter: cursor name. */ if ( descriptor[ 0 ].ds_columnType == IIAPI_COL_SVCPARM && descriptor[ 0 ].ds_dataType != IIAPI_CHA_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); svcparms = 1; break; case IIAPI_QT_CURSOR_DELETE : /* ** 1 required parameters: cursor ID. ** No other parameters allowed. */ if ( descCount != 1 ) return( E_AP0010_INVALID_COLUMN_COUNT ); else if ( descriptor[ 0 ].ds_columnType != IIAPI_COL_SVCPARM ) return( E_AP0012_INVALID_DESCR_INFO ); else if ( descriptor[ 0 ].ds_dataType != IIAPI_HNDL_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); svcparms = 1; break; case IIAPI_QT_CURSOR_UPDATE : /* ** 1 required parameter: cursor ID. */ if ( descriptor[ 0 ].ds_columnType != IIAPI_COL_SVCPARM ) return( E_AP0012_INVALID_DESCR_INFO ); else if ( descriptor[ 0 ].ds_dataType != IIAPI_HNDL_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); svcparms = 1; break; case IIAPI_QT_EXEC_PROCEDURE : /* ** 1 required parameter: procedure name or ID. ** 1 optional parameter: procedure owner. */ if ( descriptor[ 0 ].ds_columnType != IIAPI_COL_SVCPARM ) return( E_AP0012_INVALID_DESCR_INFO ); else if ( descriptor[ 0 ].ds_dataType != IIAPI_CHA_TYPE && descriptor[ 0 ].ds_dataType != IIAPI_HNDL_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); else svcparms = 1; if ( descCount > 1 && descriptor[ 1 ].ds_columnType == IIAPI_COL_SVCPARM ) { if ( descriptor[ 0 ].ds_dataType == IIAPI_HNDL_TYPE || descriptor[ 1 ].ds_dataType != IIAPI_CHA_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); svcparms = 2; } break; case IIAPI_QT_DEF_REPEAT_QUERY : /* ** 3 optional parameters: query ID of 2 integers and a name. ** Must all be present or none. */ if ( descriptor[ 0 ].ds_columnType != IIAPI_COL_SVCPARM ) svcparms = 0; else if ( descCount < 3 ) return( E_AP0010_INVALID_COLUMN_COUNT ); else if ( descriptor[ 1 ].ds_columnType != IIAPI_COL_SVCPARM || descriptor[ 2 ].ds_columnType != IIAPI_COL_SVCPARM ) return( E_AP0012_INVALID_DESCR_INFO ); else if ( descriptor[ 0 ].ds_dataType != IIAPI_INT_TYPE || descriptor[ 1 ].ds_dataType != IIAPI_INT_TYPE || descriptor[ 2 ].ds_dataType != IIAPI_CHA_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); else svcparms = 3; break; case IIAPI_QT_EXEC_REPEAT_QUERY : /* ** 1 required parameter: repeat query ID. */ if ( descriptor[ 0 ].ds_columnType != IIAPI_COL_SVCPARM ) return( E_AP0012_INVALID_DESCR_INFO ); else if ( descriptor[ 0 ].ds_dataType != IIAPI_HNDL_TYPE ) return( E_AP0025_SVC_DATA_TYPE ); svcparms = 1; break; default : /* ** 0 required parameters. ** Optional parameters verified below. */ svcparms = 0; break; } /* ** Check remaining parameters. */ for( i = svcparms; i < descCount; i++ ) { /* ** Remaining parameters should be procedure parameters ** or regular query parameters. */ if ( stmtHndl->sh_queryType == IIAPI_QT_EXEC_PROCEDURE ) switch( descriptor[ i ].ds_columnType ) { case IIAPI_COL_PROCINPARM : break; case IIAPI_COL_PROCOUTPARM : case IIAPI_COL_PROCINOUTPARM : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_60 ) return( E_AP0020_BYREF_UNSUPPORTED ); break; case IIAPI_COL_PROCGTTPARM : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_62 ) return( E_AP0021_GTT_UNSUPPORTED ); break; default : return( E_AP0012_INVALID_DESCR_INFO ); } else if ( descriptor[ i ].ds_columnType != IIAPI_COL_QPARM ) return( E_AP0012_INVALID_DESCR_INFO ); switch( descriptor[ i ].ds_dataType ) { case IIAPI_INT_TYPE : switch( descriptor[ i ].ds_length ) { case 1 : case 2 : case 4 : break; case 8 : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_65 ) return( E_AP002A_LVL3_DATA_TYPE ); break; default : return( E_AP0024_INVALID_DATA_SIZE ); } break; case IIAPI_FLT_TYPE : switch( descriptor[ i ].ds_length ) { case 4 : case 8 : break; default : return( E_AP0024_INVALID_DATA_SIZE ); } break; case IIAPI_BYTE_TYPE : case IIAPI_VBYTE_TYPE : case IIAPI_LBYTE_TYPE : case IIAPI_LVCH_TYPE : case IIAPI_DEC_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_60 ) return( E_AP0028_LVL1_DATA_TYPE ); break; case IIAPI_NCHA_TYPE : case IIAPI_NVCH_TYPE : case IIAPI_LNVCH_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_64 ) return( E_AP0029_LVL2_DATA_TYPE ); break; case IIAPI_DATE_TYPE : case IIAPI_TIME_TYPE : case IIAPI_TMWO_TYPE : case IIAPI_TMTZ_TYPE : case IIAPI_TS_TYPE : case IIAPI_TSWO_TYPE : case IIAPI_TSTZ_TYPE : case IIAPI_INTYM_TYPE : case IIAPI_INTDS_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_66 ) return( E_AP002B_LVL4_DATA_TYPE ); break; case IIAPI_LCLOC_TYPE : case IIAPI_LBLOC_TYPE : case IIAPI_LNLOC_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_67 ) return( E_AP002C_LVL5_DATA_TYPE ); else if ( descriptor[ i ].ds_length != IIAPI_LOCATOR_LEN ) return( E_AP0024_INVALID_DATA_SIZE ); break; case IIAPI_BOOL_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_68 ) return( E_AP002D_LVL6_DATA_TYPE ); else if ( descriptor[ i ].ds_length != IIAPI_BOOL_LEN ) return( E_AP0024_INVALID_DATA_SIZE ); break; case IIAPI_GEOM_TYPE : case IIAPI_POINT_TYPE : case IIAPI_MPOINT_TYPE : case IIAPI_LINE_TYPE : case IIAPI_MLINE_TYPE : case IIAPI_POLY_TYPE : case IIAPI_MPOLY_TYPE : case IIAPI_NBR_TYPE : case IIAPI_GEOMC_TYPE : if ( connHndl && connHndl->ch_partnerProtocol < GCA_PROTOCOL_LEVEL_69 ) return( E_AP002E_LVL7_DATA_TYPE ); break; } } return( OK ); }