MinGW + MSYSでVST Plug-inを作る方法とサンプル。
prefix=/opt/MinGWとします。bootstrapには、MinGWのバイナリが必要になりますが、まず binutilsをsourceからbuildします。
$ tar -zxvf binutils-2.16.91-20060119-1-src.tar.gz
$ cd binutils-2.16.91-20060119-1
$ ./configure --prefix=/opt/MinGW --target=i386-mingw32 -v
$ sudo make install
次に、bootstrap用のバイナリとヘッダファイルとライブラリファイルを$prefix/$targetに解凍します。 この時点ではw32apiとmingw-runtimeをsourceからbuildすることはできません。
$ sudo tar -zxvf w32api-3.8.tar.gz -C /opt/MinGW/i386-mingw32/
$ sudo tar -zxvf mingw-runtime-3.11.tar.gz -C /opt/MinGW/i386-mingw32/
次にgccをbuildします。configureでは、languagesとprefixとtarget以外は好きに選んで下さい。 make CFLAGS="-O2 -fomit-frame-pointer" CXXFLAGS="-mthreads -fno-omit-frame-pointer -O2" LDFLAGS=-s bootstrap などもできますが、エラーが出る事があります。オプションはほどほどにしましょう。
$ tar -zxvf gcc-core-3.4.2-20040916-1-src.tar.gz
$ tar -zxvf gcc-g++-3.4.2-20040916-1-src.tar.gz
$ mkdir gcc-work;cd gcc-work
$ ../gcc-3.4.2-20040916-1/configure --enable-languages=c,c++ \
--prefix=/opt/MinGW/ --with-gcc --with-gnu-ld --with-gnu-as \
--target=i386-mingw32 --enable-threads --disable-nls \
--disable-win32-registry --disable-shared \
--enable-sjlj-exceptions --disable-libstdcxx-debug
$ make
$ sudo make install;cd ..
以上最低限はおわりです。正しくかかれたautotoolsでは--target=i386-mingw32とし、 /opt/MinGW/binにパスを通せば使える筈ですが、だめならCCなどをオーバーライドします。
PATH=$PATH:/opt/MinGW/bin
build=i486-slackware-linux
target=i386-mingw32
host=i386-mingw32
./configure --prefix=/opt/MinGW --build=$build --host=$host --target=$target
リンクの順番は大事です。gccを直接呼び出す場合、使用するライブラリ (-lkernel32など)は最後に書きますが、automakeなどを使用していると、 libtoolが勝手に並べかえるので、gccでなくlinkerに渡すコマンド(-Wl,-lkernel32) としてかき、最後に持ってくるようにします。
# Makefile.am
lib_LTLIBRARIES = Freeverb3VST.la
Freeverb3VST_la_LDFLAGS = -module -avoid-version -no-undefined \
-Wl,-lkernel32
Freeverb3VST_la_LIBADD = ...
Freeverb3VST_la_SOURCES = ...
リンクの順番を間違えると以下のようなエラーが出ます。
/opt/MinGW//i386-mingw32/lib/libmingwex.a(gettimeofday.o):gettimeofday.c:(.text+0x45): undefined reference to `___udivdi3'
/opt/MinGW//i386-mingw32/lib/libmingwex.a(gettimeofday.o):gettimeofday.c:(.text+0x60): undefined reference to `___umoddi3'
/opt/MinGW//i386-mingw32/lib/libmingwex.a(gettimeofday.o):gettimeofday.c:(.text+0x8a): undefined reference to `___udivdi3'
windresはconfigure.inで以下のようにして取得でき、Makefile.am内で$(WINDRES)として使用できます。
(
Autotools Generic Program and File Checks)
AC_CHECK_TARGET_TOOL([WINDRES], [windres], [no])
if test "x$WINDRES" = "xno"; then
AC_MSG_ERROR([Cannot find windres])
fi
AC_SUBST(WINDRES)
architecture-vendor-osSometimes the vender tag is left out. The following are several examples of common architecture tags used:
i386-redhat-linux
ppc-yellowdog-linux
ppc-apple-darwin
i686-pc-cygwin
i386-mingw32
i386-pc-mingw32
i686-pc-cygwin
i386-linux
i686-linux
sparc-linux
sparc64-linux
arm-linux
When configuring, if you don't know the full vender tag, you can often just use the platform-os name.
export set PATH=/usr/i586-mingw32msvc/bin:$PATH
export set build=i486-linux-gnu
export set host=i586-mingw32msvc
export set target=i586-mingw32msvc
cygwin,MinGW/make 3.81でときどき発生するようです。クロスコンパイル時のパスの扱いに問題があり、 パッチの情報があります。 別のバージョンを使う手もあります。UNIXなのに、PloにC:\MinGW\...などと 設定されているのが原因です。どうしてもうまくいかないときは、*.Ploや.cacheなどすべての 生成されたファイルを消去して初めからautotoolsをやり直すのもよいかもしれません。
シングルスレッドですむ場合には特に気をつける必要がないのですが、マルチスレッドプログラムを
ビルドする場合、TLS(Thread Local Storage)やEH(Exception Handling)の機構を利用するので、
いろいろと気をつける必要があります。
よくある問題が、-mthreads利用時のmingwm10.dllへの依存です。
-D_MT -mthreadsによって、多くのビルトイン関数(putとか)がthread-safe ライブラリを利用するようになりますが、
その時、マルチスレッドでtry-catchなどEHを利用する場合にMinGWライブラリの不整合から
少なくとも24bytesずつメモリリークするのを防ぐために、
DllMain()トラップを利用してリソースの開放を行うためのちょっとしたハックです。EHを使わないなら
-fno-exceptionsで明示すればよいですが、ふつうはEHを使っているのでリークの原因となります。
ちなみに、SEHは、Windowsでデバッグ情報などの例外を管理するための機構で、C++のEHとは違いますが、SEHをC++のEHで
とらえるようにできます(/EHa)。
古いOSのサポートは面倒ですね。
Makefile.amでLDFLAGS += -Wl,-lmingw32 -Wl,-lmingwex -Wl,-lmingwthrdとかするとよい。 まあ、見つからない関数をlibディレクトリでかたっぱしからgrepすればリンクすべきライブラリは みつかるんだけど。あと、リンクする順序には気をつけましょう。
rateconv.o:rateconv.cpp:(.text+0xa40): multiple definition of `_main'
libmingw32.a(main.o):(.text+0x0): first defined here
libmingw32.a(main.o):(.text+0x85): undefined reference to `_WinMain@16'
dllを作るときには-lmingw32をつけてもいいですが、単体exeを作る時に-lmingw32を入れるとエラーになります。
configure;make;make installでインストールしないで*.aだけをコピーしたりすると以下のような エラーを吐いてdllが生成されないことがあります。
*** Warning: linker path does not have real file for library -lfftw3f-sse.
*** I have the capability to make that library automatically link in when
*** you link to this library. But I can only do this if you have a
*** shared version of the library, which you do not appear to have
*** because I did check the linker path looking for a file starting
*** with libfftw3f-sse and none of the candidates passed a file format test
*** using a file magic. Last file checked: /mnt/CVS/freeverb3_vst/lib/libfftw3f-sse.a
静的ライブラリだと、基本的には、*.laと.libs/*.aでペアになるのがlibtoolの作法なので、“どうしても”手動で コピーしたい場合は、*.laと.libs/*.aをセットになるようにしましょう(.libsは自分で掘る)。ふつうはmake installが すべてやってくれるんですが。上は、libfftw3f-sse.aのみをコピーしたためにエラーとなりました。 *.laはテキストファイルなので、ほかから*.laを持ってきてold_libraryの部分「のみ」を書き換えて対処できます。 ちなみに、コメント部分を消すとうまくいきません。 (なお、libtoolが.laファイルの2行目の「libtoolのバージョン」を参照するため、.laファイルの先頭2行のコメントは削除してはならない。) -lfooとしても、そこにlibfoo.aがあるのかlibfoo.laがあるのか、 はたまたlibfoo.soがあるのか、libfoo.dll.aがあるのか、libtoolにすべて任せるほうが簡単でしょう。
MinGW w64で普通にビルドすると、いくつかのDLL依存になることがあります。 libgcc_s_sjlj-1.dll や libstdc++-6.dllはstatic linkにすることもできます。-static-libgccや-static-libstdc++は gccやg++へのオプションなので、libtoolを利用している場合には、LDFLAGSから削られてしまうことがあります。 どうしても依存をなくしたい場合は、x86_64-w64-mingw32/lib64/libstdc++.dll.aをlibstdc++.aへのリンクに、 libgcc_s.aをlib/gcc/x86_64-w64-mingw32/4.5.0/libgcc.aへのリンクにすると強制的にstatic linkとなります。 libgcc_eh.aはlibgcc.aに含まれないいくつかのexception handlingのコードを含んでいますが、 libgcc_s.soというshared libraryはすべてを含んでいます。
上で述べたように、dll依存のライブラリと静的リンクのライブラリが共存しているので、 動的・静的ライブラリ両方を指定するなど、リンクの仕方を間違えると出ます。やっていることが わかっていれば、--allow-multiple-definitionを使って強制的にリンクできますが、MinGWやcygwinでは 時々起る問題で、DLL間でexceptionを投げられるようになるなど動的ライブラリが望ましいんですが、 バイナリ配布のときにはDLLをインストールさせるのが面倒だったりするので一概には決められないのが難点です。
MPlayer cross-platform UNIX movie player, Cygwin port
Benchmarking SSE instructions - Stack Overflow
Old Nabble - MinGW - User - MinGW with SIMD (SSE, etc)
整列したメモリを静的に確保する attribute ((aligned(n)) - PS3 Linux Information Site / Cell/B.E.のパワーを体験しよう
株式会社エス・スリー・フォー ≫ Blog Archive ≫ sizeofの不思議
The Road to Hell Is Paved with Good Intentions
Yet another Unix nightmare: statically linking libstdc++ | 2005-05-31 | christopher baus.net
This sender of this e-mail is privileged and has protexia with people in high
places. Don't ask, they are in high places. You could not have received it in
error, we know what we are doing. If it has any scandal or gossip value please
notify the newspapers, television and radio by e-mail and then delete
everything from your system. Please copy it and use it for any purposes, and
especially disclose its contents to the press: to do so would be exactly what
we really wanted. This disclaimer is to cover our you-know-what if it ever got
out that we sent it to you. Thank you for your co-operation. Please dial 911
if you need assistance.
Geoffrey S. Mendelson in Linux-IL message 02/09/msg00090.html
-- Geoffrey S. Mendelson
-- Message to Linux-IL ( http://www.mail-archive.com/linux-il%40cs.huji.ac.il/msg21564.html )
The last thing one knows in constructing a work is what to put first.
-- Blaise Pascal