Exemple #1
0
/*
** Returns the statement type
*/
static int get_statement_type(cur_data* cur)
{
    int length, type;
    char type_item[] = { isc_info_sql_stmt_type };
    char res_buffer[88], *pres;

    pres = res_buffer;

    isc_dsql_sql_info( cur->env->status_vector, &cur->stmt,
                       sizeof(type_item), type_item,
                       sizeof(res_buffer), res_buffer );
    if (cur->env->status_vector[0] == 1 && cur->env->status_vector[1] > 0)
        return -1;

    /* check the type of the statement */
    if (*pres == isc_info_sql_stmt_type)
    {
        pres++;
        length = isc_vax_integer(pres, 2);
        pres += 2;
        type = isc_vax_integer(pres, length);
        pres += length;
    } else
        return -2;	/* should have had the isc_info_sql_stmt_type info */

    return type;
}
int fb_affected_rows(rlm_sql_firebird_conn_t *conn) {
	static char count_info[] = {isc_info_sql_records};
	char info_buffer[128];
	char *p ;
	int affected_rows = -1;

	if (!conn->stmt) return -1;

	isc_dsql_sql_info(conn->status, &conn->stmt,
			  sizeof (count_info), count_info,
			  sizeof (info_buffer), info_buffer);

	if (IS_ISC_ERROR(conn->status)) {
		return fb_error(conn);
	}

	p = info_buffer + 3;
	while (*p != isc_info_end) {
		p++;
		short len = (short)isc_vax_integer(p, 2);
		p += 2;

		affected_rows = isc_vax_integer(p, len);
		if (affected_rows > 0) {
			break;
		}
		p += len;
	}
	return affected_rows;
}
static int fb_prepare(rlm_sql_firebird_conn_t *conn, char const *query)
{
	static char stmt_info[] = { isc_info_sql_stmt_type };
	char info_buffer[128];
	short l;

	if (!conn->trh) {
		isc_start_transaction(conn->status, &conn->trh, 1, &conn->dbh,
				      conn->tpb_len, conn->tpb);
		if (!conn->trh) {
			return -4;
		}
	}

	fb_free_statement(conn);
	if (!conn->stmt) {
		isc_dsql_allocate_statement(conn->status, &conn->dbh,
					    &conn->stmt);
		if (!conn->stmt) {
			return -1;
		}
	}

	fb_free_sqlda(conn->sqlda_out);
	isc_dsql_prepare(conn->status, &conn->trh, &conn->stmt, 0, query,
			 conn->sql_dialect, conn->sqlda_out);
	if (IS_ISC_ERROR(conn->status)) {
		return -2;
	}

	if (conn->sqlda_out->sqln<conn->sqlda_out->sqld) {
		conn->sqlda_out->sqln = conn->sqlda_out->sqld;
		conn->sqlda_out = (XSQLDA ISC_FAR *) realloc(conn->sqlda_out,
							     XSQLDA_LENGTH(conn->sqlda_out->sqld));
		isc_dsql_describe(conn->status, &conn->stmt, SQL_DIALECT_V6,
				  conn->sqlda_out);

		if (IS_ISC_ERROR(conn->status)) {
			return -3;
		}
	}
	/*
	 *	Get statement type
	 */
	isc_dsql_sql_info(conn->status, &conn->stmt, sizeof(stmt_info),
			  stmt_info, sizeof(info_buffer), info_buffer);
	if (IS_ISC_ERROR(conn->status)) return -4;

	l = (short) isc_vax_integer((char ISC_FAR *) info_buffer + 1, 2);
	conn->statement_type = isc_vax_integer((char ISC_FAR *) info_buffer + 3,
					       l);

	if (conn->sqlda_out->sqld) {
		fb_set_sqlda(conn->sqlda_out); //set out sqlda
	}

	return 0;
}
int
IB_Statement::statementType()
{
  if (isc_dsql_sql_info (status_->vector(),
			 &stmtHandle_,
			 sizeof (stmtTypeInfoRequest__),
			 (IB_BUFF_PTR) stmtTypeInfoRequest__,
			 stmtTypeRequestedInfoSize__,
			 stmtTypeRequestedInfo_))
    throw new IB_SQLException (IB_SQLException::engine__default_0__, status_);

  return IB_Information::getInteger (stmtTypeRequestedInfo_ + 1);
}
IB_SLONG32
IB_Statement::getUpdateCount ()
{
  int countType = 0;

  // Get the statement type count indicator as it will appear
  // in the requested info buffer.
  switch (stmtType_) {
  case isc_info_sql_stmt_update:
    countType = isc_info_req_update_count;
    break;
  case isc_info_sql_stmt_delete:
    countType = isc_info_req_delete_count;
    break;
  case isc_info_sql_stmt_insert:
    countType = isc_info_req_insert_count;
    break;
  case isc_info_sql_stmt_select:
    countType = isc_info_req_select_count;
    break;
  default:
    return 0;
  }

  if (isc_dsql_sql_info (status_->vector(),
			 &stmtHandle_,
			 sizeof (rowCountsInfoRequest__),
			 (IB_BUFF_PTR) rowCountsInfoRequest__,
			 rowCountsRequestedInfoSize__,
			 rowCountsRequestedInfo_))
    throw new IB_SQLException (IB_SQLException::engine__default_0__, status_);

  int rowCountLength;
  int countTypeIndicator=0;
  IB_SLONG32 count = 0;
  // skip over isc_info_sql_records, and overall 2 byte length field  
  IB_BUFF_PTR iterator = rowCountsRequestedInfo_ + 3; 
  while (*iterator != isc_info_end) {
    countTypeIndicator = *iterator++;
    // !!! should call IB_Information::getInteger() here.
    // HP-UX port (old CC): added type cast (int)
    rowCountLength = (int) isc_vax_integer (iterator, 2);
    iterator += 2; // skip over rowCountLength
    count = isc_vax_integer (iterator, rowCountLength);
    iterator += rowCountLength; // skip over rowCount
    if (countTypeIndicator == countType)  // found it
      break;
  }
  return count;
}
Exemple #6
0
    // Returns number of rows afected by last statement
    // or -1 if there is no such counter available.
    long getRowCount(soci::statement & statement, eRowCountType type)
    {
        ISC_STATUS stat[20];
        char cnt_req[2], cnt_info[128];

        cnt_req[0]=isc_info_sql_records;
        cnt_req[1]=isc_info_end;

        firebird_statement_backend* statementBackEnd
            = static_cast<firebird_statement_backend*>(statement.get_backend());

        // Note: This is very poorly documented function.
        // It can extract number of rows returned by select statement,
        // but it appears that this is only number of rows prefetched by
        // client library, not total number of selected rows.
        if (isc_dsql_sql_info(stat, &statementBackEnd->stmtp_, sizeof(cnt_req),
                              cnt_req, sizeof(cnt_info), cnt_info))
        {
            soci::details::firebird::throw_iscerror(stat);
        }

        long count = -1;
        char type_ = static_cast<char>(type);
        for (char *ptr = cnt_info + 3; *ptr != isc_info_end;)
        {
            char count_type = *ptr++;
            int m = isc_vax_integer(ptr, 2);
            ptr += 2;
            count = isc_vax_integer(ptr, m);

            if (count_type == type_)
            {
                // this is requested number
                break;
            }
            ptr += m;
        }

        return count;
    }
Exemple #7
0
/*
** Return the number of rows affected by last operation
*/
static int count_rows_affected(cur_data* cur)
{
    int length, type, res=0;
    int del_count = 0, ins_count = 0, upd_count = 0, sel_count = 0;
    char type_item[] = { isc_info_sql_stmt_type, isc_info_sql_records };
    char res_buffer[88], *pres;

    pres = res_buffer;

    isc_dsql_sql_info( cur->env->status_vector, &cur->stmt,
                       sizeof(type_item), type_item,
                       sizeof(res_buffer), res_buffer );
    if (cur->env->status_vector[0] == 1 && cur->env->status_vector[1] > 0)
        return -1;

    /* check the type of the statement */
    if (*pres == isc_info_sql_stmt_type)
    {
        pres++;
        length = isc_vax_integer(pres, 2);
        pres += 2;
        type = isc_vax_integer(pres, length);
        pres += length;
    } else
        return -2;	/* should have had the isc_info_sql_stmt_type info */

    if(type > 4)
        return 0;	/* not a SELECT, INSERT, UPDATE or DELETE SQL statement */

    if (*pres == isc_info_sql_records)
    {
        pres++;
        length = isc_vax_integer(pres, 2); /* normally 29 bytes */
        pres += 2;

        while(*pres != 1) {
            switch(*pres) {
            case isc_info_req_select_count:
                pres++;
                length = isc_vax_integer(pres, 2);
                pres += 2;
                sel_count = isc_vax_integer(pres, length);
                pres += length;
                break;
            case isc_info_req_insert_count:
                pres++;
                length = isc_vax_integer(pres, 2);
                pres += 2;
                ins_count = isc_vax_integer(pres, length);
                pres += length;
                break;
            case isc_info_req_update_count:
                pres++;
                length = isc_vax_integer(pres, 2);
                pres += 2;
                upd_count = isc_vax_integer(pres, length);
                pres += length;
                break;
            case isc_info_req_delete_count:
                pres++;
                length = isc_vax_integer(pres, 2);
                pres += 2;
                del_count = isc_vax_integer(pres, length);
                pres += length;
                break;
            default:
                pres++;
                break;
            }
        }
    } else
        return -3;

    switch(type) {
    case isc_info_sql_stmt_select:
        res = sel_count;
        break;
    case isc_info_sql_stmt_delete:
        res = del_count;
        break;
    case isc_info_sql_stmt_update:
        res = upd_count;
        break;
    case isc_info_sql_stmt_insert:
        res = ins_count;
        break;
    }
    return res;
}