@@ -3,7 +3,7 @@ use ffi::{core, target};
3
3
use ffi:: execution_engine as engine;
4
4
use ffi:: execution_engine:: * ;
5
5
use ffi:: target_machine:: LLVMCodeModel ;
6
- use cbox:: CBox ;
6
+ use cbox:: { CBox , CSemiBox , DisposeRef } ;
7
7
use std:: marker:: PhantomData ;
8
8
use std:: { mem, ptr} ;
9
9
use std:: ops:: * ;
@@ -17,36 +17,36 @@ use value::{Function, Value};
17
17
/// An abstract interface for implementation execution of LLVM modules.
18
18
///
19
19
/// This is designed to support both interpreter and just-in-time (JIT) compiler implementations.
20
- pub trait ExecutionEngine < ' a , ' b : ' a > : Sized + ' b where LLVMExecutionEngineRef : From < & ' b Self > {
20
+ pub trait ExecutionEngine < ' a > : ' a + Sized + DisposeRef where LLVMExecutionEngineRef : From < & ' a Self > {
21
21
/// The options given to the engine upon creation.
22
22
type Options : Copy ;
23
- /// Create a new execution engine with the given `Module` and options , or return a
23
+ /// Create a new execution engine with the given `Module` and optiions , or return a
24
24
/// description of the error.
25
- fn new ( module : & ' a Module , options : Self :: Options ) -> Result < Self , CBox < str > > ;
25
+ fn new ( module : & ' a Module , options : Self :: Options ) -> Result < CSemiBox < ' a , Self > , CBox < str > > ;
26
26
27
27
/// Add a module to the list of modules to interpret or compile.
28
- fn add_module ( & ' b self , module : & ' a Module ) {
28
+ fn add_module ( & ' a self , module : & ' a Module ) {
29
29
unsafe { engine:: LLVMAddModule ( self . into ( ) , ( & * module) . into ( ) ) }
30
30
}
31
31
/// Remove a module from the list of modules to interpret or compile.
32
- fn remove_module ( & ' b self , module : & ' a Module ) -> & ' a Module {
32
+ fn remove_module ( & ' a self , module : & ' a Module ) -> & ' a Module {
33
33
unsafe {
34
34
let mut out = mem:: uninitialized ( ) ;
35
35
engine:: LLVMRemoveModule ( self . into ( ) , module. into ( ) , & mut out, ptr:: null_mut ( ) ) ;
36
36
out. into ( )
37
37
}
38
38
}
39
39
/// Execute all of the static constructors for this program.
40
- fn run_static_constructors ( & ' b self ) {
40
+ fn run_static_constructors ( & ' a self ) {
41
41
unsafe { engine:: LLVMRunStaticConstructors ( self . into ( ) ) }
42
42
}
43
43
/// Execute all of the static destructors for this program.
44
- fn run_static_destructors ( & ' b self ) {
44
+ fn run_static_destructors ( & ' a self ) {
45
45
unsafe { engine:: LLVMRunStaticDestructors ( self . into ( ) ) }
46
46
}
47
47
/// Attempt to find a function with the name given, or `None` if there wasn't
48
48
/// a function with that name.
49
- fn find_function ( & ' b self , name : & str ) -> Option < & ' a Function > {
49
+ fn find_function ( & ' a self , name : & str ) -> Option < & ' a Function > {
50
50
util:: with_cstr ( name, |c_name| unsafe {
51
51
let mut out = mem:: zeroed ( ) ;
52
52
engine:: LLVMFindFunction ( self . into ( ) , c_name, & mut out) ;
@@ -60,22 +60,22 @@ pub trait ExecutionEngine<'a, 'b:'a>:Sized+'b where LLVMExecutionEngineRef:From<
60
60
///
61
61
/// To convert the arguments to `GenericValue`s, you should use the `GenericValueCast::to_generic` method.
62
62
/// To convert the return value from a `GenericValue`, you should use the `GenericValueCast::from_generic` method.
63
- fn run_function ( & ' b self , function : & ' a Function , args : & [ GenericValue < ' a > ] ) -> GenericValue < ' a > {
63
+ fn run_function ( & ' a self , function : & ' a Function , args : & [ GenericValue < ' a > ] ) -> GenericValue < ' a > {
64
64
let ptr = args. as_ptr ( ) as * mut LLVMGenericValueRef ;
65
65
unsafe { engine:: LLVMRunFunction ( self . into ( ) , function. into ( ) , args. len ( ) as c_uint , ptr) . into ( ) }
66
66
}
67
67
/// Returns a pointer to the global value given.
68
68
///
69
69
/// This is marked as unsafe because the type cannot be guranteed to be the same as the
70
70
/// type of the global value at this point.
71
- unsafe fn get_global < T > ( & ' b self , global : & ' a Value ) -> & ' b T {
71
+ unsafe fn get_global < T > ( & ' a self , global : & ' a Value ) -> & ' a T {
72
72
mem:: transmute ( engine:: LLVMGetPointerToGlobal ( self . into ( ) , global. into ( ) ) )
73
73
}
74
74
/// Returns a pointer to the global value with the name given.
75
75
///
76
76
/// This is marked as unsafe because the type cannot be guranteed to be the same as the
77
77
/// type of the global value at this point.
78
- unsafe fn find_global < T > ( & ' b self , name : & str ) -> Option < & ' b T > {
78
+ unsafe fn find_global < T > ( & ' a self , name : & str ) -> Option < & ' a T > {
79
79
util:: with_cstr ( name, |ptr|
80
80
mem:: transmute ( engine:: LLVMGetGlobalValueAddress ( self . into ( ) , ptr) )
81
81
)
@@ -91,17 +91,15 @@ pub struct JitOptions {
91
91
pub opt_level : usize
92
92
}
93
93
/// The MCJIT backend, which compiles functions and values into machine code.
94
- pub struct JitEngine < ' a > {
95
- engine : LLVMExecutionEngineRef ,
96
- marker : PhantomData < & ' a ( ) >
97
- }
98
- native_ref ! { contra JitEngine , engine: LLVMExecutionEngineRef }
99
- impl < ' a , ' b > JitEngine < ' a > {
94
+ pub struct JitEngine ( PhantomData < [ u8 ] > ) ;
95
+ native_ref ! { & JitEngine = LLVMExecutionEngineRef }
96
+ dispose ! { JitEngine , LLVMOpaqueExecutionEngine , LLVMDisposeExecutionEngine }
97
+ impl < ' a > JitEngine {
100
98
/// Run the closure `cb` with the machine code for the function `function`.
101
99
///
102
100
/// This will check that the types match at runtime when in debug mode, but not release mode.
103
101
/// You should make sure to use debug mode if you want it to error when the types don't match.
104
- pub fn with_function < C , A , R > ( & self , function : & ' b Function , cb : C ) where A : Compile < ' b > , R : Compile < ' b > , C : FnOnce ( extern fn ( A ) -> R ) {
102
+ pub fn with_function < C , A , R > ( & self , function : & ' a Function , cb : C ) where A : Compile < ' a > , R : Compile < ' a > , C : FnOnce ( extern "C" fn ( A ) -> R ) {
105
103
if cfg ! ( not( ndebug) ) {
106
104
let ctx = function. get_context ( ) ;
107
105
let sig = function. get_signature ( ) ;
@@ -118,21 +116,21 @@ impl<'a, 'b> JitEngine<'a> {
118
116
}
119
117
}
120
118
/// Run the closure `cb` with the machine code for the function `function`.
121
- pub unsafe fn with_function_unchecked < C , A , R > ( & self , function : & ' b Function , cb : C ) where A : Compile < ' b > , R : Compile < ' b > , C : FnOnce ( extern fn ( A ) -> R ) {
119
+ pub unsafe fn with_function_unchecked < C , A , R > ( & self , function : & ' a Function , cb : C ) where A : Compile < ' a > , R : Compile < ' a > , C : FnOnce ( extern fn ( A ) -> R ) {
122
120
cb ( self . get_function :: < A , R > ( function) ) ;
123
121
}
124
122
/// Returns a pointer to the machine code for the function `function`.
125
123
///
126
124
/// This is marked as unsafe because the types given as arguments and return could be different
127
125
/// from their internal representation.
128
- pub unsafe fn get_function < A , R > ( & self , function : & ' b Function ) -> extern fn ( A ) -> R {
126
+ pub unsafe fn get_function < A , R > ( & self , function : & ' a Function ) -> extern fn ( A ) -> R {
129
127
let ptr: & u8 = self . get_global ( function) ;
130
128
mem:: transmute ( ptr)
131
129
}
132
130
}
133
- impl < ' a , ' b : ' a > ExecutionEngine < ' a , ' b > for JitEngine < ' b > {
131
+ impl < ' a > ExecutionEngine < ' a > for JitEngine {
134
132
type Options = JitOptions ;
135
- fn new ( module : & ' a Module , options : JitOptions ) -> Result < JitEngine < ' b > , CBox < str > > {
133
+ fn new ( module : & ' a Module , options : JitOptions ) -> Result < CSemiBox < ' a , JitEngine > , CBox < str > > {
136
134
unsafe {
137
135
let mut ee = mem:: uninitialized ( ) ;
138
136
let mut out = mem:: zeroed ( ) ;
@@ -161,12 +159,10 @@ impl<'a, 'b:'a> ExecutionEngine<'a, 'b> for JitEngine<'b> {
161
159
}
162
160
}
163
161
/// The interpreter backend
164
- pub struct Interpreter < ' a > {
165
- engine : LLVMExecutionEngineRef ,
166
- marker : PhantomData < & ' a ( ) >
167
- }
168
- native_ref ! { contra Interpreter , engine: LLVMExecutionEngineRef }
169
- impl < ' a > Interpreter < ' a > {
162
+ pub struct Interpreter ( PhantomData < [ u8 ] > ) ;
163
+ native_ref ! { & Interpreter = LLVMExecutionEngineRef }
164
+ dispose ! { Interpreter , LLVMOpaqueExecutionEngine , LLVMDisposeExecutionEngine }
165
+ impl < ' a > Interpreter {
170
166
/// Run `function` with the arguments given as ``GenericValue`s, then return the result as one.
171
167
///
172
168
/// To convert the arguments to `GenericValue`s, you should use the `GenericValueCast::to_generic` method.
@@ -176,9 +172,9 @@ impl<'a> Interpreter<'a> {
176
172
unsafe { engine:: LLVMRunFunction ( self . into ( ) , function. into ( ) , args. len ( ) as c_uint , ptr) . into ( ) }
177
173
}
178
174
}
179
- impl < ' a , ' b : ' a > ExecutionEngine < ' a , ' b > for Interpreter < ' b > {
175
+ impl < ' a > ExecutionEngine < ' a > for Interpreter {
180
176
type Options = ( ) ;
181
- fn new ( module : & ' a Module , _: ( ) ) -> Result < Interpreter < ' b > , CBox < str > > {
177
+ fn new ( module : & ' a Module , _: ( ) ) -> Result < CSemiBox < ' a , Interpreter > , CBox < str > > {
182
178
unsafe {
183
179
let mut ee = mem:: uninitialized ( ) ;
184
180
let mut out = mem:: zeroed ( ) ;
0 commit comments