PRO*C編譯

 

這裏假設用戶的oracle已經安裝完成了並且可以正確運行。<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

    本文檔包括fetch.pcmakefileproc.txt 3個文件。

    fetch.pcproc源文件,詳細註釋在文件中。

    makefilemake文件,目前我也不是很懂。

    proc.txt就是本文件,主要說明環境配置。

    可以用env|less查看當前用戶的環境配置,注意看有沒有以下2個:

        LD_LIBRARY_PATH=$(ORACLE_HOME)/lib

        PATH=$(ORACLE_HOME)/BIN

        ORACLE_HOME=/opt/oracle/product/9.0.1

    如果沒有,可以用export命令加上。命令用法如下:

        export LD_LIBRARY_PATH=$(ORACLE_HOME)/lib,爲了保險起見,可以把$(ORACLE_HOME)用實際路徑代替,如下:

        export LD_LIBRARY_PATH=/opt/oracle/product/9.0.1/lib

    同理加上PATHORACLE_HOME。注意,PATH中原來就有其他路徑,應該把其他路徑加上,否則會覆蓋掉原來的路徑。例如,原來PATH中有/usr/bin,則export命令應該這樣:

        export PATH=/opt/oracle/product/9.0.1/bin:/usr/bin

:分號可以連接多個路徑。

    LD_LIBRARY_PATH沒有的話會提示libclntsh.so.9.0文件或目錄找不到。

    ORACLE_HOME沒有的話會提示PCC-F-NOERRFILE

    環境設置好以後,把fetch.pcmakefile放在同一目錄下,執行make就行了。

    $(ORACLE_HOME)/precomp/lib/env_precomp.mk文件中,可能有/usr/lib/gcc-lib/i686-rpm-linux/2.95.3/include,這個路徑中的文件與實際環境中的文件不一致的情況,要注意修改。在$(ORACLE_HOME)/precomp/admin/pcscfg.cfg中也有相同的地方要注意。

pro c sqlstm.stmt的傳遞(參考TKL000L)

有一段代碼如下。

       EXEC SQL DECLARE CUR_INET CURSOR FOR

       SELECT LPAD(TO_CHAR(ZZZ_JIMUCD),2,'0'),LPAD(TO_CHAR(COUNT(ZZZ_JIMUCD)),6,' ')

       FROM VRKAIMST

       WHERE ZZZ_KAIINNO<=999999 AND ZZZ_DELKBN=' ' AND

              (TO_DATE(:szDate,'YYYYMMDD') BETWEEN

       (TO_DATE(TO_CHAR(ZZZ_STAYY,'0000')||TO_CHAR(ZZZ_STAMM,'00')||TO_CHAR(ZZZ_STADD,'00'), 'YYYYMMDD')) AND

       (TO_DATE(TO_CHAR(ZZZ_ENDYY,'0000')||TO_CHAR(ZZZ_ENDMM,'00')||TO_CHAR(ZZZ_ENDDD,'00'), 'YYYYMMDD')))

       GROUP BY ZZZ_JIMUCD;

這時候,執行打開遊標的操作EXEC SQL OPEN CUR_INET;出錯,那麼程序跳轉到錯誤處理fn_SqlAccessError(sqlstm.stmt)

       EXEC SQL WHENEVER SQLERROR DO fn_SqlAccessError(sqlstm.stmt);

       EXEC SQL OPEN CUR_INET;

       EXEC SQL WHENEVER NOT FOUND DO break;

void fn_SqlAccessError(char *pSqlStmt)

{

       printf("sql:%s/n",pSqlStmt);

}

如果不傳遞參數,那麼,在錯誤處理函數中就輸出sqlstm.stmtnull,傳遞參數後就輸出實際的select語句.原因是:

上面的select語句,pro c中編譯成c語言後,是這個形式:

{

       ......

       sqlstm.stmt=sql0003;

       ......

       if (sqlca.sqlcode < 0) fn_SqlAccessError(sqlstm.stmt);

}

這段語句有大括號,出了大括號,sqlstm.stmt就爲null,所以必須要賦值.

或者用另一種方法:

void fn_SqlAccessError()

{

       char stmt[1000];

       size_t sqlfc,stmtlen=1000;

       unsigned int i;

       i=sqlgls(stm,&stmtlen,&sqlfc);

       /* 顯示出錯語句*/

       printf("sql:%.*s/n",stmtlen,stmt);

       /*顯示錯誤信息*/

       printf("error:%.*s/n",sqlca.sqlerrm.sqlerrml,sqlca.sqlerrm.sqlerrmc);

}

 

fetch.pc

#include <stdio.h>

EXEC SQL INCLUDE sqlca;

EXEC SQL INCLUDE oraca;

EXEC SQL BEGIN DECLARE SECTION;

    char    username[] ="MDUSR";

    char    password[] ="MDUSR";

    char    db_name[]  ="MDUSR";

    int testId;

    char testStr[32];

EXEC SQL END DECLARE SECTION;

char temp[32];

void sql_error();

int main(int argc,char *argv[])

{

    EXEC SQL WHENEVER SQLERROR do sql_error("Oracle error");

    EXEC SQL CONNECT :username IDENTIFIED BY :password USING :db_name;

    printf("Connected./n");

    EXEC SQL DECLARE TESTCURSOR CURSOR FOR

    SELECT HIDUKE FROM TK01 ;

    EXEC SQL OPEN TESTCURSOR;

    EXEC SQL WHENEVER NOT FOUND DO break;

    while(1)

    {

    printf("test string is --> ");

    EXEC SQL FETCH TESTCURSOR INTO :testStr;

    printf("%s /n ", testStr);

    }

    EXEC SQL CLOSE TESTCURSOR;

    EXEC SQL COMMIT WORK RELEASE;

    exit(0);

}

void sql_error(char *msg)

{

    char buf[500];

    int buflen, msglen;

    EXEC SQL WHENEVER SQLERROR CONTINUE;

    EXEC SQL ROLLBACK WORK RELEASE;

    printf("sqlcode:<%d>/n", sqlca.sqlcode) ;

    printf("sqlca.sqlerrm.sqlerrmc:%s/n",sqlca.sqlerrm.sqlerrmc) ;

    buflen = sizeof (buf);

    sqlglm(buf, &buflen, &msglen);

    printf("%s /n", msg);

    printf("%*.s /n", msglen, buf);

    exit(1);

}

 

makefile

#include /opt/oracle/product/9.0.1/precomp/lib/env_precomp.mk

PROC=/opt/oracle/product/9.0.1/bin/proc

GCC=$(CC)

BINDIR=$(HOME)/bin

ORAIFLAG=-I/opt/oracle/product/9.0.1/rdbms/public -I/opt/oracle/product/9.0.1/rdbms/demo -I/opt/oracle/product/9.0.1/precomp/public -I/opt/oracle/product/9.0.1/plsql/public

ORALFLAG=-L/opt/oracle/product/9.0.1/lib -L/opt/oracle/product/9.0.1/precomp/lib -L/opt/oracle/product/9.0.1/rdbms/lib -L/opt/oracle/product/9.0.1/sqlplus/lib -L/opt/oracle/product/9.0.1/network/lib -L/opt/oracle/product/9.0.1/plsql/lib

IFLAG=-I$(HOME)/include $(ORAIFLAG)

LFLAG=-L$(HOME)/lib $(ORALFLAG) -lclntsh

PROCFLAGS=char_map=string

.SUFFIXES: .pc .c .o

.pc.c:

       $(PROC) $(PROCFLAGS) iname=$*

       #rm *.lis

.pc.o:

       $(PROC) $(PROCFLAGS) iname=$*

       #rm *.lis

       $(GCC) $(IFLAG) -c $*.c

.c.o:

       $(GCC) $(IFLAG) -c $*.c

all:fetch

fetch:fetch.o

       $(GCC)  $? -o $@ $(LFLAG)

#     @echo "##### $@ loaded #####"

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章