かばだんなさん かく語りぬ Header Image

Zephir をWindows(64bit)に導入する。(ビルド編)

さて、前回 Zephir の環境構築までおこないました。今回は実際にZephirで作ったプログラムを使ってみましょう。

スケルトンの作成

まず拡張モジュールのスケルトンを作成します。コマンドプロンプトの適当なディレクトリで下記のとおり入力しましょう。

zephir init zeptest

するとこのディレクトリに、下記の3つのディレクトリが作成されます。

zeptest/      ← スケルトンのトップディレクトリ
    ext/      ← コンパイルした拡張モジュール(.dll)が格納されます。
    zeptest/    ← Zephirのプログラムを配置します。
    config.json

HelloWorldの作成

続いて実際のプログラムクラスを作成しましょう。
zeptest/zeptest/greeting.zep という名前のファイルに下記のように記載します。

namespace Zeptest;

class Greeting
{

    public static function say()
    {
        echo "hello world!";
    }

}

ビルド環境の整備

これで先ほどのコマンドプロンプトから

zephir build

と打ち込めばOK、とマニュアルには書いてあります。そんなことないけど。

環境変数の読み込み(コマンドプロンプトを開くたび)

Zephirでコンパイルするためにはコマンドプロンプトを使用しますが、普通にコマンドを実行してもコンパイルはできません。コマンドプロンプトを開くたびに、環境変数を読み込む必要があります。
マニュアルには VsDevCmd (「VS2012 の開発者コマンド プロンプト」)を実行するように書いてありますが、これでは動いてくれません。
正しくは vcvarsall (「VS2012 x86 Native Tools コマンド プロンプト」)を使うのですが、Windowsメニューから起動すると32bit版しかコンパイルできません。

そもそも私は毎回バッチを実行するのが面倒なので、下記のようなバッチファイルを1つ作成して、その中から必要なバッチを実行するようにしています。

@echo off
: #### Zephir の環境変数を設定する ###

:: PHP5.5以上 (32bit)
:: call "%VS110COMNTOOLS%\..\..\VC\vcvarsall" x86

:: PHP5.5以上 (64bit)
call "%VS110COMNTOOLS%\..\..\VC\vcvarsall" x86_amd64

:: PHP SDK を実行する
call "%PHP_SDK%\bin\phpsdk_setvars"

:: 終了。次へのアクションを促す
echo さぁ、あなたのextentionのディレクトリに移動して、「 zephir build 」を実行してください。

コマンドプロンプトを開くたびにこのバッチを呼び出すのさえ面倒な私は、さらにショートカットを作成しています。上記のバッチが C:\zephir/setenv.bat だとしたら、下記のようなリンク先のショートカットを作成します。

%comspec% /k C:\zephir/setenv.bat

これでもうショートカットをダブルクリックするだけで環境変数も読み込んだ状態のコマンドプロンプトが開きます。

先程のビルドコマンドを実行して、うまくいけば「zeptest/ext/x64/Release/php_zeptest.dll」が作成されるでしょう。

ZephirParser のコピー元ディレクトリ変更(1回だけ)

ビルド実行時に

Zephir\Exception: The zephir parser extension could not be found or compiled!

と表示されたるかもしれません。これは Zephir のプログラムをパースする php_zephir_parser.dll が存在しないというエラーなのですが、これはビルドスクリプトのバグです。64ビット環境ではコンパイルした php_zephir_parser.dll は zephir\parser\x64\Release に出力されるのですが、ビルドスクリプトは zephir\parser\Release に探しに行ってエラーとなっているのです。

最初に1回だけ手でコピーしても良いのですが、ちょっとカッコ悪い気もするのでビルドスクリプトを修正しましょう。
今回の例だと Zephir をインストールしたディレクトリ以下にある zephir\Library\Compiler.php に下記の3行を追加します。

    $buildType = 'Release';
    if (strpos($buildLog, 'Debug_TS\\') !== false) {
        $buildType = 'Debug_TS';
    } else if (strpos($buildLog, 'Release_TS\\') !== false) {
        $buildType = 'Release_TS';
    } else if (strpos($buildLog, 'Debug\\') !== false) {
        $buildType = 'Debug';
    }

    //以下の行を追加します。

    if (strpos($buildLog, '/out:x64\\') !== false) {
        $buildType = 'x64/' . $buildType;
    }

    //以上の行を追加します。

    copy($buildType . '/php_zephir_parser.dll', 'php_zephir_parser.dll');
    $extFile = $currentDir . 'php_zephir_parser.dll';

我ながら美しくないコードですが、まぁその上のビルドタイプの判定と揃えておきます。

php_zeptest.dll の配置(コンパイルのたび)

この山を乗り越えると、期待通り「zeptest/ext/x64/Release/php_zeptest.dll」は作られているのですが、今度は下記のようなメッセージが表示されます。

Installation is not implemented for windows yet! Aborting!

これ、平たく言うと「Windows版のインストールはまだ実装してないよ!強制終了!」ってことです。
(それもどうかと思うが。)

ということで、Windows版の拡張モジュールは手動で配置する必要があります。
ビルドしたコマンドプロンプトから

cp ext/x64/Release/php_zeptest.dll C:\php-5.6-nts/ext

を実行したら、php.iniファイルに

extension=php_zeptest.dll

という1行を追加しましょう。
(読み込みができたかどうか確認するには、コマンドプロンプトから「php -m」を実行します。「zeptest」が表示されれば読み込み成功です。)

で、最後にWWWサーバをリスタート(コマンドラインの場合はコマンドプロンプトをもう1度開きなおし)します。

これで拡張モジュールは作成されました。次回は拡張モジュールをPHPから呼び出してみましょう。


コメントを残す