A certain engineer "COMPLEX"

.NETでLinuxと遊んでみる Visual Studio Code編 第8回

Introduction


前回は、自作のSharedライブラリに定義された関数をP/Invokeで呼び出してみました。

.NETでLinuxと遊んでみる Visual Studio Code編 第7回
Introduction前々回は、GLibc内の関数をP/Invokeで呼び出してみました。また、CMakeでビルドしたC++のライブラリで関数を公開してみました。これを利用して、.NET Core...

しかしながら、毎回毎回/usr/local/libとかにコピーするのってどうなんでしょう?
Windowsみたいに、実行ファイルと同じディレクトリにSharedライブラリを配置しても動作するのでしょうか?
Windowsの場合、exeが呼び出すdllは、実行ファイルから以下の順序で検索されます。

  1. 実行中のプロセスの実行形式モジュールがあるフォルダー。
  2. 現在のフォルダー。
  3. Windows システム フォルダー。 このフォルダーへのパスは、GetSystemDirectory 関数が取得します。
  4. Windows ディレクトリ。 このフォルダーへのパスは、GetWindowsDirectory 関数が取得します。
  5. 環境変数 PATH 内に記述されたフォルダー。

Linuxの場合、3,4以外は同じ条件で試すことができそうです。
ただ、.NET Coreの場合、dotnet runで動作する場合のカレントディレクトリに関して情報がないので、2もちょっと先送り。
最終的に下記の内容をテストしてみます。

  1. Sharedライブラリをシステムから削除
  2. Sharedライブラリを実行ファイルと同じフォルダに配置
  3. LD_LIBRARY_PATHと実行ファイルと同じフォルダの優先順位

Try


サンプルは、.NETでLinuxと遊んでみる Visual Studio Code編 第7回と同じものを使います。

Sharedライブラリをシステムから削除

これは動かないはずです。
実行ファイルと同じディレクトリ、/usr/local/lib64にSharedライブラリが存在しないことを確認してから実行してみます。

Windowsと同じように、System.DllNotFoundExceptionがスローされました。
期待通りです。

Sharedライブラリを実行ファイルと同じフォルダに配置

きちんと動作しました。

LD_LIBRARY_PATHと実行ファイルと同じフォルダの優先順位

これは気になりますね。
別に.NET Coreに関係なく、Linuxの仕組みと同じような気がしますが...
実行時、どちらが呼び出されたかわかるように、Sharedライブラリ側を修正します。

実行ファイルに配置するSharedライブラリ

/usr/local/lib64に配置するSharedライブラリ

これらをそれぞれビルドして、/usr/local/lib64、実行ファイルと同じディレクトリであるbin/Debug/netcoreapp2.0/にコピーします。
また、環境変数LD_LIBRARY_PATHに/usr/local/lib64を追加します。
一応、各ディレクトリにSharedライブラリがコピーされたことも確認しておきます。
そして、dotnet runで実行します。

結果としては、実行フォルダのSharedライブラリが優先されました。
また、実行フォルダのSharedライブラリを削除しても、/usr/local/lib64のSharedライブラリが使用され、きちんと動作することもわかりました。

Conclusion


結論としては、Windowsと同じく、実行ファイルのあるディレクトリに配置されているライブラリが優先のようですね。

開発メモ その88 C/C++からPythonを呼び出せない

Problem


前回、C/C++のコードからPythonを呼び出してみました。

開発メモ その87 C/C++からPythonを呼び出す
ProblemPythonはグルー言語、として有名ですが、C#から呼び出す、というか.NET Framework上で動作するPythonの実装であるIronPythonはもう期待できる状態ではありません...

が、自宅の環境だと、Windows 10で動作し、Windows 7で動作しないという問題が発生しました。

Windows 10

Windows 7

python.exeはPathが通っているのは間違いないのですが...
きになるのは、Windows 10側はPythonインタプリタが一つ多いところ。

Resolution


調べてみると、そこそこ発生している問題の様子。

Python (Windows) - ImportError: No module named site
I am trying to install Python for the first time. I downloaded the following installer from the Python website:Python 2.7.1 Windows Installer (Windows binary...

python "No module named site"
So I have searched this question before, and it's been answered satisfactorily for other users on stackoverflow (Python (Windows) - ImportError: No modu...

ただ、どれも環境変数PYTHONHOME, PYTHONPATHを通せ、という説明だけで、私の環境は解決できませんでした。
そもそも、Windows 10側にはこの2つの環境変数は定義されていませんでしたし。

そんな中、日本語の開発者向けQ&Aコミュニティteratailで回答を見つけました。

windows7/64bit下のpythonでのreportlabのインストール|teratail
windows7/64bit,pytho2.6環境でreportlabをインストールしようとすると、pythonが見つからない旨のメッセージが表示されてしまい、インストールができません。pdfの生成...

ようするに、レジストリがおかしいよ、という話。
確かに、Windows 10側には指摘されているレジストリの項目が存在していましたが、Windows 7側にはありませんでした。

そのため、レジストリに適切な値を追加することで動作するようです。
上のteratailの回答では親切にもレジストリへの追加スクリプトも用意してありましたので、適切に書き換えて実行するだけです。
実行前に、問題のレジストリが存在しないことを確認してから実行します。

自分の環境では、Minicondaに関連付けたいので下記のように修正しました。
インストールしてあるMinicondaは4.0.5 64bit (Python 2.7.11)版でした。

OS=64bit python=32bit用

OS=64bit python=64bit または OS=32bit用

上の内容を、<適当な名前>.regとつけてファイルに保存し、ダブルクリックで実行します。
その後、プログラムを実行するとうまくいくようになりました、

開発メモ その87 C/C++からPythonを呼び出す

Problem


Pythonはグルー言語、として有名ですが、C#から呼び出す、というか.NET Framework上で動作するPythonの実装であるIronPythonはもう期待できる状態ではありません。

.NETでPythonを試してみる 第3回
前回は配列を引数で渡し、戻りを配列で受け取る関数を呼び出してみました。Introduction今回の目的は、パッケージを使います。PythonもNuget、npm、apt-getよろしくパッ...

ですが、Pythonで書かれたプログラムは豊富で、既存のプログラムから呼び出せるようにすると非常に便利なので、C/C++から呼び出す手法を習得してみます。
Visual Studioを想定しています。

Preparation


Python

PythonMod.py

足し算を行う関数です。

C++

ConsoleApplication.cpp

ソースはシンプルです。

Functions

使用している関数の説明です。

Py_Initialize

Python インタプリタを初期化。Python の埋め込みを行うアプリケーションでは、一番最初にこの関数を呼ぶ必要がある。

boost::python::import

指定した名前のモジュールをインポートします。
また、attr関数は指定した名前の属性を取得します。

__dictは特殊な属性で、クラスに対して使用した場合は、クラスに属するクラス変数やメソッドのオブジェクトが保存されており、クラスのインスタンスに対して使用した場合は、インスタンス変数の辞書が保存されている。

このあたりはお約束的なコードになる。

boost::python::exec_file

指定したファイル名のPythonスクリプトを実行します。
ただ、実行するといっても、この時点では何か実行されるわけではないです。
似た関数として、boost::python::execもあるが、こちらはPythonスクリプトの中身の文字列そのものを読み込む。
意味的には、第2引数、第3引数に指定した変数にデータを読み込んでいる感じ。

attr[scriptAddFunc]

先の説明にあったように、__dict属性は、メソッドや変数を保持している特殊な属性である。
そのため、exec_fileで読み込んだ後は、メソッドなどを名前で検索できるようになっている。
先に示したPythonスクリプト内のaddメソッドをオブジェクトとして取得しています。

boost::python::object v = pythonFun(2, 5);

オブジェクトとして取得したaddメソッドに引数を与えて実行しています。

boost::python::extract<int>>(v)

実行したaddメソッドの戻りを適切な型に変換しています。

VC++ Project Setting

VC++のプロジェクトの設定として

Include Directory

  • C:\Program Files\Miniconda2\pkgs\python-2.7.13-0\include
    Minicondaをインストールしている場合はここだが、環境依存。
  • <boost_dir>
    boostのインストールディレクトリ。このディレクトリからboost/python.hppが参照できる

Additional Library Directory

  • C:\Program Files\Miniconda2\pkgs\python-2.7.13-0\libs
    Minicondaをインストールしている場合はここだが、環境依存。
  • <boost_dir>\lib64-msvc-14.0
    インストールしているboostのバージョンに依存。

Additional Library

  • python27.lib
  • boostのlib
    ソース側でBOOST_PYTHON_STATIC_LIBを指定しているため指定不要。boostを静的にリンクすることになる。

Try


特に考えず、普通にビルドして実行するだけです。
注意するのは、Pythonスクリプトを実行ファイルと同一ディレクトリに配置することくらいです。

2+5の結果が正しく表示されています。

PythonMod.pyのaddメソッドを積算に変更した場合。

C++側の修正なしで挙動の変更が可能です。
このあたりはIronPythonと同じです。

開発メモ その86 Fedora 26 ServerでGitKrakenのデスクトップアイコンを表示する

Problem


前回、デスクトップにアイコンを表示できるようになりました。

WindowsならExplorerからAlt+ドラッグアンドドロップでショートカットを作れます。
Linuxでも可能ですが、これで作られるのは、ただのシンボリックリンクです。

Solution


結論から言うと、やり方がわかりませんでした\(^o^)/

ですが、ランチャに登録する方法はわかりました。
GithubGistにアイコンも含めて登録するスクリプトを書いてくださった方いました。

ただ、この方法だと、デスクトップに表示する方法で私の環境では動作しませんでした。
なので、少し書き換えて、ランチャに登録するようにしてみました。

viで開いたテキストに下記の内容を入力して保存します。


[Desktop Entry]
Name=GitKraken
Comment=Git Flow
Exec=/opt/gitkraken/gitkraken
Icon=/opt/gitkraken/icon.png
Terminal=false
Type=Application
Encoding=UTF-8
Categories=Utility;Development;

ランチャからGitKrakenが見つかるようになりました。
アプリを起動し、お気に入りに追加することもできます。

右クリックでメニューが表示されるので、お気に入りに追加をクリックします。

左側のバーに追加されました。

開発メモ その85 Fedora 26 Serverでデスクトップにアイコンを表示する

Problem


Fedora 26をインストールしたとき、デスクトップに何も表示されていませんし、アプリをデスクトップに表示したいと思いましたが方法がわからないのでメモ。

Solution


そのものズバリな記事を書いていらっしゃる方がいました。

GNOME デスクトップにアイコンを表示する
F edora 25 から、 Wayland がデフォルトの ウィンドウシステム に採用されるようになりました。Wayland は、 X Window System の代替を目指している Linux 向けに開...

Gnome Tweak Toolをインストールして設定すれば使えるとのこと。
下記でインストール可能。

起動は、デスクトップ画面で端末を立ち上げて、gnome-tweak-toolとして起動します。

デスクトップタブを選択します。

デスクトップにアイコンを表示するを有効にすると、アイコンが表示されます。