Upgrade to Pro — share decks privately, control downloads, hide ads and more …

RustからPythonを呼び出す

 RustからPythonを呼び出す

Rust 1.0 Release記念祝賀LT会のスライドです
補足:http://d.sunnyone.org/2015/05/rustpython.html

sunnyone

May 16, 2015
Tweet

More Decks by sunnyone

Other Decks in Technology

Transcript

  1. コード例 extern crate cpython; use cpython::{PythonObject, Python}; fn main() {

    let gil_guard = Python::acquire_gil(); let py = gil_guard.python(); let sys = py.import("sys").unwrap(); let version = sys.get("version").unwrap()                 .extract::<String>().unwrap(); println!("Hello Python \"{}\"", version); }
  2. 特徴的なところ extern crate cpython; use cpython::{PythonObject, Python}; fn main() {

    let gil_guard = Python::acquire_gil(); let py = gil_guard.python(); let sys = py.import("sys").unwrap(); let version = sys.get("version").unwrap()                 .extract::<String>().unwrap(); println!("Hello Python \"{}\"", version); } GIL (Giant Interpreter Lock) 獲得にRAIIを活用 ↓ PyGILState_Ensure() と PyGILState_Release() 呼び出しが簡略化
  3. acquire_gil実装部分 #[must_use] pub struct GILGuard { gstate: ffi::PyGILState_STATE } impl

    GILGuard { pub fn acquire() -> GILGuard { ::pythonrun::prepare_freethreaded_python(); let gstate = unsafe { ffi::PyGILState_Ensure() }; GILGuard { gstate: gstate } } } impl !Send for GILGuard {} impl Drop for GILGuard { fn drop(&mut self) { unsafe { ffi::PyGILState_Release(self.gstate) } } } pythonrun.rs (抜粋+コメント削除/順序他編集) Ensureしたstateを GILGuard構造体に保存 Drop traitで Release
  4. 罠 • コンパイルできない src/objects/num.rs:81:23: 81:59 error: unresolved name `std::num::cast` src/objects/num.rs:81

    match std::num::cast::<c_long, $rust_type>(val) { src/objects/num.rs:61:1: 88:3 note: in expansion of int_fits_c_long! src/objects/num.rs:116:1: 116:22 note: expansion site src/objects/num.rs:81:23: 81:59 error: unresolved name `std::num::cast` src/objects/num.rs:81 match std::num::cast::<c_long, $rust_type>(val) {
  5. 罠 • src/objects/num.rsを見ると… // TODO: manual implementation for i64 on

    systems with 32-bit long // TODO: manual implementation for i64 on systems with 32-bit long (つд ) ⊂ ゴシゴシ (;゚д゚)
  6. 罠 • Pythonの側はC-styleなサイズ – プラットフォームごとにi32などからの変換が必要 – http://docs.python.jp/2/library/stdtypes.html#int-float- long-complex • 今回はLinux/x86だったのでひっかかった

    • Linux(他)/x64, Windows/x86, x64はいけそう • 一応isizeの変換コードを外せばコンパイルできる – https://github.com/sunnyone/rust- cpython/tree/feature/linux-32