Cookbook > Apache_api

Apache Portable Runtimeをあなたのプロジェクトに取り込む

By Hiroyuki OYAMA Wed Sep 10 20:18:40 2003

Apache HTTP Server 2.x系でプラットフォーム依存部分を吸収し、一貫したAPIを提供するために利用されているライブラリAPR - Apache Portable Runtimeを、Apache以外のプロジェクトで利用するための方法。

Apache module APIの美味しいドコ取り

APRを使用するとApache module APIで利用できていた
  • リソースプール
  • 扱いやすく安全な文字列処理関数
  • 動的なデータ型
  • などを、Apache HTTP Server以外のプログラムで利用できます。さらに
  • メモリマップドI/O
  • 共有メモリ
  • スレッド
  • など、プラットフォームごとにAPIやオプションが異なる機能も、一貫したAPIで利用する事ができるようになります。

    しかしASFの他のプロジェクトと同様に、APIのリファレンスマニュアルはあれど、その利用方法やサンプルに関するドキュメントは貧弱です。というわけで、あなたのプロジェクトでAPRを利用する(取り込む)ための手順と、それを簡略化するツールについて書いてみます。
    ここで説明するビルド環境を構築するためにはAPRの他に
  • GNU Autoconf
  • GNU Automake
  • GNU Libtool
  • がそれぞれ必要になるので、予めインストールしておきます。これらのプログラムはビルド環境の構築及び開発を行う際に必要なツールで、作成したプロジェクトを配布しビルドする際には必要ありません。

    APRを取り込む手順

    APRは単なるライブラリなので、あなたのプログラムからリンクすれば利用できます。
    終了
    というのもナンなので、次のような要件を満たすための手順を考えてみます。
    1. プロジェクトの配付パッケージにAPRをバンドルしたい
    2. GNU Automake/Autoconf/libtoolなどのGNU Autotoolsをプロジェクトで使用したい
    ひとまずAPRのパッケージを取得してビルドし、インストールしてください。
    $ wget http://www.apache.org/dist/apr/apr-0.9.3.tar.gz
    $ tar zxvf apr-0.9.3.tar.gz
    $ cd apr-0.9.3/
    $ ./configure
    $ make
    $ sudo make install
    詳細なコンパイルオプションなどは割愛します。この場合おそらく次のようなレイアウトで、APRがインストールされたと思います。
    /usr/local/apr/bin/apr-config
    /usr/local/apr/build/apr_rules.mk
    /usr/local/apr/build/libtool
    /usr/local/apr/lib/libapr-0.a
    /usr/local/apr/lib/libapr-0.*
    次にAPRを利用するプロジェクトmyprojectを作成し、取り込みの手順を見てみましょう。プロジェクトに必要なファイルは
  • APRのソースコード
  • サンプルプログラムmyproject.c
  • ビルドのルールを定義するMakefile.am
  • 環境のチェック手順を定義するconfigure.in
  • です。この他にもAPRのパッケージからコピーして使用するファイルが幾つか在るので、そちらは順を追いながら説明します。

    ディレクトリとソースコードの用意

    では実際にプロジェクトのディレクトリと、ソースコードmyproject.cを用意します。
    $ mkdir myproject
    $ cd myproject
    $ vi myproject.c
    #include "apr_errno.h"
    #include "apr_general.h"
    #include "apr_strings.h"
    #include "apr_file_io.h"
    #include "apr_pools.h"
     
    #include <stdlib.h>
    #include <unistd.h>
    
    
    static apr_file_t *local_stdout, *local_stdin, *local_stderr;
    
    int main(int argc, const char * const *argv)
    {
        apr_pool_t *p;
        apr_status_t rc;
        char *str;
    
        /* initialize */
        apr_app_initialize(&argc, &argv, NULL);
        apr_pool_create(&p, NULL);
        apr_file_open_stdout(&local_stdout, p);
        apr_file_open_stdin(&local_stdin, p);
        apr_file_open_stderr(&local_stderr, p);
    
        str = apr_pstrcat(p, "myproject", ": ", "Hello World", NULL);
        apr_file_printf(local_stdout, "\n", str);
    
        return EXIT_SUCCESS;
    }
    いくつかのAPRの関数を使用しているほかは、普通のCのソースコードと同じです。このソースコードは
    1. APR環境の初期化
    2. リソースプールの生成
    3. stdout, stdin, stderrのオープン
    4. 文字列"myproject: Hello World"を結合
    5. stdoutに文字列を出力
    するだけの簡単なものです。

    さらにプロジェクト内にAPRのコードツリーへのシンボリックリンクを作成します。APRのコードツリーのパスや各種設定値は、
    /usr/local/apr/bin/apr-config
    を使用して調べることができます。コードツリーのパスは--srcdirオプションで得ることが出来るので、次のようにシンボリックリンクを作成します。シンボリックリンクではなくコードツリー全体をmyprojectにコピーしても構いません。
    $ ln -s `/usr/local/apr/bin/apr-config --srcdir` apr
    $ ls -F
    apr@         myproject.c

    Makefile.amの用意

    次に、プロジェクト内で使用するソースコードのビルド方法などを指定するMakefile.amを用意します。Makefie.amはGNU Automakeプログラムが使用する定義ファイルで、Makefile.amファイルを設置したディレクトリでautomakeコマンドを実行すると、Makefileの雛型となるMakefile.inを生成します。
    $ vi Makefile.am
    INCLUDES = -I$(srcdir)/apr/include
    SUBDIRS = apr
    
    bin_PROGRAMS = myproject
    myproject_SOURCE = myproject.c
    myproject_LDADD = apr/libapr-0.la
    このプロジェクトではAPRを使用するので、プロジェクト内のAPRのヘッダファイルのディレクトリへのパスを
    INCLUDES = -I$(srcdir)/apr/include
    で指定します。またAPRをビルドする必要があるので、APRのコードツリーへのパスを
    SUBDIRS = apr
    で指定します。
    このプロジェクトでは実行ファイルmyprojectをビルドします。ビルドする実行ファイルの名称を
    bin_PROGRAMS = myproject
    で指定し、そのソースコードを
    myproject_SOURCE = myproject.c
    に列挙します。またmyprojectプログラムはAPRをリンクする必要があるので
    myproject_LDADD = apr/libapr-0.la
    でAPRのLibtoolライブラリlibapr-0.laのパスを指定します。Libtoolライブラリにつて詳細は
    GNU Autoconf/Automake/Libtoolを参照して、私に聞かないでください :)

    configure.inの用意

    次に、ビルド環境のチェックや調整を行うconfigureスクリプトの処理内容を定義するconfigure.inファイルを用意します。configure.inファイルはGNU Autoconfプログラムが使用する定義ファイルで、configure.inファイルを設置したディレクトリでautoconfコマンドを実行すると、configureスクリプトを生成します。
    $ vi configure.in
    AC_INIT()
    AC_CONFIG_AUX_DIR(build)
    AM_INIT_AUTOMAKE(myproject, 0.0.0, no-define)
    
    sinclude(build/apr_common.m4)
    sinclude(build/find_apr.m4)
    
    echo $ac_n "${nl}Configuring Apache Portable Runtime library ...${nl}"
    
    APR_FIND_APR("$srcdir/apr", "./apr", 1)
    if test "$apr_found" = "reconfig"; then
        APR_SUBDIR_CONFIG(apr)
    fi
    
    AC_PROG_CC
    AC_PROG_LIBTOOL
    AC_OUTPUT(Makefile)
    configure.inの内容については割愛します。また、configureスクリプトへの変換に使用するAPR固有のマクロファイルを、下記のとおりプロジェクト内に設置します。
    $ mkdir build
    $ ln -s `/usr/local/apr/bin/apr-config --srcdir`/build/apr_common.m4 build/apr_common.m4
    $ ln -s `/usr/local/apr/bin/apr-config --srcdir`/build/find_apr.m4 build/find_apr.m4
    $ ls -F build
    apr_common.m4@ find_apr.m4@
    最後にGNU Autoconf, Automakeが要求する各ファイルを設置します。とりあえずは空のファイルを作成しておきます。
    $ touch NEWS README AUTHORS ChangeLog
    最終的にmyprojectは次のようなファイルのレイアウトになりました。
    $ ls -F
    AUTHORS        Makefile.am    README         build/         myproject.c
    ChangeLog      NEWS           apr@           configure.in

    ビルド用ファイルの生成

    プロジェクトのソースコード及び各定義ファイルの用意ができたので、最後にMakefile.inやconfigureスクリプトなどのビルド用のファイルを生成しす。まず、configure.inで使用するマクロから非標準のものを検索し、aclocal.m4に追加するaclocalコマンドを実行します。
    $ aclocal
    aclocalコマンドを実行すると、aclocal.m4ファイルが生成されます。
    $ ls -F
    AUTHORS        Makefile.am    README         apr@           configure.in
    ChangeLog      NEWS           aclocal.m4     build/         myproject.c
    次にソースコードのコンパイルやリンクに使用するlibtoolスクリプトを生成するために、libtoolizeコマンドを実行します。
     $ libtoolize
    You should update your `aclocal.m4' by running aclocal.
    Putting files in AC_CONFIG_AUX_DIR, `build'.
    libtoolizeコマンドを実行するとプロジェクトの buildディレクトリにconfig.guess,config.sub,ltmain.shの各ファイルが作成されます。(正確には既にインストールされているファイルへのシンボリックリンクです)
    $ ls -F build
    apr_common.m4@ config.guess@  config.sub@    find_apr.m4@   ltmain.sh@
    次にMakefileの雛型となるMakefile.inファイルを生成するために、automakeコマンドを実行します。automakeコマンドはMakefile.am等の定義を元にMakefile.inファイルを生成します。
    $ automake --add-missing
    configure.in: installing `build/install-sh'
    configure.in: installing `build/mkinstalldirs'
    configure.in: installing `build/missing'
    Makefile.am: installing `./COPYING'
    Makefile.am: installing `./INSTALL'
    Makefile.am: installing `build/depcomp'
    automakeコマンドの--add-missingオプションは、必要なファイルをインストールしてくれます。

    最後にautoconfコマンドを実行すると、configure.inファイルからconfigureスクリプトを生成します。
    $ autoconf
    最終的にプロジェクト内に次のようなファイルを設置・生成しました。
    $ ls -F
    AUTHORS           INSTALL@          NEWS              apr@              configure*
    COPYING@          Makefile.am       README            autom4te.cache/   configure.in
    ChangeLog         Makefile.in       aclocal.m4        build/            myproject.c
    このうち aclocal.m4ファイルと autom4te.cachディレクトリは不要になったので削除しておいても構いません。
    $ rm -rf aclocal.m4 autom4te.cache

    プロジェクトのビルド

    用意したプロジェクトをビルドしてみましょう。一般的なオープンソースプロジェクトのソースパッケージと同様の手順でビルドできます。
    $ ./configure
    $ make
    configureスクリプトはサブディレクトリapr/内のconfigureスクリプトも実行します。makeするとapr/ディレクトリ内のライブラリもビルドされます。
    ビルドが成功すると、カレントディレクトリに実行ファイルmyprojectが生成されますが、これはビルド環境内で正しくライブラリを見つけられるように、必要な環境設定などを行った上でプログラムを実行するshellスクリプトによるラッパーです。
    $ ./myproject
    myproject: Hello World
    $ file ./myproject
    myproject: Bourne shell script text
    実行ファイルの実体は.libs/myprojectに在り、make installするとこちらの実行ファイルがインストールされます。

    プロジェクトのメンテナンス

    以上でGNU Autotoolの元でAPRを利用する環境を構築(APRizeというらしい)することができました。プロジェクトにソースコードを追加する場合はMakefile.amにそのファイル名を追加した上で、automakeコマンドを再度実行して最新のMakefile.inを生成する必要があります。これらの作業は定型的なものなんで、次のようなshellスクリプトbuildconfなどを用意し、定義ファイルを更新した際に実行してプロジェクトをメンテナンスします。
    $ vi buildconf
    #!/bin/sh
    aclocal
    libtoolize
    automake --add-missing
    autoconf
    rm -rf aclocal.m4 autom4te.cache

    まとめ

    APRをプロジェクトに取り込み、オープンソースプロジェクトっぽくGNU Autotoolsを利用したビルド環境を構築する手順を説明しました。手数が多く少々面倒に思えるかもしれませんが、Automakeは高度なMakefileの雛型を生成してくれ、Libtoolはコンパイラの種類を問わない一貫したコンパイルやリンクのコマンドインターフェイスを提供してくれます。
    ちなみにこれらの手順を自動化するスクリプト aprize を作成してAPRの開発者メーリングリストにpostしてみたのですが、今のところ完全に無視されているようです :-) APRはライブラリなので、雑多なツールは必要ないのかもしれません。もしご入用でしたならばダウンロードして、スクリプト中の
    my $installbuilddir = "/usr/local/apr/build";  # @installbuilddir@
    の部分を
    $ /usr/local/apr/bin/apr-config --installbuilddir
    の実行結果のパスに書き換えた上で利用してください。(APRのパッケージに取り込んでもらえれば、APRのconfigure実行時にaprize.inから適切に置換させる事ができるんですけどね) 次のように -g -nオプションとプロジェクト名を指定して実行すれば、APRizeされたプロジェクトの雛型を生成します。
    $ aprize -g -n myproject
    Creating [DIR] myproject
    Creating [DIR] myproject/build
    Creating [FILE] myproject/configure.in
    Creating [FILE] myproject/Makefile.am
    Creating [FILE] myproject/myproject.c
    Creating [FILE] myproject/buildconf
    Creating [LINK] myproject/apr
    Creating [LINK] myproject/build/apr_common.m4
    Creating [LINK] myproject/build/find_apr.m4
    Creating [FILE] myproject/NEWS
    Creating [FILE] myproject/README
    Creating [FILE] myproject/AUTHORS
    Creating [FILE] myproject/ChangeLog
    Creating [FILE] myproject/configure
    You should update your `aclocal.m4' by running aclocal.
    Putting files in AC_CONFIG_AUX_DIR, `build'.
    configure.in: installing `build/install-sh'
    configure.in: installing `build/mkinstalldirs'
    configure.in: installing `build/missing'
    Makefile.am: installing `./COPYING'
    Makefile.am: installing `./INSTALL'
    Makefile.am: installing `build/depcomp'
    これだけ。ちなみにAPRはAutomakeを使っていないので、make distなどのターゲットを持っていません。そのため配布用のtar.gz等のパッケージを作成する場合は、別途スクリプトを用意した方が良いかもしれません。←だめじゃん
    APRを使って気持ちよくなる方法は、また日を改めて書いてみたいと思います。

    Comments

    Post a comment

    Name:


    URL:


    Comments:


    WebエンジニアのためのApacheモジュールプログラミングガイド

    ApacheをHackする!
    モジュールプログラミング強烈初体験!!
    定価: 2,919円(税込)
    ISBN: 4-7741-1799-4

    hiroyuki_oyama IM status

    Apache Users

    Apache Modules

    CPAN


    Home > Cookbook > Apache_api > Apache Portable Runtimeをあなたのプロジェクトに取り込む