首页 > Berkeley DB, Winter Zhang > 使用Visual C++ 2005编译Oracle Berkeley DB

使用Visual C++ 2005编译Oracle Berkeley DB

2009年4月15日 Winter

1 前言

Oracle Berkeley DB 是行业领先的可嵌入开源数据库引擎,它为开发人员提供了无需管理的快速、可靠的本地持久性。它是一个直接链接到您应用程序的库。您的应用程序进行简单的函数调用,而不是向远程服务器发送消息,从而消除了客户端-服务器体系结构的性能损耗。 它消除了 SQL 查询处理的开销,从而使应用程序按可预测的访问模式更快地运行。它提供了事务和恢复用于高并发的锁定,多进程和多线程冷热备份以及用于高可用性应用程序的单主复制在提供强大功能的同时它还具有强大的可配置性使得开发人员能够控制它行为的众多方面

Visual C++ 2005Windows 平台上最为流行的企业级C/C++编译器能够在windows平台上产生高效的二进制代码Visual C++ 2005是Visual Studio 2005的重要组成部分,其安装包含在Visual Studio 2005的安装中,并且其与其他语言的编译器共用一个集成开发环境(IDE)。

本文介绍了如何在Windows上用VC++2005 编译Oracle Berkeley DB 4.7.25 版本


2 下载Oracle Berkeley DB

Oracle Berkeley DB 可以从此处下载: http://www.oracle.com/technology/global/cn/software/products/berkeley-db/db/index.html

1

点击Berkeley DB 4.7.25.NC.zip,由于本文描述的是如何从源代码编译出Berkeley DB,故而不选择下载Windows安装程序下载完成后解压该文件解压后进入db-4.7.25.NC, 我们可以发现该文件夹的内容

22

3 编译

进入build_windows目录,我们可发现该目录下有一个工程文件(.dsw)和很多的项目文件(.dsp),这里我们选择使用工程文件Berkeley_DB.dsw:

打开Microsoft Visual Studio 2005的IDE, 选择菜单->File->Open->Project/Solution,打开build_windows目录下的Berkeley_DB.dsw文件

34

打开后会提示要求进行project文件的格式转换选择”Yes To All”:

41

转换后选择编译类型(本文是Debug x86 Win32),鼠标右键单击build_all, 选择build,就开始了编译过程

5

build_all编译默认会编译Berkeley DB 静态库动态库以及一系列的工具程序和示例程序

编译完成后可以看到build_windows底下多了一个Debug目录进入Debug目录,我们可以看到编译出来的文件

62

4 运行示例程序

ex_access是Oracle Berkeley DB自带的一个示例程序, 该程序将用户输入的字符串作为关键字(key),将字符串倒置作为数据(data),而后将此键值对存入BerkeleyDB数据库。 当用户键入exit时,该程序将显示数据库的内容, 而后退出:

71

5 总结

WindowsVisual C++2005编译Berkeley DB是比较容易的读者如果出现了什么编译上的问题可以与我交流在后续章节中我还将介绍命令行的编译方法以及使用现今流行的Code::Blocks编译Oracle Berkeley DB的方法

分类: Berkeley DB, Winter Zhang 标签: ,
  1. hotDB
    2009年4月20日17:42 | #1

    我在2003上编译出错呢,请协助解答,谢谢。此外,我以前是oracle dba工作,现在想用内存数据库,想选择这个。

  2. 2009年4月21日11:24 | #2

    能不能提供一下你的出错信息?

  3. hotDB
    2009年4月21日12:33 | #3

    谢谢,已经好了,编译类型选择错误。此外,有关于源码的学习资料吗?谢谢!

  4. chaohuang
    2009年4月21日12:42 | #4

    Hi hotDB,

    请浏览Berkeley DB在Oracle Technology Network(OTN)的官方网站:www.berkeleydb.com。 在官网我们提供了很多的文档,白皮书,客户案例等。

    如果你在使用中有进一步的问题,欢迎发到BDB的官方论坛。我们会在那里回答你的。

    谢谢。

  5. jeak
    2009年4月21日16:36 | #5

    错误:无法打开文件”libdb47.lib“;
    无法打开包括文件”tcl.h“等
    几十处错误

  6. davidzhao
    2009年4月23日13:33 | #6

    在你的IDE中指定正确的头文件路径和库文件路径。另外你不需要包含tcl.h的。你是做编译DB的示例程序吗?

  7. 2009年4月23日14:07 | #7

    你好, 如果按照本文的步骤一步步来, 即只编译build_all, 是不会有这种错误提示的. 因为build_all不包含对tcl库的编译, 这对java也成立.

    请问, 你是否需要编译tcl呢?

  8. ArthurWang
    2009年7月3日11:50 | #8

    想要研究一下Berkeley DB C++代码,该从哪里入手呢?谢谢

  9. nemo
    2009年7月5日22:35 | #9

    你好,我请教一个问题,我在vs2008上编译完成,但是在测试doc文档中的一些代码时,发现:C++语言的可以过去,但是c语言的都过不去,总是出现一些奇怪的提示。
    如:
    #include

    Db db(NULL, 0); // Instantiate the Db object

    u_int32_t oFlags = DB_CREATE; // Open flags;

    try {
    // Open the database
    db.open(NULL, // Transaction pointer
    “my_db.db”, // Database file name
    NULL, // Optional logical database name
    DB_BTREE, // Database access method
    oFlags, // Open flags
    0); // File mode (using defaults)
    // DbException is not subclassed from std::exception, so
    // need to catch both of these.
    } catch(DbException &e) {
    // Error handling code goes here
    } catch(std::exception &e) {
    // Error handling code goes here
    } 测试可以通过,但是与它对应的c语言版本的
    #include

    DB *dbp; /* DB structure handle */
    u_int32_t flags; /* database open flags */
    int ret; /* function return value */

    /* Initialize the structure. This
    * database is not opened in an environment,
    * so the environment pointer is NULL. */
    ret = db_create(&dbp, NULL, 0);
    if (ret != 0) {
    /* Error handling goes here */
    }

    /* Database open flags */
    flags = DB_CREATE; /* If the database does not exist,
    * create it.*/

    /* open the database */
    ret = dbp->open(dbp, /* DB structure pointer */
    NULL, /* Transaction pointer */
    “my_db.db”, /* On-disk file that holds the database. */
    NULL, /* Optional logical database name */
    DB_BTREE, /* Database access method */
    flags, /* Open flags */
    0); /* File mode (using defaults) */
    if (ret != 0) {
    /* Error handling goes here */
    }却出现这个提示:
    DB->put: method not permitted before handle’s open method。

    c和c++版的对应代码都有类似的情况:c++通得过,c通不过。
    我在用vs6.0时,也发现这个错误,但是自从我把buildwindows\release下的libdb47.dll拷贝到bin文件夹下后,已经解决问题了。现在转到vs2008下面发现这个办法不灵了。。。。。
    不知何故。
    希望你帮我看一下,感激不尽!!!

  10. Winter Zhang
    2009年7月6日15:02 | #10

    nemo :
    你好,我请教一个问题,我在vs2008上编译完成,但是在测试doc文档中的一些代码时,发现:C++语言的可以过去,但是c语言的都过不去,总是出现一些奇怪的提示。
    如:
    #include

    Db db(NULL, 0); // Instantiate the Db object
    u_int32_t oFlags = DB_CREATE; // Open flags;
    try {
    // Open the database
    db.open(NULL, // Transaction pointer
    “my_db.db”, // Database file name
    NULL, // Optional logical database name
    DB_BTREE, // Database access method
    oFlags, // Open flags
    0); // File mode (using defaults)
    // DbException is not subclassed from std::exception, so
    // need to catch both of these.
    } catch(DbException &e) {
    // Error handling code goes here
    } catch(std::exception &e) {
    // Error handling code goes here
    } 测试可以通过,但是与它对应的c语言版本的
    #include

    DB *dbp; /* DB structure handle */
    u_int32_t flags; /* database open flags */
    int ret; /* function return value */
    /* Initialize the structure. This
    * database is not opened in an environment,
    * so the environment pointer is NULL. */
    ret = db_create(&dbp, NULL, 0);
    if (ret != 0) {
    /* Error handling goes here */
    }
    /* Database open flags */
    flags = DB_CREATE; /* If the database does not exist,
    * create it.*/
    /* open the database */
    ret = dbp->open(dbp, /* DB structure pointer */
    NULL, /* Transaction pointer */
    “my_db.db”, /* On-disk file that holds the database. */
    NULL, /* Optional logical database name */
    DB_BTREE, /* Database access method */
    flags, /* Open flags */
    0); /* File mode (using defaults) */
    if (ret != 0) {
    /* Error handling goes here */
    }却出现这个提示:
    DB->put: method not permitted before handle’s open method。
    c和c++版的对应代码都有类似的情况:c++通得过,c通不过。
    我在用vs6.0时,也发现这个错误,但是自从我把buildwindows\release下的libdb47.dll拷贝到bin文件夹下后,已经解决问题了。现在转到vs2008下面发现这个办法不灵了。。。。。
    不知何故。
    希望你帮我看一下,感激不尽!!!

    你好, 基本上,这个错误的是因为:机器上装有多个版本的BDB, 运行时链接的库和编译期的库不同.

    建议首先检查一下编译使用的BDB库文件的位置和版本,然后检查一下程序运行时使用的PATH变量, 看看其中是否包含其他位置/版本的BDB的动态链接库.

  11. nemo
    2009年7月7日21:41 | #11

    我原先重装过系统,但是bdb的目录还在,所以我只是添加了系统的path便由6.0转到2008,结果出了以上的问题。今日听君一语,终于决定重装bdb,再重新编译,现在已经解决了。感谢!!!

  12. ArthurWang
    2009年7月8日20:01 | #12

    #include
    #include
    #include

    int main(int argc, char *argv)
    {
    u_int32_t env_flags = DB_CREATE | DB_INIT_MPOOL;
    std::string envHome(“/testEnv”);
    DbEnv myEnv(0);

    try{
    myEnv.open(envHome.c_str(), env_flags, 0);
    }
    catch(DbException &e){
    std::cerr<<”Error openning database environment 1:”<<envHome<<std::endl;
    std::cerr<<e.what()<<std::endl;
    exit(-1);
    }
    catch(std::exception &e){
    std::cerr<<”Error openning database environment 2:”<<envHome<<std::endl;
    std::cerr<<e.what()<<std::endl;
    exit(-1);
    }

    std::cout<<”This operarion is completed…”<<std::endl;
    }

    上面代码中的envHome怎么设置才能正确生成数据库环境呢?我创建了envHome文件夹也不行。。谢谢!

  13. 2009年7月9日14:25 | #13

    你好, 鉴于你将环境目录设置为/testEnv, 我想知道一下你是用什么用户来运行该示例程序的, 是root用户还是其他的普通用户? 如果是其他用户, 请确认一下是否该用户可以向/testEnv里面添加文件. 因为正常情况下,打开环境的时候, 会在环境文件夹下创建若干文件.

    一般情况下, 用root用户创建的文件夹可以被其他用户读(cd/ls),.但是, 要让普通用户可以往该文件夹放文件, 还需要用chmod设置一下文件夹的mode.

  14. ArthurWang
    2009年7月10日16:03 | #14

    我用的是Windows环境,VS2008,管理员权限,那个路径设置成相对路径就没事儿,可能是由于源代码是在Linux环境下编写的,路径格式不同吧。。
    谢谢您的解答!

  15. LongSky
    2009年8月20日14:06 | #15

    请问应该如何使用dbenv->set_cachesize 来动态的更改数据库的内存,我尝试过很多方法都不能动态设置

  16. 2009年8月26日17:42 | #16

    @LongSky
    您好, 我们正在研究这个问题, 并将尽快给您答复.

  17. marisa
    2009年10月15日11:51 | #17

    @jeak
    我也出现了这个问题,我的解决方法重新编译,我出现的原因是还没有生成成功我就结束了编译,然后重新编译后就出现这个问题。预祝成功

  18. 2009年10月16日10:47 | #18

    你好,很抱歉很久没给回复。

    一般来说,要更改Environment内存,需要首先注意满足以下条件:

    A, mutex的最大值需要足够大, 因为如果不够大的话, mutex将被消耗光, 设置/更改将出错。可以用DB_ENV->mutex_set_max来更改此值。

    B, Cache的最大值需要足够大, 显然应当要大于你动态更改的最大值。可以用DB_ENV->set_cache_max来设置此值。

    而后,在DB_ENV->open的前后,都可以调用DB_ENV->set_cachesize来设置内存的大小,也可以通过DB_ENV->get_cachesize来获得内存的大小。设置的与获得的并非完全一致,二者之间有一些差别,具体解释如下:

    1 首次创建环境(即首次产生__db.001等文件):如果在DB_ENV->open之前未调用DB_ENV->set_cachesize来设置大小, 则默认的cachesize是256KB, nchache是1。如果有设置,当设置的cachesize<500MB时, 实际的cachesize大约是设置大小的1.25倍,否则,比实际值大一点点。ncache和设置的相同。创建环境以后,在环境目录下会有ncache个region文件。文件大小(regsize)略大于实际cachesize/ncache,这个大小是不会变化的,以后新增加的region文件也是这么大。

    2 更改内存大小:如上,当cachesize<500MB, 则会上浮25%,否则保持原值。变化的流程是:a,如果当前要实际设置的cachesize不需要ncache个region文件,则region文件数目会减少,即ncache减小,并且删除多余的region文件。如果需要更多的region文件,则ncache会增加,同时创建更多的region文件。 否则region文件和ncache维持不变。

    3 判断是否需要ncache的数目很简单,基本依据是:cachesize大小与ncache-2个总容量, ncache-1个总容量, 以及ncache个总容量的比较关系。

    4 get_cachesize获得的gigabyte和cachesize是在创建时候设置的值,而ncache反映的实际的ncache,即region文件的数目。ncache的数目也可以通过对环境目录下的region文件数目分析出来,因为那些文件大小一样, 具体值如1所言。

    在这点上, API实际功能和文档上可能有些不一致,后续将证实此情况。

    参考: http://www.oracle.com/technology/documentation/berkeley-db/db/api_reference/C/frame_main.html

  19. cc
    2010年2月3日23:30 | #19

    您好,我用的是VC++6.0编译的D:\DB\db-4.8.26\examples_cxx\getting_started 文件夹下的MyDb.dsw 出现以下报错:
    ——————–Configuration: MyDb – Win32 Debug——————–
    Linking…
    MSVCRTD.lib(crtexe.obj) : error LNK2001: unresolved external symbol _main
    Debug/MyDb.exe : fatal error LNK1120: 1 unresolved externals
    Error executing link.exe.

    MyDb.exe – 2 error(s), 0 warning(s) vc++”settings”和“options”都做了修改 可以编译像“hello world”

本文的评论功能被关闭了.
Դ