4 // (C) 2008 Mainsoft, Inc. (http://www.mainsoft.com)
5 // (C) 2008 db4objects, Inc. (http://www.db4o.com)
7 // Permission is hereby granted, free of charge, to any person obtaining
8 // a copy of this software and associated documentation files (the
9 // "Software"), to deal in the Software without restriction, including
10 // without limitation the rights to use, copy, modify, merge, publish,
11 // distribute, sublicense, and/or sell copies of the Software, and to
12 // permit persons to whom the Software is furnished to do so, subject to
13 // the following conditions:
15 // The above copyright notice and this permission notice shall be
16 // included in all copies or substantial portions of the Software.
18 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
22 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 using System
.Linq
.Expressions
;
30 using System
.Reflection
;
32 namespace System
.Linq
.jvm
{
36 class VoidTypeMarker
{
39 static readonly Type VoidMarker
= typeof (VoidTypeMarker
);
40 static readonly MethodInfo
[] delegates
= new MethodInfo
[5];
42 LambdaExpression lambda
;
46 var methods
= from method
in typeof (Interpreter
).GetMethods (
47 BindingFlags
.NonPublic
| BindingFlags
.Public
| BindingFlags
.Instance
)
48 where method
.Name
== "GetDelegate"
51 foreach (var method
in methods
)
52 delegates
[method
.GetGenericArguments ().Length
- 1] = method
;
55 public Interpreter (LambdaExpression lambda
)
60 public Delegate
CreateDelegate ()
62 var types
= GetGenericSignature ();
63 var creator
= delegates
[types
.Length
- 1].MakeGenericMethod (types
);
65 return (Delegate
) creator
.Invoke (this, new object [0]);
68 public void Validate ()
70 new ExpressionValidator (lambda
).Validate ();
73 Type
[] GetGenericSignature ()
75 var count
= lambda
.Parameters
.Count
;
76 var types
= new Type
[count
+ 1];
78 var return_type
= lambda
.GetReturnType ();
79 if (return_type
== typeof (void))
80 return_type
= VoidMarker
;
82 types
[count
] = return_type
;
83 for (int i
= 0; i
< count
; i
++) {
84 types
[i
] = lambda
.Parameters
[i
].Type
;
90 object Run (object [] arg
)
92 return ExpressionInterpreter
.Interpret (lambda
, arg
);
95 Delegate GetDelegate
<TResult
> ()
97 if (typeof (TResult
) == VoidMarker
)
98 return new Action (ActionRunner
);
100 return new Func
<TResult
> (FuncRunner
<TResult
>);
103 TResult FuncRunner
<TResult
> ()
105 return (TResult
) Run (new object [0]);
110 Run (new object [0]);
113 Delegate GetDelegate
<T
, TResult
> ()
115 if (typeof (TResult
) == VoidMarker
)
116 return new Action
<T
> (ActionRunner
<T
>);
118 return new Func
<T
, TResult
> (FuncRunner
<T
, TResult
>);
121 TResult FuncRunner
<T
, TResult
> (T arg
)
123 return (TResult
) Run (new object [] { arg }
);
126 void ActionRunner
<T
> (T arg
)
128 Run (new object [] { arg }
);
131 Delegate GetDelegate
<T1
, T2
, TResult
> ()
133 if (typeof (TResult
) == VoidMarker
)
134 return new Action
<T1
, T2
> (ActionRunner
<T1
, T2
>);
136 return new Func
<T1
, T2
, TResult
> (FuncRunner
<T1
, T2
, TResult
>);
139 TResult FuncRunner
<T1
, T2
, TResult
> (T1 arg1
, T2 arg2
)
141 return (TResult
) Run (new object [] { arg1, arg2 }
);
144 void ActionRunner
<T1
, T2
> (T1 arg1
, T2 arg2
)
146 Run (new object [] { arg1, arg2 }
);
149 Delegate GetDelegate
<T1
, T2
, T3
, TResult
> ()
151 if (typeof (TResult
) == VoidMarker
)
152 return new Action
<T1
, T2
, T3
> (ActionRunner
<T1
, T2
, T3
>);
154 return new Func
<T1
, T2
, T3
, TResult
> (FuncRunner
<T1
, T2
, T3
, TResult
>);
157 TResult FuncRunner
<T1
, T2
, T3
, TResult
> (T1 arg1
, T2 arg2
, T3 arg3
)
159 return (TResult
) Run (new object [] { arg1, arg2, arg3 }
);
162 void ActionRunner
<T1
, T2
, T3
> (T1 arg1
, T2 arg2
, T3 arg3
)
164 Run (new object [] { arg1, arg2, arg3 }
);
167 Delegate GetDelegate
<T1
, T2
, T3
, T4
, TResult
> ()
169 if (typeof (TResult
) == VoidMarker
)
170 return new Action
<T1
, T2
, T3
, T4
> (ActionRunner
<T1
, T2
, T3
, T4
>);
172 return new Func
<T1
, T2
, T3
, T4
, TResult
> (FuncRunner
<T1
, T2
, T3
, T4
, TResult
>);
175 TResult FuncRunner
<T1
, T2
, T3
, T4
, TResult
> (T1 arg1
, T2 arg2
, T3 arg3
, T4 arg4
)
177 return (TResult
) Run (new object [] { arg1, arg2, arg3, arg4 }
);
180 void ActionRunner
<T1
, T2
, T3
, T4
> (T1 arg1
, T2 arg2
, T3 arg3
, T4 arg4
)
182 Run (new object [] { arg1, arg2, arg3, arg4 }
);