【发布时间】:2015-01-28 03:12:27
【问题描述】:
我陷入了两个不同的问题/错误之中,无法想出一个体面的解决方案。任何帮助将不胜感激
上下文、FFI、调用大量 C 函数,以及将 C 类型包装在 rust 结构中。
第一个问题是ICE: this path should not cause illegal move。
这迫使我使用 & 引用进行所有结构包装,如下所示:
pub struct CassResult<'a> {
result:&'a cql_ffi::CassResult
}
而不是更简单,更可取的:
pub struct CassResult {
result:cql_ffi::CassResult
}
其他代码如:
pub fn first_row(&self) -> Result<CassRow,CassError> {unsafe{
Ok(CassRow{row:*cql_ffi::cass_result_first_row(self.result)})
}}
将导致:
error: internal compiler error: this path should not cause illegal move
Ok(CassRow{row:*cql_ffi::cass_result_first_row(self.result)})
^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
所以,我继续使用生命周期托管引用来包装所有内容,在我尝试实现迭代器之前,所有内容都不是很糟糕。在这一点上,我看不到this problem。
method next has an incompatible type for trait: expected concrete lifetime, found bound lifetime parameter
因此,鉴于这两个相互冲突的问题,我完全陷入困境,找不到任何方法来围绕 FFI 迭代器类构造实现适当的 rust 迭代器。
编辑:根据 Shep 的建议,我得到:
pub struct CassResult {
pub result:cql_ffi::CassResult
}
和
pub fn get_result(&mut future:future) -> Option<CassResult> {unsafe{
let result:&cql_ffi::CassResult = &*cql_ffi::cass_future_get_result(&mut future.future);
Some(CassResult{result:*result})
}}
然后得到:
error: cannot move out of borrowed content
Some(CassResult{result:*result}
有什么方法可以使这种模式起作用吗?它在整个 FFI 包装代码中重复出现。
【问题讨论】:
-
如果您提供了您想要工作的完整代码,对此发表评论会更容易。我怀疑 Stack Overflow 也不是解决这个问题的好地方;我建议你试试 Rust IRC 频道。
-
作为第一个错误的解决方法,您可能需要先查看参考。而不是
foo: T = unsafe { *ptr },试试foo: &mut T = unsafe { &mut *ptr }(为了清楚起见,添加了冗余类型注释)。 -
我想我遇到了这样的事情,在我的特殊情况下,我能够通过为该类型实现
Copy来解决它(这很有意义),我猜你会是CassResult. -
叮叮叮。考虑到我的困境,Shep 对此 ICE 的解决方法是(我相信)理想的答案。 FWIW,正在进行中的代码是github.com/tupshin/cql-ffi-safe
-
或不完全。添加了一个编辑。