Tclのラッパーライブラリ(前提編)
高木です。おはようございます。
以前から私はTcl/Tkを使う機会が結構ありました。
それは現在でも変わっていません。
純粋にTcl/Tkをスクリプト言語として使うというより、CやC++から呼び出せるライブラリとしての使い方が圧倒的多数です。
Tcl/TkはCで書かれた言語処理系であり、アプリケーションに組み込むことができるライブラリでもあります。
APIはCで使うためのものです。
もちろん、C++からでも使えますが、C特有の面倒くささはついて回ります。
そういうわけで、以前からTcl C APIをC++でラッピングしたライブラリを何度か作っては壊しを繰り返してきました。
そういう経験からたどり着いた結論としては、少なくとも私が使う限りにおいては、ラッパーライブラリが必要なのはほぼTclのみであり、Tkを本格的にラッピングする必要はないということです。
また、Tclのラッパーライブラリにしても、最小限の機能だけを扱うことにして、それ以上のことをやりたいなら生のTcl C APIを呼び出す方がいいだろうという考えに至りました。
もし、本格的なTclのラッパーライブラリが必要なら、先日も紹介したC++/Tclのようなものもあります。
Tkのラッパーライブラリが欲しければ、(いかにもジョークですが)C++/Tkのようなものもあります。
私が作るライブラリは、そんなに本格的なものではなく、シンプルかつ軽量で、できるだけ導入が簡単なものにしたいと考えています。
ところで、社内では私以外にもTcl/Tkのラッパーライブラリに挑戦しようとしている社員がいます。
同じテーマをぶつけて嫌がらせをするとかではなく、人それぞれ求めているものは異なるので、切磋琢磨しながらお互いによいものが作れれば一番です。
と、前置きはこれぐらいにして、ここからが本題です。
具体的な内容は次回以降にまわすとして、今回はTclのラッパーライブラリを作るうえでの前提条件について書いておくことにします。
何に使うのか?
私の普段の(技術の)仕事は、組込みや制御関連の開発がメインです。
その多くは、何らかの周辺デバイスを制御することになります。
常に実機が使えればいいのですが、多くの場合そうはいきませんし、実機が常に使えたとしても非常に使い勝手が悪い場合があります。
そんなときは、Tcl/Tkで周辺デバイスをシミュレーションすることになります。
どんな風にTcl/Tkを使うのか?
多くのケースではC++からTcl/Tkをライブラリとして使います。
開発するコードがCの場合でも、Tcl/Tkを呼び出す部分はC++のことが多いですね。
Tcl/Tkを呼び出す部分は、それ専用のスレッドを作ります。
スレッドの最初でTcl/Tkを初期化して、スレッドが終了する時点でTcl/Tkを後始末します。
Tcl自体をマルチスレッドにすることはありません。
何を扱わないのか?
Tcl/Tk全体をラッピングしようとすれば膨大な作業が発生します。
今回はあくまでもシンプルで軽量なものを目指しますので、そういうことはしません。
そこで、劣後順位を付けて、何を扱わないかを最初に決めることにします。
- Tkのライブラリは原則ラッピングしません。
ただし、Tk_Init関数やTk_MainLoop関数の呼び出しぐらいは扱うかもしれません。 - OOTclは扱いません。
- TclのChannelやEncodingやFileSystemは扱いません。
- Tcl_Objを用いた新しい形式だけを対象とし、レガシーな文字列ベースのAPIは扱いません。
ここまで扱わないものを決めておけば、残ったものに注力できるようになります。
残ったものの中で確実に扱うのは、
- Tcl_Obj
- Tcl_Interp
- Tcl_Command
- Tcl変数
ぐらいです。
Tcl_DStringのようなユーティリティはもしかしたら扱うかもしれません。
開発環境は?
対象プラットフォームとしては、Windows上のMSYS2、RaspbianおよびRaspberry Pi Desktop、Fedoraを考えています。
これだけ対象にしておけば、Raspbianと同じくDebanベースのUbuntuやLinux Mintなんかでも動くでしょう。
C++のバージョンは17といいたいところですが、Debian 9ベースのLinuxではGCCのバージョンが6.xなのでC++14を使うことにします。
Boost C+++ Librariesなど、大きな外部ライブラリには依存しないようにします。
こんな感じで前提条件を定めました。
次回から具体的な設計に入っていきます。