通讯区域提供了SQL语句和数据库之间通信的桥梁!Oracle提供了两个通信区,分别是sqlca以及oraca!!!
在Proc使用通讯区,要么用#include命令包含到源代码中,要么用嵌入式SQL语句包含到代码中:
EXEC SQL INCLUDE sqlca;
SQLCA
- SQLCA 是ORACLE提供的两个通信区之一。
- SQLCA实际上是一个结构体变量,其目的是为了诊断错误和事件处理结果。
- 原型及其解释
struct sqlca
{
char sqlcaid[8];//被初始化唯sqlca,标识SQL通讯区
long sqlabc;//SQL通讯区的长度
//最近执行的SQL语句的状态码
//0:正确执行
//>0:执行了语句,但没有记录行返回
//<0:数据库,系统,网络故障,SQL语句没有执行
long sqlcode;
struct
{
unsigned short sqlerrml;//sqlerrmc中文本长度
//与sqlcode一致的对应的错误信息文本
//只有当sqlcode<0才能访问,否则是上次错误信息
char sqlerrmc[70];
}sqlerrm;
char sqlerrp[8];//保留字段,没有使用
//sqlerrd[0],sqlerrd[1]没有使用
//sqlerrd[2]SQL语句处理的行数,如果SQL执行失败,则没有定义
//sqlerrd[3]没有使用
//sqlerrd[4]出现语法分析错误的字符开始位置,第一个位置是0
//sqlerrd[5]没有使用
long sqlerrd[6];
//警告标记
//sqlwarn[0]其他警告标记设置,该标记就被设置
//sqlwarn[1]字段值被截断输出到宿主变量的时候被设置
//sqlwarn[2]没有使用
//sqlwarn[3]查询字段个数不等于宿主变量个数的时候被设置
//sqlwarn[4]表中记录被没有where子句的delete,update处理的时候被设置
//sqlwarn[5]当EXEC SQL CREATE{PROCDURE|FUNCTION|PACKAGE}语句编译错误的时候被设置
//sqlwarn[6],sqlwarn[7]没有被使用
char sqlwarn[8];
char sqlext[8];//没有被使用
};
struct sqlca sqlca;
对于sqlerrd[6]
- 0,1 ,3,5-系统保留
- 2 -当前SQL指令处理的行数
- 4 -保存相对位移,指出在什么地方出现语法错误
sqlcode用于保存最近一次运行SQL指令的状态
返回结果 | 说明 |
---|---|
0 | 正常 |
>0 | 有一个异常发生 |
<0 | 系统错误,可能来自网络,或数据库本身 |
- 对于sqlwarn[8]
- 0-指示是否设置了警告标志
- 1-指示是否将字符结果返回给宿主变量时,数据截短了
- 3-如果查询时,返回的列数和指定的宿主数组变量的维数不等时设置该位
- 4-UPDATE和DELETE时没有行被处理,设置改标志位
- 5-当EXEC SQL CREATE {PROCEDURE|FUNCTION|PACKAGE|PACKAGE BODY}失败时,设置该位
- 2,6,7-系统保留
- 示例
void main(){
…
EXEC SQL INCLUDE sqlca;
…
EXEC SQL WHENEVER SQLERROR Do err_report(sqlca);
…
}
void err_report( struct sqlca sqlca)
{
if (sqlca.sqlcode < 0)
printf("\n%d - %s\n\n",sqlca.sqlerrm.sqlerrml,sqlca.sqlerrm.sqlerrmc);
exit(1);
}
ORACA
当需要更进一步的信息时,ORACA将帮助我们达成愿望,所以ORACA也可以看作时SQLCA的补充和辅助.
struct oraca
{
/* text */ char oracaid[8]; /* Reserved */
/* ub4 */ int oracabc; /* Reserved */
/* ub4 */ int oracchf; /* <> 0 if "check cur cache consistncy"*/
/* ub4 */ int oradbgf; /* <> 0 if "do DEBUG mode checking" */
/* ub4 */ int orahchf; /* <> 0 if "do Heap consistency check" */
/* ub4 */ int orastxtf; /* SQL stmt text flag */
struct {
/* ub2 */ unsigned short orastxtl;
/* text */ char orastxtc[70];
} orastxt; /* text of last SQL stmt */
struct {
/* ub2 */ unsigned short orasfnml;
/* text */ char orasfnmc[70];
} orasfnm; /* name of file containing SQL stmt */
/* ub4 */ int oraslnr; /* line nr-within-file of SQL stmt */
/* ub4 */ int orahoc; /* highest max open OraCurs requested */
/* ub4 */ int oramoc; /* max open OraCursors required */
/* ub4 */ int oracoc; /* current OraCursors open */
/* ub4 */ int oranor; /* nr of OraCursor re-assignments */
/* ub4 */ int oranpr; /* nr of parses */
/* ub4 */ int oranex; /* nr of executes */
};
结构体成员及其说明:
oracaid[8] 标识一个ORACA通信区
oracabc用于保存ORACA通信区的长度
oradbgf调试标志,0-关闭,1-开启
oracchf
- 如果oradbgf=1,那oracchf遵循下列规则:
- 0-禁止光标缓冲一致性检查
- 1-进行光标缓冲一致性检查
- orahchf如果oradbgf=1,那oracchf遵循下列规则:
- 0-禁止堆缓冲一致性检查
- 1-进行堆缓冲一致性检查
- 如果oradbgf=1,那oracchf遵循下列规则:
orastxtf可以是以下各值:
- 0-不保存SQL文本
- 1-仅对SQLERROR保存SQL文本
- 2-仅对SQLERROR和SQLWARNING保存SQL文本
- 3-总是保存SQL文本
- orastxt.orastxtl当前SQL语句的长度
- orastxt. orasfnmc[70]SQL文本,最多70字符
orasfnm
- orasfnm.orasfnml保存源文件名长度
- orasfnm.orasfnmc保存源文件名,最长70字符
oraslnr标识当前SQL语句所在行的行号
orahoc运行时最多能打开的光标数
- oramoc运行时对多需要打开的光标数
- oracoc当前打开的光标数
- oranor记录光标缓冲池的再赋值次数
- oranpr记录SQL语句分析次数
oranex记录SQL语句执行的次数
要使用ORACA,那么就要显式的加载ORACA结构到Pro*C程序中。可通过语句
EXEC SQL INCLUDE oraca;
EXEC ORACLE OPTION(ORACA=YES);
利用通讯区显示错误信息
//错误SQL语言给打印出来
void sqlerr02()
{
char stm[120];
size_t sqlfc, stmlen=120;
unsigned int ret = 0;
printf("func sqlerr02() begin\n");
//出错时,可以把错误SQL语言给打印出来
EXEC SQL WHENEVER SQLERROR CONTINUE;
ret = sqlgls(stm, &stmlen, &sqlfc);
/*
if (ret != 0)
{
printf("func sqlgls() err, %d \n", ret);
return ;
}*/
printf("中国\n");
printf("出错的SQL:%.*s\n", stmlen, stm);
printf("出错原因:%.*s\n", sqlca.sqlerrm.sqlerrml, sqlca.sqlerrm.sqlerrmc);
//printf("出错原因:%.70s\n", sqlca.sqlerrm.sqlerrml, sqlca.sqlerrm.sqlerrmc);
EXEC SQL ROLLBACK WORK RELEASE;
printf("func sqlerr02() end\n");
exit(1);
}