Skip to content

File cas_protocol.h

File List > broker > cas_protocol.h

Go to the documentation of this file

/*
 * Copyright 2008 Search Solution Corporation
 * Copyright 2016 CUBRID Corporation
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 *
 */


/*
 * cas_protocol.h -
 *
 * CAUTION!
 *
 * In case of common,  
 * cci repository source (src/cci/broker_cas_protocol.h) must be updated,
 * becuase CCI source and Engine source have been separated.
 */

#ifndef _CAS_PROTOCOL_H_
#define _CAS_PROTOCOL_H_

#ifdef __cplusplus
extern "C"
{
#endif

#ident "$Id$"

#define SRV_CON_CLIENT_INFO_SIZE    10
#define SRV_CON_CLIENT_MAGIC_LEN    5
#define SRV_CON_CLIENT_MAGIC_STR    "CUBRK"
#define SRV_CON_CLIENT_MAGIC_STR_SSL    "CUBRS"
#define SRV_CON_MSG_IDX_CLIENT_TYPE 5

#define IS_SSL_CLIENT(driver_info) \
        (strncmp (driver_info, SRV_CON_CLIENT_MAGIC_STR_SSL, SRV_CON_CLIENT_MAGIC_LEN) == 0)

/* 8th and 9th-byte (index 7 and 8) are reserved for backward compatibility.
 * 8.4.0 patch 1 or earlier versions hold minor and patch version on them.
 */
#define SRV_CON_MSG_IDX_PROTO_VERSION   6
#define SRV_CON_MSG_IDX_FUNCTION_FLAG   7
#define SRV_CON_MSG_IDX_RESERVED2       8
/* For backward compatibility */
#define SRV_CON_MSG_IDX_MAJOR_VER   (SRV_CON_MSG_IDX_PROTO_VERSION)
#define SRV_CON_MSG_IDX_MINOR_VER   (SRV_CON_MSG_IDX_FUNCTION_FLAG)
#define SRV_CON_MSG_IDX_PATCH_VER   (SRV_CON_MSG_IDX_RESERVED2)

#define SRV_CON_DBNAME_SIZE     32
#define SRV_CON_DBUSER_SIZE     32
#define SRV_CON_DBPASSWD_SIZE       32
#define SRV_CON_URL_SIZE                512
#define SRV_CON_DBSESS_ID_SIZE      20
#define SRV_CON_VER_STR_MAX_SIZE        20

#define SRV_CON_DB_INFO_SIZE \
        (SRV_CON_DBNAME_SIZE + SRV_CON_DBUSER_SIZE + SRV_CON_DBPASSWD_SIZE + \
         SRV_CON_URL_SIZE + SRV_CON_DBSESS_ID_SIZE)
#define SRV_CON_DB_INFO_SIZE_PRIOR_8_4_0 \
        (SRV_CON_DBNAME_SIZE + SRV_CON_DBUSER_SIZE + SRV_CON_DBPASSWD_SIZE + \
         SRV_CON_URL_SIZE)
#define SRV_CON_DB_INFO_SIZE_PRIOR_8_2_0 \
        (SRV_CON_DBNAME_SIZE + SRV_CON_DBUSER_SIZE + SRV_CON_DBPASSWD_SIZE)

  typedef enum
  {
    CAS_CLIENT_TYPE_MIN = 0,
    CAS_CLIENT_NONE = 0,
    CAS_CLIENT_CCI = 1,
    CAS_CLIENT_ODBC = 2,
    CAS_CLIENT_JDBC = 3,
    CAS_CLIENT_PHP = 4,
    CAS_CLIENT_OLEDB = 5,
    CAS_CLIENT_SERVER_SIDE_JDBC = 6,
    CAS_CLIENT_GATEWAY = 7,
    CAS_CLIENT_TYPE_MAX = 7
  } CAS_CLIENT_TYPE;

  typedef enum
  {
    CAS_INFO_STATUS_INACTIVE = 0,
    CAS_INFO_STATUS_ACTIVE = 1
  } CAS_INFO_STATUS_TYPE;

  typedef enum
  {
    CAS_INFO_STATUS = 0,
    CAS_INFO_RESERVED_1 = 1,
    CAS_INFO_RESERVED_2 = 2,
    CAS_INFO_ADDITIONAL_FLAG = 3
  } CAS_INFO_TYPE;

  typedef enum
  {
    CAS_CHANGE_MODE_UNKNOWN = 0,
    CAS_CHANGE_MODE_AUTO = 1,
    CAS_CHANGE_MODE_KEEP = 2,
    CAS_CHANGE_MODE_DEFAULT = CAS_CHANGE_MODE_AUTO
  } CAS_CHANGE_MODE;

  typedef int T_BROKER_VERSION;



#define CAS_INFO_FLAG_MASK_AUTOCOMMIT       0x01
#define CAS_INFO_FLAG_MASK_FORCE_OUT_TRAN       0x02
#define CAS_INFO_FLAG_MASK_NEW_SESSION_ID       0x04

#define CAS_INFO_SIZE           (4)
#define CAS_INFO_RESERVED_DEFAULT   (-1)

#define MAX_HA_DBINFO_LENGTH    (SRV_CON_DBNAME_SIZE + MAX_CONN_INFO_LENGTH)

#define MSG_HEADER_INFO_SIZE        CAS_INFO_SIZE
#define MSG_HEADER_MSG_SIZE         ((int) sizeof(int))
#define MSG_HEADER_SIZE             (MSG_HEADER_INFO_SIZE +  MSG_HEADER_MSG_SIZE)

#define BROKER_INFO_SIZE            8
#define BROKER_RENEWED_ERROR_CODE       0x80
#define BROKER_SUPPORT_HOLDABLE_RESULT          0x40
/* Do not remove or rename BROKER_RECONNECT_WHEN_SERVER_DOWN */
#define BROKER_RECONNECT_WHEN_SERVER_DOWN       0x20

/* For backward compatibility */
#define BROKER_INFO_MAJOR_VERSION               (BROKER_INFO_PROTO_VERSION)
#define BROKER_INFO_MINOR_VERSION               (BROKER_INFO_FUNCTION_FLAG)
#define BROKER_INFO_PATCH_VERSION               (BROKER_INFO_SYSTEM_PARAM)
#define BROKER_INFO_RESERVED                    (BROKER_INFO_RESERVED3)

#define CAS_PID_SIZE                            4
#define SESSION_ID_SIZE                         4
#define DRIVER_SESSION_SIZE         SRV_CON_DBSESS_ID_SIZE
#define CAS_CONNECTION_REPLY_SIZE_PRIOR_PROTOCOL_V3               (CAS_PID_SIZE + BROKER_INFO_SIZE + SESSION_ID_SIZE)
#define CAS_CONNECTION_REPLY_SIZE_V3               (CAS_PID_SIZE + BROKER_INFO_SIZE + DRIVER_SESSION_SIZE)
#define CAS_CONNECTION_REPLY_SIZE_V4               (CAS_PID_SIZE + CAS_PID_SIZE + BROKER_INFO_SIZE + DRIVER_SESSION_SIZE)
#define CAS_CONNECTION_REPLY_SIZE               CAS_CONNECTION_REPLY_SIZE_V4

#define CAS_KEEP_CONNECTION_ON                  1

#define CAS_GET_QUERY_INFO_PLAN         1

#define CAS_STATEMENT_POOLING_OFF       0
#define CAS_STATEMENT_POOLING_ON        1

#define CCI_PCONNECT_OFF                        0
#define CCI_PCONNECT_ON                         1

/* BITMASK for System Parameter */
#define MASK_ORACLE_COMPAT_NUMBER_BEHAVIOR      0x01    // oracle_compat_number_behavior

#define CAS_REQ_HEADER_JDBC "JDBC"
#define CAS_REQ_HEADER_ODBC "ODBC"
#define CAS_REQ_HEADER_PHP  "PHP"
#define CAS_REQ_HEADER_OLEDB    "OLEDB"
#define CAS_REQ_HEADER_CCI  "CCI"

#define SHARD_ID_INVALID        (-1)
#define SHARD_ID_UNSUPPORTED    (-2)

/* db_name used by client's broker health checker */
#define HEALTH_CHECK_DUMMY_DB "___health_check_dummy_db___"

  enum t_cas_func_code
  {
    CAS_FC_END_TRAN = 1,
    CAS_FC_PREPARE = 2,
    CAS_FC_EXECUTE = 3,
    CAS_FC_GET_DB_PARAMETER = 4,
    CAS_FC_SET_DB_PARAMETER = 5,
    CAS_FC_CLOSE_REQ_HANDLE = 6,
    CAS_FC_CURSOR = 7,
    CAS_FC_FETCH = 8,
    CAS_FC_SCHEMA_INFO = 9,
    CAS_FC_OID_GET = 10,
    CAS_FC_OID_PUT = 11,
    CAS_FC_DEPRECATED1 = 12,
    CAS_FC_DEPRECATED2 = 13,
    CAS_FC_DEPRECATED3 = 14,
    CAS_FC_GET_DB_VERSION = 15,
    CAS_FC_GET_CLASS_NUM_OBJS = 16,
    CAS_FC_OID_CMD = 17,
    CAS_FC_COLLECTION = 18,
    CAS_FC_NEXT_RESULT = 19,
    CAS_FC_EXECUTE_BATCH = 20,
    CAS_FC_EXECUTE_ARRAY = 21,
    CAS_FC_CURSOR_UPDATE = 22,
    CAS_FC_GET_ATTR_TYPE_STR = 23,
    CAS_FC_GET_QUERY_INFO = 24,
    CAS_FC_DEPRECATED4 = 25,
    CAS_FC_SAVEPOINT = 26,
    CAS_FC_PARAMETER_INFO = 27,
    CAS_FC_XA_PREPARE = 28,
    CAS_FC_XA_RECOVER = 29,
    CAS_FC_XA_END_TRAN = 30,
    CAS_FC_CON_CLOSE = 31,
    CAS_FC_CHECK_CAS = 32,
    CAS_FC_MAKE_OUT_RS = 33,
    CAS_FC_GET_GENERATED_KEYS = 34,
    CAS_FC_LOB_NEW = 35,
    CAS_FC_LOB_WRITE = 36,
    CAS_FC_LOB_READ = 37,
    CAS_FC_END_SESSION = 38,
    CAS_FC_GET_ROW_COUNT = 39,
    CAS_FC_GET_LAST_INSERT_ID = 40,
    CAS_FC_PREPARE_AND_EXECUTE = 41,
    CAS_FC_CURSOR_CLOSE = 42,
    CAS_FC_GET_SHARD_INFO = 43,
    CAS_FC_CAS_CHANGE_MODE = 44,

    /* Whenever you want to introduce a new function code, you must add a corresponding function entry to
     * server_fn_table of both CUBRID and (MySQL, Oracle). */
    CAS_FC_MAX,

    /* function code list of protocol version V2 - 9.0.0.xxxx */
    CAS_FC_CURSOR_CLOSE_FOR_PROTO_V2 = 41,
    CAS_FC_PREPARE_AND_EXECUTE_FOR_PROTO_V2 = 42
  };
  typedef enum t_cas_func_code T_CAS_FUNC_CODE;

  enum t_cas_protocol
  {
    PROTOCOL_V0 = 0,        /* old protocol */
    PROTOCOL_V1 = 1,        /* query_timeout and query_cancel */
    PROTOCOL_V2 = 2,        /* send columns meta-data with the result for executing */
    PROTOCOL_V3 = 3,        /* session information extend with server session key */
    PROTOCOL_V4 = 4,        /* send as_index to driver */
    PROTOCOL_V5 = 5,        /* shard feature, fetch end flag */
    PROTOCOL_V6 = 6,        /* cci/cas4m support unsigned integer type */
    PROTOCOL_V7 = 7,        /* timezone types, to pin xasl entry for retry */
    PROTOCOL_V8 = 8,        /* JSON type */
    PROTOCOL_V9 = 9,        /* cas health check: get function status */
    PROTOCOL_V10 = 10,      /* Secure Broker/CAS using SSL */
    PROTOCOL_V11 = 11,      /* make out resultset */
    PROTOCOL_V12 = 12,      /* Remove trailing zeros from double and float types */
    CURRENT_PROTOCOL = PROTOCOL_V12
  };
  typedef enum t_cas_protocol T_CAS_PROTOCOL;

  enum t_broker_info_pos
  {
    BROKER_INFO_DBMS_TYPE = 0,
    BROKER_INFO_KEEP_CONNECTION,
    BROKER_INFO_STATEMENT_POOLING,
    BROKER_INFO_CCI_PCONNECT,
    BROKER_INFO_PROTO_VERSION,
    BROKER_INFO_FUNCTION_FLAG,
    BROKER_INFO_SYSTEM_PARAM,
    BROKER_INFO_RESERVED3
  };
  typedef enum t_broker_info_pos T_BROKER_INFO_POS;

  enum t_driver_info_pos
  {
    DRIVER_INFO_MAGIC1 = 0,
    DRIVER_INFO_MAGIC2,
    DRIVER_INFO_MAGIC3,
    DRIVER_INFO_MAGIC4,
    DRIVER_INFO_MAGIC5,
    DRIVER_INFO_CLIENT_TYPE,
    DRIVER_INFO_PROTOCOL_VERSION,
    DRIVER_INFO_FUNCTION_FLAG,
    DRIVER_INFO_RESERVED,
  };
  typedef enum t_driver_info_pos T_DRIVER_INFO_POS;

  enum t_dbms_type
  {
    CAS_DBMS_NONE = 0,
    CAS_DBMS_CUBRID = 1,
    CAS_DBMS_MYSQL = 2,
    CAS_DBMS_ORACLE = 3,
    CAS_PROXY_DBMS_CUBRID = 4,
    CAS_PROXY_DBMS_MYSQL = 5,
    CAS_PROXY_DBMS_ORACLE = 6,
    CAS_CGW_DBMS_ORACLE = 7,
    CAS_CGW_DBMS_MYSQL = 8,
    CAS_CGW_DBMS_MARIADB = 9
  };
  typedef enum t_dbms_type T_DBMS_TYPE;
#define IS_CONNECTED_TO_PROXY(type) \
    ((type) == CAS_PROXY_DBMS_CUBRID \
    || (type) == CAS_PROXY_DBMS_MYSQL \
    || (type) == CAS_PROXY_DBMS_ORACLE)

#define IS_VALID_CAS_FC(fc) \
    (fc >= CAS_FC_END_TRAN && fc < CAS_FC_MAX)

/* Current protocol version */
#define CAS_PROTOCOL_VERSION    ((unsigned char)(CURRENT_PROTOCOL))

/* Indicates version variable holds CAS protocol version. */
#define CAS_PROTO_INDICATOR     (0x40)

/* Make a version to be used in CAS. */
#define CAS_PROTO_MAKE_VER(VER)         \
        ((T_BROKER_VERSION) (CAS_PROTO_INDICATOR << 24 | (VER)))
#define CAS_PROTO_CURRENT_VER           \
        ((T_BROKER_VERSION) CAS_PROTO_MAKE_VER(CURRENT_PROTOCOL))

#define DOES_CLIENT_MATCH_THE_PROTOCOL(CLIENT, MATCH) ((CLIENT) == CAS_PROTO_MAKE_VER((MATCH)))
#define DOES_CLIENT_UNDERSTAND_THE_PROTOCOL(CLIENT, REQUIRE) ((CLIENT) >= CAS_PROTO_MAKE_VER((REQUIRE)))

/* Pack/unpack CAS protocol version to/from network. */
#define CAS_PROTO_VER_MASK      (0x3F)
#define CAS_PROTO_PACK_NET_VER(VER)         \
        (char)((char)CAS_PROTO_INDICATOR | (char)(VER))
#define CAS_PROTO_UNPACK_NET_VER(VER)       \
        (CAS_PROTO_MAKE_VER(CAS_PROTO_VER_MASK & (char)(VER)))
#define CAS_PROTO_PACK_CURRENT_NET_VER      \
        CAS_PROTO_PACK_NET_VER(CURRENT_PROTOCOL)

#define CAS_CONV_ERROR_TO_OLD(V) (V + 9000)
#define CAS_CONV_ERROR_TO_NEW(V) (V - 9000)

#define CAS_MAKE_VER(MAJOR, MINOR, PATCH)       \
    ((T_BROKER_VERSION) (((MAJOR) << 16) | ((MINOR) << 8) | (PATCH)))

#define CAS_MAKE_PROTO_VER(DRIVER_INFO) \
    (((DRIVER_INFO)[SRV_CON_MSG_IDX_PROTO_VERSION]) & CAS_PROTO_INDICATOR) ? \
        CAS_PROTO_UNPACK_NET_VER ((DRIVER_INFO)[SRV_CON_MSG_IDX_PROTO_VERSION]) : \
        CAS_MAKE_VER ((DRIVER_INFO)[SRV_CON_MSG_IDX_MAJOR_VER], \
                      (DRIVER_INFO)[SRV_CON_MSG_IDX_MINOR_VER], \
                      (DRIVER_INFO)[SRV_CON_MSG_IDX_PATCH_VER])

#define CAS_TYPE_FIRST_BYTE_PROTOCOL_MASK 0x80

/* For backward compatibility */
#define CAS_VER_TO_MAJOR(VER)    ((int) (((VER) >> 16) & 0xFF))
#define CAS_VER_TO_MINOR(VER)    ((int) (((VER) >> 8) & 0xFF))
#define CAS_VER_TO_PATCH(VER)    ((int) ((VER) & 0xFF))
#define CAS_PROTO_TO_VER_STR(MSG_P, VER)            \
    do {                            \
            switch (VER)                    \
              {                         \
            case PROTOCOL_V1:                   \
                *((char **) (MSG_P)) = (char *) "8.4.1";    \
                break;                      \
            case PROTOCOL_V2:                   \
                *((char **) (MSG_P)) = (char *) "9.0.0";    \
                break;                      \
            case PROTOCOL_V3:                   \
                *((char **) (MSG_P)) = (char *) "8.4.3";    \
                break;                      \
            case PROTOCOL_V4:                   \
                *((char **) (MSG_P)) = (char *) "9.1.0";    \
                break;                      \
            default:                        \
                *((char **) (MSG_P)) = (char *) "";     \
                break;                      \
              }                         \
              } while (0)

  extern const char *cas_bi_get_broker_info (void);
  extern char cas_bi_get_dbms_type (void);
  extern void cas_bi_set_dbms_type (const char dbms_type);
  extern void cas_bi_set_keep_connection (const char keep_connection);
  extern char cas_bi_get_keep_connection (void);
  extern void cas_bi_set_statement_pooling (const char statement_pooling);
  extern char cas_bi_get_statement_pooling (void);
  extern void cas_bi_set_cci_pconnect (const char cci_pconnect);
  extern char cas_bi_get_cci_pconnect (void);
  extern void cas_bi_set_oracle_compat_number_behavior (char oracle_compat_number_behavior);
  extern void cas_bi_set_protocol_version (const char protocol_version);
  extern char cas_bi_get_protocol_version (void);
  extern void cas_bi_set_renewed_error_code (const bool renewed_error_code);
  extern bool cas_bi_get_renewed_error_code (void);
  extern bool cas_di_understand_renewed_error_code (const char *driver_info);
  extern void cas_bi_make_broker_info (char *broker_info, char dbms_type, char statement_pooling, char cci_pconnect,
                       char oracle_compat_number_behavior);
#ifdef __cplusplus
}
#endif

 /*
  * CAUTION!
  *
  * In case of common,  
  * cci repository source (src/cci/broker_cas_protocol.h) must be updated,
  * becuase CCI source and Engine source have been separated.
  */

#endif              /* _CAS_PROTOCOL_H_ */