mieki256's diary



2018/03/12(月) [n年前の日記]

#1 [windows][mruby] Visual Studio上でデバッグウインドウに何かメッセージを出す

昨日、Visual Studio 2015 Community上で、C++ で書いたプログラム内から何かメッセージをどこかしらに出力したいけど出力されなくて悩んでたのだけど。

その後ググってたら、#include <Windows.h> をして、OutputDebugString() を使えば、デバッグウインドウにメッセージを出せるらしい、と分かった。

_その3 デバッグウィンドウを知らないと大変です
_Win32アプリケーションのデバッグ方法 [VC++の使い方]

ただ、tchar.h もインクルードして、出力したい文字列は _T("hoge") と囲まないといかんようだなと…。
#include <Windows.h>
#include <tchar.h>

...

        OutputDebugString(_T("# MSG: Load Image\n"));

...

もっとも、コレ、Windows + Visual Studio でしか使えない気がするわけで。MinGW用や、*NIX上でも使えるソースを書きたい場合は、何かもうちょっと工夫が必要になるのだろうなと。

まあ、動作確認が終わったら、該当行をコメントアウトしちゃうだけでもいいのかもしれんけど。

#2 [ruby][mruby] MinGWでSDL2関係のビルドができるか実験

Windows10 x64 上で、mruby-sdl2 をビルドしたい。が、どうも sdl2-config を呼び出してるように見える。

_crimsonwoods/mruby-sdl2: mrbgem to use SDL2.0
_mruby-sdl2/mrbgem.rake at master - crimsonwoods/mruby-sdl2

sdl2-config の中身はシェルスクリプトなので、bash だの sh だのが用意されてる環境が前提のような気がする。となると、Visual Studio (Visual C++) を使ったビルドはできない予感。

しかし、もしかしたら MinGW + MSYS ならビルドできるのだろうか…? 実験してみないと分からんな…。実験しよう…。

SDL2関係のインストール。 :

以下の記事を参考にして、MinGW + MSYS で、SDL2関係が使えるように環境を整える。

_MinGW 用の SDL2 インストール手順 メモ
_MinGW (32bit) 開発環境 インストール手順 メモ

自分の環境には MinGW + MSYS がインストールしてあるので、足りてなかった mingw32-libz dev (v1.2.8-1) だけ、MinGW Installer を使って、追加インストールした。

環境変数PATHの最初のほうに、以下を追加した状態で…。つまり、MinGW の bin/* と、MSYS の bin/* が呼び出せるようにしておいてから…。
C:\mingw\MinGW\bin;C:\mingw\MinGW\msys\1.0\bin

C:\mingw\MinGW\msys\1.0\msys.bat を実行。bash が起動する。

MinGW 用の SDL2関係ファイルを入手。

_Simple DirectMedia Layer - SDL version 2.0.8 (stable)
_https://www.libsdl.org/release/SDL2-devel-2.0.8-mingw.tar.gz

SDL2-devel-2.0.8-mingw.tar.gz をDL・解凍して、出てきたディレクトリをカレントディレクトリにする。今回は、D:\sdl2\dev\mingw\ というフォルダを作成して、その中に入れておいた。

以下を実行。
make install-package arch=i686-w64-mingw32 prefix=/mingw

これで、MinGWインストールフォルダ内の bin/ , include/ , lib/ ディレクトリ等の中に、SDL2関係のファイル(*.dll , *.h , *.a 等)がコピーされた。ちなみに、sdl2-config も bin/ にコピーされて、実行権限もついている。

この make install-package、今まで知らなかった…。これでサクッと下準備ができたのか…。

ビルドしてみる。 :

以下を参考にして、サンプルがビルドできるかどうか確認。

_MSYS2 + MinGW 環境に SDL2 をインストール - takaya030の備忘録

適当なフォルダを作成して、sdl2_sample.cpp を作成。sdl2_sample.cpp の内容は、上記ページのソレを使わせてもらったり。ちなみに、return (TRUE); でエラーが出たので、return (true); に変更。

Makefile を作成。上記ページのソレを参考にして、内容は以下にした。SDL_PREFIX を /mingw にしてるところが違い、だろうか。
TARGETS = sdl2_sample

all: $(TARGETS)

SDL_PREFIX  = /mingw
SDL_CONFIG  = $(SDL_PREFIX)/bin/sdl2-config
CG_LIBS     =

CROSS_COMPILE   = /mingw/bin/
CC = $(CROSS_COMPILE)gcc
CXX = $(CROSS_COMPILE)g++

CFLAGS = -g -Wall `/bin/sh $(SDL_CONFIG) --cflags`
CXXFLAGS = -g -Wall `/bin/sh $(SDL_CONFIG) --cflags`
LDFLAGS = `/bin/sh $(SDL_CONFIG) --libs`    -Wl,-rpath,$(SDL_PREFIX)/lib
LIBS = -lopengl32 -lglu32 -lm

clean:
    rm -f *.o *.a *~ $(TARGETS)

sdl2_sample: sdl2_sample.o
    $(CXX) -o $@ $^ $(LDFLAGS) $(LIBS)
clean: だの sdl2_sample: だのの次の行の先頭のスペースは、タブ文字を入れておかないといかんらしい。空白スペース4つにしたら、「区切り文字がおかしいぞ」と怒られた。

make を実行。sdl2_sample.o と sdl2_sample.exe ができた。

sdl2_sample.exe を実行。ウインドウが開いて何か描画された。

とりあえずここまでの作業で、MinGW + MSYS を利用すれば SDL2 を使った何かしらをビルドすることはできる、と分かった。

mruby-sdl2 をビルドしようとするが失敗。 :

以下の mrbgem をビルドできるのか実験。

_crimsonwoods/mruby-sdl2: mrbgem to use SDL2.0

mruby のファイル一式が入ってるディレクトリをカレントディレクトリにして、build_config.rb を編集。以下を最初のほうに追加。
conf.gem :github => 'crimsonwoods/mruby-sdl2', :branch => 'master'

make を実行。エラーが出た。
$ make
ruby ./minirake
(in d:/Ruby/mruby/mruby)
CC build/mrbgems/mruby-sdl2/src/misc.c -> build/host/mrbgems/mruby-sdl2/src/misc.o
gcc: error: `sdl2-config: No such file or directory
gcc: error: unrecognized command line option '--cflags`'
gcc: error: `sdl2-config: No such file or directory
gcc: error: unrecognized command line option '--cflags`'
rake aborted!
Command Failed: [gcc -g -std=gnu99 -O3 -Wall -Werror-implicit-function-declaration -Wdeclaration-after-statement -Wwrite-strings -g3 -O0 `sdl2-config --cflags` -DMRB_DEBUG -DMRBGEM_MRUBY_SDL2_VERSION=0.0.0 -I"d:/Ruby/mruby/mruby/include" -MMD -o "d:/Ruby/mruby/mruby/build/host/mrbgems/mruby-sdl2/src/misc.o" -c "d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c"]
make: *** [all] Error 1

sdl2-config が無いと言われてるような気がする…。でも、変だな。sdl2-config は、PATHが通った場所に、ちゃんとあるように見えるけど。
$ which sdl2-config
/mingw/bin/sdl2-config
あるよなあ。おかしいな。

Windowsの場合はshebangが使えないのではないかという疑惑。 :

*NIXの世界では、shebang というものがあって。

_シバン (Unix) - Wikipedia

テキストファイルの一行目に、
#!/bin/sh
とか
#!/usr/bin/ebv ruby
と書いておくと、

「このテキストファイルは /bin/sh で動かすファイルだよ」
「このテキストファイルは /usr/bin/env ruby で見つかったファイルで動かすファイルだよ」

という指定になって、それぞれを動かすことができる ―― てな仕組みを shebang と呼ぶらしい。

sdl2-config も、一番最初の行に、
#!/bin/sh
と書いてある。だから、bash上で、いきなり sdl2-config と打っても、実行することができる。

しかし、Windows上で動く Ruby は、shebang は見てないような気がするわけで。
mieki256@hogefuga: MINGW32: ~$ ruby -v
ruby 2.2.6p396 (2016-11-15 revision 56800) [i386-mingw32]

mieki256@hogefuga: MINGW32: ~$ irb

irb(main):001:0> `echo "hoge"`
=> "\"hoge\"\n"

irb(main):002:0> `which sdl2-config`
=> "\"C:\\mingw\\MinGW\\bin\\sdl2-config\"\n"

irb(main):003:0> `sdl2-config`
Errno::ENOENT: No such file or directory - sdl2-config
        from (irb):3:in ``'
        from (irb):3
        from c:/Ruby/Ruby22/bin/irb:11:in `<main>'

irb(main):004:0> `sh sdl2-config`
Usage: sdl2-config [--prefix[=DIR]] [--exec-prefix[=DIR]] [--version] [--cflags] [--libs] [--static-libs]
=> ""

irb(main):005:0> exit

MinGW + MSYS 上で、Ruby mingw版 の irb を実行すると…。
  • `which sdl2-config` で、sdl2-config が置いてある場所を把握できていることは分かる。
  • しかし、`sdl2-config` をしても、実行できない。
  • `sh sdl2-config` なら、実行できる。
ということで、どうも shebang は見てないのではないか、そのファイルを何を使って動かすか、そこまで指定しないといかんのではないかなあ、という気がしてきたわけで。

ならば、mruby-sdl2 の、mrbgem.rake を修正して、sdl2-config の前に sh をつければ動くのだろうか。以下のように修正してみた。
MRuby::Gem::Specification.new('mruby-sdl2') do |spec|
  spec.license = 'MIT'
  spec.authors = 'crimsonwoods'

  spec.cc.flags << '`sh sdl2-config --cflags`'
  spec.linker.flags_before_libraries << '`sh sdl2-config --libs`'
end

mieki256@dorobune: MINGW32: /d/Ruby/mruby/mruby$ make
ruby ./minirake
(in d:/Ruby/mruby/mruby)
CC build/mrbgems/mruby-sdl2/src/misc.c -> build/host/mrbgems/mruby-sdl2/src/misc.o
gcc: error: `sh: No such file or directory
gcc: error: sdl2-config: No such file or directory
gcc: error: unrecognized command line option '--cflags`'
gcc: error: `sh: No such file or directory
gcc: error: sdl2-config: No such file or directory
gcc: error: unrecognized command line option '--cflags`'
rake aborted!
Command Failed: [gcc -g -std=gnu99 -O3 -Wall -Werror-implicit-function-declaration -Wdeclaration-after-statement -Wwrite-strings -g3 -O0 `sh sdl2-config --cflags` -DMRB_DEBUG -DMRBGEM_MRUBY_SDL2_VERSION=0.0.0 -I"d:/Ruby/mruby/mruby/include" -MMD -o "d:/Ruby/mruby/mruby/build/host/mrbgems/mruby-sdl2/src/misc.o" -c "d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c"]

make: *** [all] Error 1

sdl2-config のみならず、sh すら見つからないと言ってきた。うーん。

もしかして、rake だか minirake だか分からんけど、どうもソレが動いてるときは、MinGW の bin/ や MSYS の bin/ を検索できないPATH状態になっているのかな…。

直接書いてみる。 :

このあたり、要するに、sdl2-config が出力した文字列を、コンパイラだかリンカだかのオプションとして指定してる、ということだよなと。

だったら、sdl2-config を介さずに、sdl2-config が出力した文字列を、mrbgem.rake に直接書いちゃえば、ひとまずビルドが通ったりしないかと思えてきたわけで。
$ sdl2-config --cflags
-I/mingw/include/SDL2 -Dmain=SDL_main

$ sdl2-config --libs
-L/mingw/lib -lmingw32 -lSDL2main -lSDL2 -mwindows

上の出力結果を参考にして、mrbgem.rake を以下のように修正。
MRuby::Gem::Specification.new('mruby-sdl2') do |spec|
  spec.license = 'MIT'
  spec.authors = 'crimsonwoods'

  # spec.cc.flags << '`sh sdl2-config --cflags`'
  # spec.linker.flags_before_libraries << '`sh sdl2-config --libs`'
  spec.cc.flags << '-I"d:/mingw/MinGW/include/SDL2" -Dmain=SDL_main'
  spec.linker.flags_before_libraries << '-L"d:/mingw/MinGW/lib" -lmingw32 -lSDL2main -lSDL2 -mwindows'
end

これで make したら…。
mieki256@dorobune: MINGW32: /d/Ruby/mruby/mruby$ make
ruby ./minirake
(in d:/Ruby/mruby/mruby)
CC build/mrbgems/mruby-sdl2/src/misc.c -> build/host/mrbgems/mruby-sdl2/src/misc.o
d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c: In function 'mrb_sdl2_misc_buffer_initialize':
d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c:37:3: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
   mrb_sdl2_misc_buffer_data_t *data =
   ^~~~~~~~~~~~~~~~~~~~~~~~~~
d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c:49:3: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement] enum mrb_vtype const arg_type = mrb_type(arg); ^~~
d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c:62:25: error: implicit declaration of function 'mrb_ary_len' [-Werror=implicit-function-declaration] mrb_int const n = mrb_ary_len(mrb, arg); ^~~~~~~~~~
... d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c:446:3: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement] mrb_sdl2_misc_buffer_data_t *data = ^~~~~~~~~~~~~~~~~~~~~~~~~~
cc1.exe: some warnings being treated as errors rake aborted! Command Failed: [gcc -g -std=gnu99 -O3 -Wall -Werror-implicit-function-declaration -Wdeclaration-after-statement -Wwrite-strings -g3 -O0 -I"d:/mingw/MinGW/include/SDL2" -Dmain=SDL_main -DMRB_DEBUG -DMRBGEM_MRUBY_SDL2_VERSION=0.0.0 -I"d:/Ruby/mruby/mruby/include" -MMD -o "d:/Ruby/mruby/mruby/build/host/mrbgems/mruby-sdl2/src/misc.o" -c "d:/Ruby/mruby/mruby/build/mrbgems/mruby-sdl2/src/misc.c"] make: *** [all] Error 1
今までと違って、sdl2-config が見つからない等の文句は出なくなった。しかし、それでもエラーが。「mrb_ary_len なんて知らんわい」と怒られてる。

ググってみたら、mrb_ary_len は、 _mruby 1.3.0 まではあった けど、 _mruby 1.4.0 では無くなった ように見える。

ということは、mrb_ary_len() を別の何かで代替すればビルドできるようになるのかな。と思ってググってみたけど、「代わりにコレを使えや」という話は見つからず。そもそもどうして無くなったんだろう…。神様の気分かな。

ならば、mruby 1.3.0 のファイル一式を使えばビルドできるんじゃないか。 _Releases - mruby/mruby から 1.3.0 のzip をDL・解凍して、それらのファイル群を使って試してみた。

今度は「strlen なんて知らねえよ」とエラーが出た。

おかしいな…。mruby のソースの中でも strlen() って結構使われてるのに…。

mruby-sdl2 の sdl2.h に #include <string.h> を追加してみた。一応ビルドは通ったように見えた。

ビルドは通ったけど、実行してもうんともすんとも言わない mruby.exe や mirb.exe が出来上がってしまった…。なんだこりゃ…。

mruby-sdl2 を追加すると、文字の出力ができない mruby, mirb が出来上がるっぽいな…。外してビルドすると各種メッセージがちゃんと表示される…。何故。

余談。 :

mruby関係の記事をググって眺めていた際、「mruby のライブラリ作者は mruby 本体のアップデートに追従していくのが大変」という話を見かけたけれど。なるほど、こんな感じで、今までビルドできていたものがビルドできなくなっていくのかと、たかだか一例ではあるけれど、素人なりになんとなく分かったつもりになったりもして。

また、Ruby関係は、「タダ乗りさせないために積極的に改変していく」「タダ乗り連中は置いてけぼりにする」というポリシーで開発をしていると神様自ら発言しているわけで…。

_今日現在のmrubyについて雑想 - もなもなもなかのページ
_参加しないと見せないよ.を作った罪 - もなもなもなかのページ

「コレどうしてビルドできないんだ」と仮に問うてみても、「俺達についてこないライブラリ作者が悪い」と返されるのがRubyの文化、なのだろうと。

mruby + SDL2 で、love2d みたいな形でアプリを作っておけば、CRuby のバージョンが上がるたびにライブラリ側も更新する苦労を味合わなくて済むのだろうか、などと素人考えで夢想していたのだけど。mruby も mruby で、コレを使うのはなんだか大変そうだなという印象になってきたりもして。だったら、まだ、古い CRuby + ライブラリで作業してたほうがいいのかもしれないよな…。

いやまあ、love2d みたいなのが欲しければ love2d 使えばいいじゃん、lua も比較的習得しやすい言語だし、という話にもなりそうだけど。

以上、1 日分です。

過去ログ表示

Prev - 2018/03 - Next
1 2 3
4 5 6 7 8 9 10
11 12 13 14 15 16 17
18 19 20 21 22 23 24
25 26 27 28 29 30 31

カテゴリで表示

検索機能は Namazu for hns で提供されています。(詳細指定/ヘルプ


注意: 現在使用の日記自動生成システムは Version 2.19.6 です。
公開されている日記自動生成システムは Version 2.19.5 です。

Powered by hns-2.19.6, HyperNikkiSystem Project