#include "dpiImpl.h"
int dpiPool__acquireConnection(dpiPool *pool, const char *userName,
uint32_t userNameLength, const char *password, uint32_t passwordLength,
dpiConnCreateParams *params, dpiConn **conn, dpiError *error)
{
dpiConn *tempConn;
if (dpiGen__allocate(DPI_HTYPE_CONN, pool->env, (void**) &tempConn,
error) < 0)
return DPI_FAILURE;
error->env = pool->env;
if (dpiConn__create(tempConn, pool->env->context, userName, userNameLength,
password, passwordLength, pool->name, pool->nameLength, pool,
NULL, params, error) < 0) {
dpiConn__free(tempConn, error);
return DPI_FAILURE;
}
*conn = tempConn;
return DPI_SUCCESS;
}
static int dpiPool__checkConnected(dpiPool *pool, const char *fnName,
dpiError *error)
{
if (dpiGen__startPublicFn(pool, DPI_HTYPE_POOL, fnName, error) < 0)
return DPI_FAILURE;
if (!pool->handle)
return dpiError__set(error, "check pool", DPI_ERR_NOT_CONNECTED);
return DPI_SUCCESS;
}
static int dpiPool__create(dpiPool *pool, const char *userName,
uint32_t userNameLength, const char *password, uint32_t passwordLength,
const char *connectString, uint32_t connectStringLength,
const dpiCommonCreateParams *commonParams,
dpiPoolCreateParams *createParams, dpiError *error)
{
uint32_t poolMode;
uint8_t getMode;
void *authInfo;
if (createParams->externalAuth &&
((userName && userNameLength > 0) ||
(password && passwordLength > 0)))
return dpiError__set(error, "check mixed credentials",
DPI_ERR_EXT_AUTH_WITH_CREDENTIALS);
if (dpiOci__handleAlloc(pool->env->handle, &pool->handle,
DPI_OCI_HTYPE_SPOOL, "allocate pool handle", error) < 0)
return DPI_FAILURE;
poolMode = DPI_OCI_SPC_STMTCACHE;
if (createParams->homogeneous)
poolMode |= DPI_OCI_SPC_HOMOGENEOUS;
if (dpiOci__handleAlloc(pool->env->handle, &authInfo,
DPI_OCI_HTYPE_AUTHINFO, "allocate authinfo handle", error) < 0)
return DPI_FAILURE;
if (dpiUtils__setAttributesFromCommonCreateParams(authInfo,
DPI_OCI_HTYPE_AUTHINFO, commonParams, error) < 0)
return DPI_FAILURE;
if (createParams->plsqlFixupCallback &&
createParams->plsqlFixupCallbackLength > 0) {
if (dpiUtils__checkClientVersion(pool->env->versionInfo, 12, 2,
error) < 0)
return DPI_FAILURE;
if (dpiOci__attrSet(authInfo, DPI_OCI_HTYPE_AUTHINFO,
(void*) createParams->plsqlFixupCallback,
createParams->plsqlFixupCallbackLength,
DPI_OCI_ATTR_FIXUP_CALLBACK,
"set PL/SQL session state fixup callback", error) < 0)
return DPI_FAILURE;
}
if (dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, (void*) authInfo, 0,
DPI_OCI_ATTR_SPOOL_AUTH, "set auth info", error) < 0)
return DPI_FAILURE;
if (dpiOci__sessionPoolCreate(pool, connectString, connectStringLength,
createParams->minSessions, createParams->maxSessions,
createParams->sessionIncrement, userName, userNameLength, password,
passwordLength, poolMode, error) < 0)
return DPI_FAILURE;
getMode = (uint8_t) createParams->getMode;
if (dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, (void*) &getMode, 0,
DPI_OCI_ATTR_SPOOL_GETMODE, "set get mode", error) < 0)
return DPI_FAILURE;
if (dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, (void*)
&createParams->timeout, 0, DPI_OCI_ATTR_SPOOL_TIMEOUT,
"set timeout", error) < 0)
return DPI_FAILURE;
if (pool->env->versionInfo->versionNum > 12 ||
(pool->env->versionInfo->versionNum == 12 &&
pool->env->versionInfo->releaseNum >= 2)) {
if (dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, (void*)
&createParams->waitTimeout, 0, DPI_OCI_ATTR_SPOOL_WAIT_TIMEOUT,
"set wait timeout", error) < 0)
return DPI_FAILURE;
}
if (pool->env->versionInfo->versionNum >= 12) {
if (dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, (void*)
&createParams->maxLifetimeSession, 0,
DPI_OCI_ATTR_SPOOL_MAX_LIFETIME_SESSION,
"set max lifetime session", error) < 0)
return DPI_FAILURE;
}
pool->homogeneous = createParams->homogeneous;
pool->externalAuth = createParams->externalAuth;
pool->pingInterval = createParams->pingInterval;
pool->pingTimeout = createParams->pingTimeout;
return DPI_SUCCESS;
}
void dpiPool__free(dpiPool *pool, dpiError *error)
{
if (pool->handle) {
dpiOci__sessionPoolDestroy(pool, DPI_OCI_SPD_FORCE, 0, error);
pool->handle = NULL;
}
if (pool->env) {
dpiEnv__free(pool->env, error);
pool->env = NULL;
}
dpiUtils__freeMemory(pool);
}
static int dpiPool__getAttributeUint(dpiPool *pool, uint32_t attribute,
uint32_t *value, const char *fnName)
{
int status, supported = 1;
dpiError error;
if (dpiPool__checkConnected(pool, fnName, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
DPI_CHECK_PTR_NOT_NULL(pool, value)
switch (attribute) {
case DPI_OCI_ATTR_SPOOL_MAX_LIFETIME_SESSION:
if (pool->env->versionInfo->versionNum < 12)
supported = 0;
break;
case DPI_OCI_ATTR_SPOOL_WAIT_TIMEOUT:
if (pool->env->versionInfo->versionNum < 12 ||
(pool->env->versionInfo->versionNum == 12 &&
pool->env->versionInfo->releaseNum < 2))
supported = 0;
break;
case DPI_OCI_ATTR_SPOOL_BUSY_COUNT:
case DPI_OCI_ATTR_SPOOL_OPEN_COUNT:
case DPI_OCI_ATTR_SPOOL_STMTCACHESIZE:
case DPI_OCI_ATTR_SPOOL_TIMEOUT:
break;
default:
supported = 0;
break;
}
if (supported)
status = dpiOci__attrGet(pool->handle, DPI_OCI_HTYPE_SPOOL, value,
NULL, attribute, "get attribute value", &error);
else status = dpiError__set(&error, "get attribute value",
DPI_ERR_NOT_SUPPORTED);
return dpiGen__endPublicFn(pool, status, &error);
}
static int dpiPool__setAttributeUint(dpiPool *pool, uint32_t attribute,
uint32_t value, const char *fnName)
{
int status, supported = 1;
void *ociValue = &value;
uint8_t shortValue;
dpiError error;
if (dpiPool__checkConnected(pool, fnName, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
switch (attribute) {
case DPI_OCI_ATTR_SPOOL_GETMODE:
shortValue = (uint8_t) value;
ociValue = &shortValue;
break;
case DPI_OCI_ATTR_SPOOL_MAX_LIFETIME_SESSION:
if (pool->env->versionInfo->versionNum < 12)
supported = 0;
break;
case DPI_OCI_ATTR_SPOOL_WAIT_TIMEOUT:
if (pool->env->versionInfo->versionNum < 12 ||
(pool->env->versionInfo->versionNum == 12 &&
pool->env->versionInfo->releaseNum < 2))
supported = 0;
break;
case DPI_OCI_ATTR_SPOOL_STMTCACHESIZE:
case DPI_OCI_ATTR_SPOOL_TIMEOUT:
break;
default:
supported = 0;
break;
}
if (supported)
status = dpiOci__attrSet(pool->handle, DPI_OCI_HTYPE_SPOOL, ociValue,
0, attribute, "set attribute value", &error);
else status = dpiError__set(&error, "set attribute value",
DPI_ERR_NOT_SUPPORTED);
return dpiGen__endPublicFn(pool, status, &error);
}
int dpiPool_acquireConnection(dpiPool *pool, const char *userName,
uint32_t userNameLength, const char *password, uint32_t passwordLength,
dpiConnCreateParams *params, dpiConn **conn)
{
dpiConnCreateParams localParams;
dpiError error;
int status;
if (dpiPool__checkConnected(pool, __func__, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
DPI_CHECK_PTR_AND_LENGTH(pool, userName)
DPI_CHECK_PTR_AND_LENGTH(pool, password)
DPI_CHECK_PTR_NOT_NULL(pool, conn)
if (!params) {
dpiContext__initConnCreateParams(&localParams);
params = &localParams;
}
if (pool->externalAuth && userName && userNameLength > 0 &&
(userName[0] != '[' || userName[userNameLength - 1] != ']')) {
dpiError__set(&error, "verify proxy user name with external auth",
DPI_ERR_EXT_AUTH_INVALID_PROXY);
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error );
}
status = dpiPool__acquireConnection(pool, userName, userNameLength,
password, passwordLength, params, conn, &error);
return dpiGen__endPublicFn(pool, status, &error);
}
int dpiPool_addRef(dpiPool *pool)
{
return dpiGen__addRef(pool, DPI_HTYPE_POOL, __func__);
}
int dpiPool_close(dpiPool *pool, dpiPoolCloseMode mode)
{
dpiError error;
if (dpiPool__checkConnected(pool, __func__, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
if (dpiOci__sessionPoolDestroy(pool, mode, 1, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
return dpiGen__endPublicFn(pool, DPI_SUCCESS, &error);
}
int dpiPool_create(const dpiContext *context, const char *userName,
uint32_t userNameLength, const char *password, uint32_t passwordLength,
const char *connectString, uint32_t connectStringLength,
const dpiCommonCreateParams *commonParams,
dpiPoolCreateParams *createParams, dpiPool **pool)
{
dpiCommonCreateParams localCommonParams;
dpiPoolCreateParams localCreateParams;
dpiPool *tempPool;
dpiError error;
if (dpiGen__startPublicFn(context, DPI_HTYPE_CONTEXT, __func__,
&error) < 0)
return dpiGen__endPublicFn(context, DPI_FAILURE, &error);
DPI_CHECK_PTR_AND_LENGTH(context, userName)
DPI_CHECK_PTR_AND_LENGTH(context, password)
DPI_CHECK_PTR_AND_LENGTH(context, connectString)
DPI_CHECK_PTR_NOT_NULL(context, pool)
if (!commonParams) {
dpiContext__initCommonCreateParams(&localCommonParams);
commonParams = &localCommonParams;
}
if (!createParams || context->dpiMinorVersion < 1) {
dpiContext__initPoolCreateParams(&localCreateParams);
if (createParams)
memcpy(&localCreateParams, createParams,
sizeof(dpiPoolCreateParams__v30));
createParams = &localCreateParams;
}
if (dpiGen__allocate(DPI_HTYPE_POOL, NULL, (void**) &tempPool, &error) < 0)
return dpiGen__endPublicFn(context, DPI_FAILURE, &error);
if (dpiEnv__init(tempPool->env, context, commonParams, &error) < 0) {
dpiPool__free(tempPool, &error);
return dpiGen__endPublicFn(context, DPI_FAILURE, &error);
}
if (dpiPool__create(tempPool, userName, userNameLength, password,
passwordLength, connectString, connectStringLength, commonParams,
createParams, &error) < 0) {
dpiPool__free(tempPool, &error);
return dpiGen__endPublicFn(context, DPI_FAILURE, &error);
}
createParams->outPoolName = tempPool->name;
createParams->outPoolNameLength = tempPool->nameLength;
*pool = tempPool;
dpiHandlePool__release(tempPool->env->errorHandles, &error.handle);
return dpiGen__endPublicFn(context, DPI_SUCCESS, &error);
}
int dpiPool_getBusyCount(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool, DPI_OCI_ATTR_SPOOL_BUSY_COUNT,
value, __func__);
}
int dpiPool_getEncodingInfo(dpiPool *pool, dpiEncodingInfo *info)
{
dpiError error;
int status;
if (dpiPool__checkConnected(pool, __func__, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
DPI_CHECK_PTR_NOT_NULL(pool, info)
status = dpiEnv__getEncodingInfo(pool->env, info);
return dpiGen__endPublicFn(pool, status, &error);
}
int dpiPool_getGetMode(dpiPool *pool, dpiPoolGetMode *value)
{
dpiError error;
if (dpiPool__checkConnected(pool, __func__, &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
DPI_CHECK_PTR_NOT_NULL(pool, value)
if (dpiOci__attrGet(pool->handle, DPI_OCI_HTYPE_SPOOL, value, NULL,
DPI_OCI_ATTR_SPOOL_GETMODE, "get attribute value", &error) < 0)
return dpiGen__endPublicFn(pool, DPI_FAILURE, &error);
return dpiGen__endPublicFn(pool, DPI_SUCCESS, &error);
}
int dpiPool_getMaxLifetimeSession(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool,
DPI_OCI_ATTR_SPOOL_MAX_LIFETIME_SESSION, value, __func__);
}
int dpiPool_getOpenCount(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool, DPI_OCI_ATTR_SPOOL_OPEN_COUNT,
value, __func__);
}
int dpiPool_getStmtCacheSize(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool, DPI_OCI_ATTR_SPOOL_STMTCACHESIZE,
value, __func__);
}
int dpiPool_getTimeout(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool, DPI_OCI_ATTR_SPOOL_TIMEOUT, value,
__func__);
}
int dpiPool_getWaitTimeout(dpiPool *pool, uint32_t *value)
{
return dpiPool__getAttributeUint(pool, DPI_OCI_ATTR_SPOOL_WAIT_TIMEOUT,
value, __func__);
}
int dpiPool_release(dpiPool *pool)
{
return dpiGen__release(pool, DPI_HTYPE_POOL, __func__);
}
int dpiPool_setGetMode(dpiPool *pool, dpiPoolGetMode value)
{
return dpiPool__setAttributeUint(pool, DPI_OCI_ATTR_SPOOL_GETMODE, value,
__func__);
}
int dpiPool_setMaxLifetimeSession(dpiPool *pool, uint32_t value)
{
return dpiPool__setAttributeUint(pool,
DPI_OCI_ATTR_SPOOL_MAX_LIFETIME_SESSION, value, __func__);
}
int dpiPool_setStmtCacheSize(dpiPool *pool, uint32_t value)
{
return dpiPool__setAttributeUint(pool, DPI_OCI_ATTR_SPOOL_STMTCACHESIZE,
value, __func__);
}
int dpiPool_setTimeout(dpiPool *pool, uint32_t value)
{
return dpiPool__setAttributeUint(pool, DPI_OCI_ATTR_SPOOL_TIMEOUT, value,
__func__);
}
int dpiPool_setWaitTimeout(dpiPool *pool, uint32_t value)
{
return dpiPool__setAttributeUint(pool, DPI_OCI_ATTR_SPOOL_WAIT_TIMEOUT,
value, __func__);
}