Skip to content

Instantly share code, notes, and snippets.

@kubo
Created September 19, 2018 14:10
Show Gist options
  • Save kubo/d5aa0ad913a57a9322748b198a4dd5ce to your computer and use it in GitHub Desktop.
Save kubo/d5aa0ad913a57a9322748b198a4dd5ce to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <oci.h>
/*
Run the following SQL in advance.
drop table clob_test_1755 purge;
create table clob_test_1755 (clob_col clob);
insert into clob_test_1755 values (empty_clob());
commit;
*/
/* Change the following three values */
const char *username = "username";
const char *password = "password";
const char *database = "";
static void checkerr(void *handle, ub4 htype, sword status, const char *func)
{
text errbuf[512];
sb4 errcode = 0;
switch (status) {
case OCI_SUCCESS:
case OCI_SUCCESS_WITH_INFO:
return;
break;
case OCI_NEED_DATA:
printf(" %s => OCI_NEED_DATA\n", func);
break;
case OCI_NO_DATA:
printf(" %s => OCI_NO_DATA\n", func);
break;
case OCI_ERROR:
OCIErrorGet(handle, 1, NULL, &errcode, errbuf, sizeof(errbuf), htype);
printf(" %s => OCI_ERROR\n %.*s\n", func, (int)sizeof(errbuf), errbuf);
break;
case OCI_INVALID_HANDLE:
printf(" %s => OCI_INVALID_HANDLE\n", func);
break;
case OCI_STILL_EXECUTING:
printf(" %s => OCI_STILL_EXECUTE\n", func);
break;
case OCI_CONTINUE:
printf(" %s => OCI_CONTINUE\n", func);
break;
default:
printf(" %s => Unknown %d\n", func, status);
}
exit(1);
}
#define chke(func) do { \
sword status = (func); \
if (status != OCI_SUCCESS) { \
checkerr(envhp, OCI_HTYPE_ENV, status, #func); \
} \
} while (0)
#define chk(func) do { \
sword status = (func); \
if (status != OCI_SUCCESS) { \
checkerr(errhp, OCI_HTYPE_ERROR, status, #func); \
} \
} while (0)
static void read_lob_using_OCILobRead2(OCISvcCtx *svchp, OCIError *errhp, OCILobLocator *lob);
static void read_lob_using_OCILobArrayRead(OCISvcCtx *svchp, OCIError *errhp, OCILobLocator *lob);
int main()
{
OCIEnv *envhp;
OCISvcCtx *svchp;
OCIServer *srvhp;
OCISession *seshp;
OCIError *errhp;
OCIStmt *stmtp;
OCIDefine *defnp;
const char *sql = "select clob_col from clob_test_1755";
OCILobLocator *lob;
/* allocate handles */
chke(OCIEnvCreate(&envhp, OCI_DEFAULT, NULL, NULL, NULL, NULL, 0, NULL));
chke(OCIHandleAlloc(envhp, (dvoid**)&svchp, OCI_HTYPE_SVCCTX, 0, NULL));
chke(OCIHandleAlloc(envhp, (dvoid**)&srvhp, OCI_HTYPE_SERVER, 0, NULL));
chke(OCIHandleAlloc(envhp, (dvoid**)&seshp, OCI_HTYPE_SESSION, 0, NULL));
chke(OCIHandleAlloc(envhp, (dvoid**)&errhp, OCI_HTYPE_ERROR, 0, NULL));
chke(OCIDescriptorAlloc(envhp, (dvoid**)&lob, OCI_DTYPE_LOB, 0, NULL));
/* connect */
chk(OCIServerAttach(srvhp, errhp, (const text*)database, strlen(database), OCI_DEFAULT));
chk(OCIAttrSet(seshp, OCI_HTYPE_SESSION, (void*)username, strlen(username), OCI_ATTR_USERNAME, errhp));
chk(OCIAttrSet(seshp, OCI_HTYPE_SESSION, (void*)password, strlen(password), OCI_ATTR_PASSWORD, errhp));
chk(OCIAttrSet(svchp, OCI_HTYPE_SVCCTX, srvhp, 0, OCI_ATTR_SERVER, errhp));
chk(OCIAttrSet(svchp, OCI_HTYPE_SVCCTX, seshp, 0, OCI_ATTR_SESSION, errhp));
chk(OCISessionBegin(svchp, errhp, seshp, OCI_CRED_RDBMS, OCI_DEFAULT));
/* prepare, execute and fetch */
chk(OCIStmtPrepare2(svchp, &stmtp, errhp, (const text*)sql, strlen(sql), NULL, 0, OCI_NTV_SYNTAX, OCI_DEFAULT));
chk(OCIDefineByPos(stmtp, &defnp, errhp, 1, &lob, 0, SQLT_CLOB, NULL, NULL, NULL, OCI_DEFAULT));
chk(OCIStmtExecute(svchp, stmtp, errhp, 0, 0, NULL, NULL, OCI_DEFAULT));
chk(OCIStmtFetch(stmtp, errhp, 1, OCI_FETCH_NEXT, OCI_DEFAULT));
read_lob_using_OCILobRead2(svchp, errhp, lob);
read_lob_using_OCILobArrayRead(svchp, errhp, lob);
return 0;
}
static void read_lob_using_OCILobRead2(OCISvcCtx *svchp, OCIError *errhp, OCILobLocator *lob)
{
oraub8 byte_amt = 0;
oraub8 char_amt = UB4MAXVAL;
char buf[50];
chk(OCILobRead2(svchp, errhp, lob, &byte_amt, &char_amt, 1, buf, sizeof(buf), OCI_ONE_PIECE, NULL, NULL, 0, SQLCS_IMPLICIT));
printf("len=%d, data='%.*s'\n", (int)byte_amt, (int)byte_amt, buf);
}
static void read_lob_using_OCILobArrayRead(OCISvcCtx *svchp, OCIError *errhp, OCILobLocator *lob)
{
ub4 array_iter = 1;
OCILobLocator *lobp_arr[1];
oraub8 byte_amt_arr[1];
oraub8 char_amt_arr[1];
oraub8 offset_arr[1];
void *bufp_arr[1];
oraub8 bufl_arr[1];
char buf[50];
lobp_arr[0] = lob;
byte_amt_arr[0] = 0;
char_amt_arr[0] = UB4MAXVAL;
offset_arr[0] = 1;
bufp_arr[0] = buf;
bufl_arr[0] = sizeof(buf);
chk(OCILobArrayRead(svchp, errhp, &array_iter, lobp_arr, byte_amt_arr, char_amt_arr, offset_arr, bufp_arr, bufl_arr, OCI_ONE_PIECE, NULL, NULL, 0, SQLCS_IMPLICIT));
printf("len=%d, data='%.*s'\n", (int)byte_amt_arr[0], (int)byte_amt_arr[0], buf);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment