• Pro*C编程研究一:从.pc到.exe


    【第一步】在Windows下编辑一个.pc程序(Pro*C源程序,作者用到:C:proctestexam1.pc),其内容如下: 

    [cpp] view plaincopy
     
    1. #include <stdio.h>  
    2. #include <string.h>  
    3.   
    4. EXEC SQL INCLUDE SQLCA;  
    5.   
    6. int main()  
    7. {  
    8.    /*declare variables*/  
    9.    EXEC SQL BEGIN DECLARE SECTION;  
    10.    VARCHAR usr[20], pass[20], serv[20];     
    11.    char name[8];  
    12.    int age;    
    13.    EXEC SQL END DECLARE SECTION;    
    14.      
    15.    /*connect DB*/  
    16.    strcpy(usr.arr,"any3");  
    17.    usr.len=(unsigned short)strlen((char *)usr.arr);  
    18.    strcpy(pass.arr,"any3");  
    19.    pass.len=(unsigned short)strlen((char *)pass.arr);  
    20.    strcpy(serv.arr,"ORCL");  
    21.    serv.len=(unsigned short)strlen((char *)serv.arr);  
    22.     
    23.    /*Connecting DB Command*/  
    24.    EXEC SQL CONNECT :usr IDENTIFIED BY :pass USING :serv;  
    25.    printf("Connect! ");  
    26.     
    27.     /*Input*/  
    28.     printf("Input Member Age:");  
    29.     scanf("%d", &age);  
    30.        
    31.    /*Exec SQL*/  
    32.    EXEC SQL SELECT age, name into :age, :name from family_lu where age=:age;  
    33.    printf("Name=%s    ,Age=%d ", name, age);  
    34.     
    35.     /*commit and disconnect DB*/  
    36.     EXEC SQL COMMIT WORK RELEASE;  
    37.     printf("Disconnect! ");  
    38.       
    39.     return 1;  
    40. }  

     作者机器上使用到的oracle实例ORCL,并以用户名/密码(any3/any3)登陆。

    为示例,作者建立测试数据表 family_lu ,其结构明细为:

    CREATE TABLE family_lu
    (
           age   number,
           name  varchar2(20),
           reltn varchar2(20)          
    );

    插入数据:

    insert into family_lu values(0, 'anan', 'child');

    【第二步】在Windows下使用Oracle数据库的...inProc.exe预编译该.pc文件,生成对应的.c源程序。

    【建议一】

    注意到安装Oracle时已经将“D:oracleproduct10.2.0db_1in;”自动添加到“系统环境变量->系统变量->Path”中,因此,在“开始->运行->cmd”回车后,直接进入到.pc文件所在路径,输入proc命令。

    如本人Win7系统下为:

    C:UsersAdministrator>cd ../../proctest

    然后输入命令:proc exam1.pc

    【第三步】使用Windows下的gcc编译器对上述.c源文件进行编译,并生成windows下的可执行文件。

    注意到这里是最容易报错(非犯错)的地方!!!

    【建议二】使用最新的gcc编译器。

    对于较低版本的gcc,对于这一段源程序

    usr.len=(unsigned short)strlen((char *)usr.arr);

    编译会报错:

    invalid conversion from `const char*' to `char*'

    而升级到最新编译器则不存在此问题

    ——当然也可能是编码时语法不严谨导致,但无论如何,最新的编译器可用性更好,并且向下兼容。

    作者机器上安装了JFE and GCC,它自动被添加到了“系统环境变量->系统变量->Path”中,但其版本较低。

    这里手动将“D:Program FilesCodeBlocksMinGWin;”添加到“系统环境变量->系统变量->Path”的最前方(注意MinGW已经安装在本机上,为作者安装CodeBlocks时自带),即对于同名的gcc编译器,希望调用Path中靠前的那一个。MinGW的GCC编译器版本为4.7.1。

    【建议三】使用正确的库文件

    对于.pc源程序中有SQL(DB连接、数据查询等)相关代码的,在Pro*C将.pc转化为.c时,会自动在.c文件中声明并引用

    extern void sqlcxt (void **, unsigned int *,  struct sqlexd *, const struct sqlcxp *);

    extern void sqlcx2t(void **, unsigned int *, struct sqlexd *, const struct sqlcxp *);
    extern void sqlbuft(void **, char *);
    extern void sqlgs2t(void **, char *);
    extern void sqlorat(void **, unsigned int *, void *);

    等相关函数,因为在简单的Pro*C编程示例中,在.pc预编译成.c文件后,多数情况下都只使用了sqlcxt函数(而未使用sqlbuft等),因此,gcc在编译.c时将报错:

    undefined reference to `sqlcxt(void**, unsigned*, sqlexd*, sqlcxp const*)'

    这是由于gcc在编译时未加入Pro*C指定的库文件(静态库.lib或动态连接库.dll),该库包括了sqlcxt的定义。

    由于Pro*C广泛应用于Linux+Oracle环境,因此在多数博客文章或论坛发帖中,常见到:

    ////////////引用部分开始////////////

    需要用到$ORACLE_HOME/lib/libclntsh.so
    故需加上 -L $ORACLE_HOME/lib -l clntsh
    更正后的命令为:
    gcc -o test test.c -I /home/oracle/oracle/product/10.2.0/db_1/precomp/public -L $ORACLE_HOME/lib -l clntsh

    ////////////引用部分结束////////////LINK: http://blog.chinaunix.net/uid-261392-id-2138943.html

    在百度中搜索关键字“windows libclntsh”,非常好运地找到了《OCI Instant Client》 LINK:http://www.cnblogs.com/freewater/archive/2011/08/09/2132801.html

    作者找到Linux和Unix下的libclntsh.so.11.1(.so是Linux等下的动态连接库),正好对应于Windows下的oci.dll。

    最后,在《gcc编译dll和调用dll》一文中

    LINK:http://blog.csdn.net/denglei265/article/details/3889470

    找到调用.dll库文件生成windows下可执行文件的(简单)方法,如作者使用命令:

    C:proctest>gcc exam1.c D:oracleproduct10.2.0db_1BINoci.dll -o exam1

    成功生成可执行文件,运行之得到效果:

    C:proctest>exam1
    Connect!
    Input Member Age:0
    Name=anan       ,Age=0
    Disconnect!

    而这恰好是本文Pro*C程序示例希望实现的效果!

  • 相关阅读:
    javascript封装自定义滚动条方法,可自定义四个边框滚动条
    前端页面优化:javascript图片延迟加载
    VPS用LNMP安装WordPress
    结缘PDO
    Laravel踩坑笔记——illuminate/html被抛弃
    Android定时器实现方法[转]
    关于安装Android Studio的一些问题的解决方法
    nginx 多站点配置方法
    PHP5.6.x的新鲜事
    ThinkPHP学习手记——环境搭建
  • 原文地址:https://www.cnblogs.com/lvdongjie/p/3755139.html
Copyright © 2020-2023  润新知