OSTRACISM CO.

ScalaとOCamlとF#とPythonと...

Windows向けOCamlその2

 OCaml for Windowsのページ(http://fdopen.github.io/opam-repository-mingw/)を読むとEsy(https://esy.sh/)に移行してはどうですかという状況のようだ。EsyはMavenと同じ香りがするんだが、どうなんだろう。

 京都大学(https://www.fos.kuis.kyoto-u.ac.jp/~igarashi/class/pl/setup.html)ではWindowsはOCaml学習にWSLやVirtualBoxを使う前提にしており、OCamlをWindowsネイティブで動かすことはいまだに茨の道という認識で、以前から態度は変わってない。むしろWSL登場で楽になったのだろう。

 私のPC利用環境にはまだ32bit Windowsがあるので、Windows向けのOCaml開発環境は32bitのCygwinを使っている。OCamlは開発が放棄されたWODIの32bit版。コンパイラのバージョンは4.02.1。Windowsで動作するライブラリ群がそれなりに揃っており、生成される実行モジュールはcygwin1.dllを要求しない。ただ、omakeがないのでそれなりに面倒ではある。curlライブラリなどのTLSのバージョン等が世間に付いていけなくなるまではこれでイケると踏んでいる。

 以下、CygwinはC:\cygwinにインストールされているものとする。

 WODIを動かすには、install.shを動かしてインストールした後で、C:\cygwin\etc\profile.d\wodi32.sh の「if [ -f "/opt/wodi32/etc/env_ignore" ]; then」のif文をfiまで、「if [ -f "/opt/wodi32/etc/env_add" ]; then」のif文をfiまで削除する。また、OCAMLFIND_CONFとOCAMLLIBのパスが適切そうか確認する。

 パッケージはアーカイブの中身を C:\cygwin\opt\wodi32\var\cache\godi に上書きする。

 パッケージを使えるようにするのはgodi_console。

 VSCodeでは拡張機能にhackwalyさんのOCaml (deprecated)を使っている。何故deprecatedの方なのかというと、VSCode起動時にあれがないこれがないとエラーを出力しないからだ。

 VSCodeでデバッガが動くようにするため、環境変数を設定。環境変数 Path に C:\cygwin\opt\wodi32\bin を加える。環境変数 OCAMLLIB を C:/cygwin/opt/wodi32/lib/ocaml/std-lib にする。


デバッグ向けのビルド例

ocamlfind ocamlc -o calibre_news_fix.run.exe -g -linkpkg -package unix,zip tTools.ml tCharEntity.ml tHtmlParser.ml calibre_news_fix.ml

リリース向けのビルド例

ocamlfind ocamlopt -o calibre_news_fix.exe -linkpkg -package unix,zip tTools.ml tCharEntity.ml tHtmlParser.ml calibre_news_fix.ml

launch.jsonの例

{
    "version": "0.2.0",
    "configurations": [
        {
            "name": "OCaml",
            "type": "ocamldebug",
            "request": "launch",
            "program": "${workspaceRoot}/calibre_news_fix.run.exe",
            "console": "internalConsole",
            "stopOnEntry": false,
            "arguments": ["a\\temp1.epub", "a\\i.epub"]
        }
    ]
}

 ocamldebugのコマンドをVSCodeのデバッグコマンド(F5とかF10とかVisual Studio風)に置き換えてくれるので、体に染みついてるデバッグ方法を使える。ただし、VSCodeのデバッガでは変数が表示されないが、ウォッチ式に自分で変数を加えると見ることができる。CodeViewやTurbo Debuggerで劇的に楽になったのを思い出した。私はocamldebugをコマンドラインで利用したことはなく、SYMDEBよりは高機能なんだろうけど、コマンドを覚える気がないので、今まではPRINTデバッグをしていた。PRINTデバッグができるのがOCamlの良い点。そういえば最近仕事でUbuntuにてC++のプロジェクトをVSCode + gdbを使ってデバッグした。いつの間にかLinuxでもGUIデバッガーの環境が整っていたんだね。


2021.05.06


 WODIのパッケージにomakeが入っていることに気付く。godi_consoleでgodi-omakeをインストール。Linuxと同じようにomakeでビルドできる。

 Cygwinでopamを使う方法を試してみたが、camlzipの導入でメゲたので当分WODI。

 Emacsでocamldebugを使ってみたが、まぁ、Visual Studioで甘やかされた俺には無理。


2021.09.02


 CygwinのOCaml(WODI)でビルドしたバイナリでUTF-8を出力すると、UTF-8に設定したCygwinの端末(mintty)で文字化けする。Windowsのコマンドプロンプトで出力した場合と同じように化ける。UTF-8テキストをシフトJIS扱いした状態。GPD WIN2に入れてあるちょっと前のCygwinのOCamlでは化けないので、Cygwinの何かがデグレしてる。

 UTF-8のテキストファイルを標準出力に表示するだけのプログラムをCで書いて、i686-w64-mingw32-gccでビルド。文字化けする。同じプログラムをgccでビルドすると文字化けしない。i686-w64-mingw32-gccの仕様が変わったかデグレか?

 WODIはi686-w64-mingw32-gccなどMinGWをインストール時に要求する。ということはOCamlもMinGWのライブラリを使っていると考えられる。おかげで実行時Cygwinには依存しなくなる(cygwin1.dllが必要ない)。

 Windowsのコマンドプロンプトでchcp 65001(コマンドプロンプトでの表示などのコードページをUTF-8に変更)すると、文字化けしない。なんだろう、MinGWとCygwinの相性が悪くなったという意味なんだろうか。例えばcygwin1.dllを使ってない場合、端末への出力をシフトJIS(ANSI)と見做すようになったとか。いや、例えばとか適当なこと考えたが、/cygdrive/c/Windows/system32/fc /? を実行したら化けない。これだ、これが原因だ。余計なことをしてくれたもんだ。こういう機能はオフにできるようになってないんですかね。スイッチがなけりゃ自力では解決できそうにない。

 MinGWとCygwinの相性が、ある意味悪くなったのは事実。

 Cygwinの更新履歴(https://cygwin.com/cygwin-ug-net/ov-new.html)を見たら、『Revamped pseudo console support. Conditionally activating it only when a non-cygwin application is run. 』とある。多分これだな。

 minttyにてプログラムを動かす前にchcp.com 65001を呼び出すと文字化けは解消した。~/.bashrcにでも書く。bashが自動的には.comを実行モジュールと認識しないのか、.comを付けないと呼び出せない。実体は.exeなんだろうけど、なんで.comなんだろう。/cygdrive/c/Windows/system32/fc /? は英語で表示される。Windows付属以外のコマンドで日本語(シフトJIS)を使うものは文字化けするのだろうが、すぐには思いつかないので困るまではこれでいい。


2021.09.06


「インデックス」へ戻る


OSTRACISM CO.

OSTRA / Takeshi Yoneki