Cargo で gcc のフラグを任意に渡す方法→cargo rustc からのみ可能(2016-05-08修正)
要は Windows の GUI サンプルコードをお試しで動かすと コンソールも一緒に立ち上がってたのが嫌だったので調べると見つかった。
で、このフラグを Cargo から渡す方法はないか調べた。
確認環境
2016-05-08修正
申し訳ない、最初に書いた記事は自分の誤読で案について話しているだけで Cargoの設定ファイルで gcc へ任意のオプションを渡す方法は現時点では存在しておりませんでした。
ただ、cargo rustc
からであれば渡せます。
cargo rustc --release -- -C link_args=-Wl,--subsystem,windows
これは簡単なツール作って Windows エクスプローラから exe 起動して コマンドプロンプトが出なくなったのを確認済。
修正前の記事で紹介した
issue#544の件
のはまさしくこの cargo rustc
での機能を実装したよと言う事のみでした。すみません。
↓で見つけた。 github.com
やり方は簡単で、対象のプロジェクトの Cargo.toml に以下の一文を追加する。
[rustc] flags="-C link_args=\"-Wl,--subsystem,windows\""
MSVC ABI だとこの現象が発生しないのかは未確認。
ちなみにissue#544はcargo rustc
タスクでコマンドラインからオプションとして渡す方法がメインの話なのだが、
こちらでやると
前の記事の方法で設定した
追加ライブラリサーチパスが有効にならない。あくまでcargo run
orcargo build
した時だけって事なのかな。
Cargo でグローバルにライブラリサーチパスを追加する方法
Cargo で C ネイティブライブラリをリンクさせる為に 配置されているパスを Cargo に明示的に指示したい場合どうするか。
確認環境*1
プロジェクト単位での設定方法
探すと Qiita でこんな記事が見つかった。
グローバルに設定する方法
今回自分がやりたいのはこちら。
先に紹介した方法でもいいんだけど特に自分のような Windows ユーザだと MSVC/MinGW/Cygwin とかで配置する場所の慣習が変わってくるのと ほぼマルチユーザで使う事はないのでライブラリをインストールしたら プロジェクト単位すら面倒でグローバルに設定したくなる。
で Cargo のドキュメント探してたらあった。
Cargo は設定ファイルを記述する事が可能らしく
*2、
cargo run
や cargo build
実行時はまずその設定を読み込んでくれるらしい。
自分は %HOME% を設定してるので、%HOME%.cargo\config ファイルを配置。 そしてライブラリサーチパスの設定を以下のように書いた。 *3
[target.native] rustc-link-search = ["C:/path/to/lib"]
["C:/path/to/lib"]
は自分がリンクさせたいライブラリが存在するパスを指定する事。
参考
- http://doc.crates.io/build-script.html#overriding-build-scripts
- (推測) リンク先のサンプルは 64bit linux で foo ライブラリをリンクする際のパス指定方法だと思われる
一度このドキュメントはどこかでちゃんと読み込んでおきたいかな。 Tomlファイル自体の形式は分かりやすいんだけど何をどう設定できるのかがあんまり把握できてないし。
Rust で try! マクロが上手く動かなかった
Rust 絶賛学習中なんだけども、try! を
使用したサンプルが動かなかったのでメモとして残す。
原因はちゃんと追ってないが、状況と回避方法だけ。
(と言っても try! マクロ使わないようにするってだけだけど)
2016-05-08 追記
原因分かった。未読だったエラーハンドリング を読んでtry! の API docでのサンプル見てやっと理解した。
Result を返す関数の中で記述を簡略化する為のものなのね。
Rust の main は戻り値が無い(()
を返す) 所に
try!
マクロ内の処理が失敗すると return Err が返るようになってるからコンパイルエラーになると。
けどそれならそれでサンプルは何がしかの Result を返す関数内で使うサンプルにすべきじゃないのかなあ。 まだまだ勉強が足りんかな。
と言うわけで単にtry!を使わないようにすると言うのはプロトタイピングレベルじゃなければやらないようにすべきなので 冒頭のは完全に消しはしないけど打ち消し線つけさせておいてもらいます。
環境
- Win7 Pro 64bit
> rustc --version rustc 1.8.0 (db2939409 2016-04-11)
- GNU ABI
状況
ファイル IO をやってみたくて API doc のサンプルを コンパイルするとコンパイルエラー発生。
fn main() { use std::io::prelude::*; use std::fs::File; let mut buffer = try!(File::create("foo.txt")); try!(buffer.write(b"some bytes")); }
<std macros>:5:8: 6:42 error: mismatched types: expected `()`, found `core::result::Result<_, _>` (expected (), found enum `core::result::Result`) [E0308] <std macros>:5 return $ crate:: result:: Result:: Err ( <std macros>:6 $ crate:: convert:: From:: from ( err ) ) } } ) main.rs:37:22: 37:51 note: in this expansion of try! (defined in <std macros>) <std macros>:5:8: 6:42 help: run `rustc --explain E0308` to see a detailed explanation <std macros>:5:8: 6:42 error: mismatched types: expected `()`, found `core::result::Result<_, _>` (expected (), found enum `core::result::Result`) [E0308] <std macros>:5 return $ crate:: result:: Result:: Err ( <std macros>:6 $ crate:: convert:: From:: from ( err ) ) } } ) main.rs:39:5: 39:39 note: in this expansion of try! (defined in <std macros>) <std macros>:5:8: 6:42 help: run `rustc --explain E0308` to see a detailed explanation error: aborting due to 2 previous errors
エラーメッセージ見るとマクロ展開時に期待する型じゃないとか言われた。
けど API doc じゃ
File::create
は Result 返すし
try! マクロ も Result を返すもので使うみ
たいな事書いてあるのに、エラーメッセージはどうもそうなってない。
とりあえず try!
を使用しないようにすればファイル書き込みはいけた。
fn main() { use std::io::prelude::*; use std::fs::File; let mut buffer = File::create("foo.txt").expect("cannot create file."); buffer.write(b"some bytes"); }
マクロのコードも追っかけてみたいけどまだ Rust でのマクロの作り方は全く学習してないので保留。
Rust 開発環境構築 - Eclipse で構築してみた
LifeTime や Trait、関数型プログラミング的な事も可能らしいシステムプログラミング言語辺りの ワードが気になって Rust を始めてみようと思いたった。
で、まずは環境構築からと言う事で探してみた。
開発環境選定
タイトルにも入れてるが今回は Eclipse のプラグインで提供されている RustDT を選ぶことにした。 デバッグ機能が頭一つ抜けていると思ったため。
定義ジャンプ・コード補完・色付け辺りは大体どの環境も備えてて、gdb をコマンドラインでガシガ シ使える人ならどれを選んでもそんなに機能差は無いと思う。
以下各環境を少し調べた雑感。
Emacs
- 個人的には手を切りたいエディターというのはさておき
- 例によって色々モードはあり設定も今はさほど面倒でもない
- GDB とのデバッグ連携もかなり GUI っぽくなってるんだが 見た目がもはや他の IDE よりも煩雑になってる感じなのでスルー
IntelliJ
- こちらもプラグインがあるのだが軽く情報を探った感じデバッガ連携が見当たらなかったので見送り
- サイトを見ただけで試してはいない
VisualStudio
Eclipse
他にもいくつか見かけたが未確認。
事前環境
- MinGW-w64
- Rust 1.8.0 GNU ABI
- racer
- コード補完を受け持つ外部ツール
- 一番楽なのは Rust 入れた後
cargo install racer
とコマンド打つだけ
- Rust のソースを DL、環境変数 RUST_SRC_PATH にソースを展開したパスを指定してある事
- racer で必要
結構事前準備が必要なんだけどどれもさほど面倒でもないのと記事を書いた時点では 既に導入してしまっていたので割愛。
Eclipse, RustDT インストール
とは言っても、既に ブログ記事 があったので基本はそこに従った。
ただ、事前環境でも書いたが、Rust は GNU ABI の方を入れる事。
デバッグ動作確認
こんなコードを書いた。*1
fn main() { let a = 10; let b = 20; let c = "こんにちわ"; println!("{}, {} 年後の世界!", c, add(a, b)); } fn add(x: i32, y: i32) -> i32 { x + y }
んで2行目にブレークポイント設定してデバッグ実行。ブレークポイント設定は行表示している辺りを ダブルクリックすれば設定される。
んでブレークした所にも止まるし、ステップ実行も可能なんだけど変数を見る時 数値はいいんだが文字列は C/C++ 同様パッと見た感じさっぱり分からん。
ここ に書かれていた事を頼りに gdb の Rust pretty-printer を導入してみたが 文字列は対応してないっぽい。
文字列の簡単なデバッグ方法が今後の課題だけどとりあえずは しばらく RustDT を使いつつ勉強してみよう。
Dungeon Crawl Stone Soup 0.17.1(英語版)をビルドしてみた
ちょっと思う所があって PC フリゲのローグライクの一つである Dungeon Crawl Stone Soupをソースからビルドして上手く行ったので その時の環境をメモしておく。
- OS は Win7 Pro 32bit
- ソースは 公式に置かれてる
Full source with dependencies
のリンクから DL- 試したバージョンは 0.17.1。
- ビルド方法は MinGW。手順は INSTALL.txt に書かれている事そのまま実行するだけ。
ソースビルド上手く行ったよって記事は賞味期限めちゃくちゃ短い気がするけどまあ。 英語だけどソースDLすれば本当にちゃんと手順が書かれてるので細かい事はここでは書きません。 繰り返しだけどソースビルド関係は特に腐るの早そうだし。
cider での TDD っぽいワークフロー
ワークフロー
- REPL 起動(
C-c M-j
) ※ 1 回のみ - 何か関数書く
- REPL 上でテスト
- ok なら保存・リロード(
C-x C-s
,C-c C-n
,C-c C-k
) - REPL 上で実行したコードと結果を = とした is フォームにコピペし、
適当な名前を付けて保存・リロード(
C-x C-s
,C-c C-n
,C-c C-k
) C-c ,
でテスト
2-6 を繰り返す。
TDD と言うよりは REPL で試した結果を残すようにすると言った方が正しいかも。