KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jruby > runtime > callback > DumpingInvocationCallbackFactory


1 /***** BEGIN LICENSE BLOCK *****
2  * Version: CPL 1.0/GPL 2.0/LGPL 2.1
3  *
4  * The contents of this file are subject to the Common Public
5  * License Version 1.0 (the "License"); you may not use this file
6  * except in compliance with the License. You may obtain a copy of
7  * the License at http://www.eclipse.org/legal/cpl-v10.html
8  *
9  * Software distributed under the License is distributed on an "AS
10  * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
11  * implied. See the License for the specific language governing
12  * rights and limitations under the License.
13  *
14  * Copyright (C) 2006 Ola Bini <ola@ologix.com>
15  *
16  * Alternatively, the contents of this file may be used under the terms of
17  * either of the GNU General Public License Version 2 or later (the "GPL"),
18  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
19  * in which case the provisions of the GPL or the LGPL are applicable instead
20  * of those above. If you wish to allow use of your version of this file only
21  * under the terms of either the GPL or the LGPL, and not to allow others to
22  * use your version of this file under the terms of the CPL, indicate your
23  * decision by deleting the provisions above and replace them with the notice
24  * and other provisions required by the GPL or the LGPL. If you do not delete
25  * the provisions above, a recipient may use your version of this file under
26  * the terms of any one of the CPL, the GPL or the LGPL.
27  ***** END LICENSE BLOCK *****/

28 package org.jruby.runtime.callback;
29
30 import java.io.File JavaDoc;
31 import java.io.FileOutputStream JavaDoc;
32
33 import org.jruby.Ruby;
34 import org.jruby.RubyKernel;
35 import org.objectweb.asm.ClassWriter;
36 import org.objectweb.asm.MethodVisitor;
37 import org.objectweb.asm.Opcodes;
38 import org.jruby.runtime.Arity;
39 import org.jruby.runtime.Block;
40 import org.jruby.runtime.CallbackFactory;
41 import org.jruby.runtime.CompiledBlockCallback;
42 import org.jruby.runtime.ThreadContext;
43 import org.jruby.runtime.builtin.IRubyObject;
44 import org.jruby.util.CodegenUtils;
45
46 public class DumpingInvocationCallbackFactory extends CallbackFactory implements Opcodes {
47     private final static CodegenUtils cg = CodegenUtils.instance;
48
49     private final Class JavaDoc type;
50     private final String JavaDoc typePath;
51     private final Ruby runtime;
52
53     private final static String JavaDoc SUPER_CLASS = cg.p(InvocationCallback.class);
54     private final static String JavaDoc FAST_SUPER_CLASS = cg.p(FastInvocationCallback.class);
55     private final static String JavaDoc BLOCK_ID = cg.ci(Block.class);
56     private final static String JavaDoc CALL_SIG = cg.sig(RubyKernel.IRUBY_OBJECT, cg.params(Object JavaDoc.class, Object JavaDoc[].class, Block.class));
57     private final static String JavaDoc FAST_CALL_SIG = cg.sig(RubyKernel.IRUBY_OBJECT, cg.params(Object JavaDoc.class, Object JavaDoc[].class));
58     private final static String JavaDoc BLOCK_CALL_SIG = cg.sig(RubyKernel.IRUBY_OBJECT, cg.params(ThreadContext.class, RubyKernel.IRUBY_OBJECT, IRubyObject[].class, Block.class, IRubyObject[][].class));
59     private final static String JavaDoc IRUB = cg.p(RubyKernel.IRUBY_OBJECT);
60     private final static String JavaDoc IRUB_ID = cg.ci(RubyKernel.IRUBY_OBJECT);
61
62     private String JavaDoc dumpPath;
63     
64     public DumpingInvocationCallbackFactory(Ruby runtime, Class JavaDoc type, String JavaDoc path) {
65         this.type = type;
66         this.typePath = cg.p(type);
67         this.runtime = runtime;
68         this.dumpPath = path;
69     }
70
71     private String JavaDoc getReturnName(String JavaDoc method, Class JavaDoc[] args) throws Exception JavaDoc {
72         String JavaDoc t = type.getMethod(method,args).getReturnType().getName().replace('.','/');
73         if("void".equalsIgnoreCase(t)) {
74             throw new IllegalArgumentException JavaDoc("Method " + method + " has a void return type. This is not allowed in JRuby.");
75         }
76         return t;
77     }
78
79     private ClassWriter createCtor(String JavaDoc namePath) throws Exception JavaDoc {
80         ClassWriter cw = new ClassWriter(true);
81         cw.visit(V1_4, ACC_PUBLIC + ACC_SUPER, namePath, null, SUPER_CLASS, null);
82         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
83         mv.visitCode();
84         mv.visitVarInsn(ALOAD, 0);
85         mv.visitMethodInsn(INVOKESPECIAL, SUPER_CLASS, "<init>", "()V");
86         mv.visitInsn(RETURN);
87         mv.visitMaxs(1, 1);
88         mv.visitEnd();
89         return cw;
90     }
91
92     private ClassWriter createCtorFast(String JavaDoc namePath) throws Exception JavaDoc {
93         ClassWriter cw = new ClassWriter(true);
94         cw.visit(V1_4, ACC_PUBLIC + ACC_SUPER, namePath, null, FAST_SUPER_CLASS, null);
95         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
96         mv.visitCode();
97         mv.visitVarInsn(ALOAD, 0);
98         mv.visitMethodInsn(INVOKESPECIAL, FAST_SUPER_CLASS, "<init>", "()V");
99         mv.visitInsn(RETURN);
100         mv.visitMaxs(1, 1);
101         mv.visitEnd();
102         return cw;
103     }
104
105     private ClassWriter createBlockCtor(String JavaDoc namePath) throws Exception JavaDoc {
106         ClassWriter cw = new ClassWriter(true);
107         cw.visit(V1_4, ACC_PUBLIC + ACC_SUPER, namePath, null, cg.p(Object JavaDoc.class), new String JavaDoc[] { cg.p(CompiledBlockCallback.class) });
108         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
109         mv.visitCode();
110         mv.visitVarInsn(ALOAD, 0);
111         mv.visitMethodInsn(INVOKESPECIAL, cg.p(Object JavaDoc.class), "<init>", "()V");
112         mv.visitInsn(RETURN);
113         mv.visitMaxs(1, 1);
114         mv.visitEnd();
115         return cw;
116     }
117
118     private Class JavaDoc tryClass(String JavaDoc name) {
119         try {
120             return Class.forName(name,true,runtime.getJRubyClassLoader());
121         } catch(Exception JavaDoc e) {
122             return null;
123         }
124     }
125
126     private MethodVisitor startCall(ClassWriter cw) {
127         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "call", CALL_SIG, null, null);;
128         mv.visitCode();
129         mv.visitVarInsn(ALOAD, 1);
130         mv.visitTypeInsn(CHECKCAST, typePath);
131         return mv;
132     }
133
134     private MethodVisitor startCallS(ClassWriter cw) {
135         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "call", CALL_SIG, null, null);;
136         mv.visitCode();
137         mv.visitVarInsn(ALOAD, 1);
138         mv.visitTypeInsn(CHECKCAST, IRUB);
139         return mv;
140     }
141
142     private MethodVisitor startCallFast(ClassWriter cw) {
143         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "call", FAST_CALL_SIG, null, null);;
144         mv.visitCode();
145         mv.visitVarInsn(ALOAD, 1);
146         mv.visitTypeInsn(CHECKCAST, typePath);
147         return mv;
148     }
149
150     private MethodVisitor startCallSFast(ClassWriter cw) {
151         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "call", FAST_CALL_SIG, null, null);;
152         mv.visitCode();
153         mv.visitVarInsn(ALOAD, 1);
154         mv.visitTypeInsn(CHECKCAST, IRUB);
155         return mv;
156     }
157
158     private MethodVisitor startBlockCall(ClassWriter cw) {
159         MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "call", BLOCK_CALL_SIG, null, null);;
160         mv.visitCode();
161         return mv;
162     }
163
164     private Class JavaDoc endCall(ClassWriter cw, MethodVisitor mv, String JavaDoc name) {
165         mv.visitEnd();
166         cw.visitEnd();
167         byte[] code = cw.toByteArray();
168         String JavaDoc cname = name.replace('.','/');
169         File JavaDoc f = new File JavaDoc(dumpPath,cname+".class");
170         f.getParentFile().mkdirs();
171         try {
172             FileOutputStream JavaDoc fos = new FileOutputStream JavaDoc(f);
173             fos.write(code);
174             fos.close();
175         } catch(Exception JavaDoc e) {
176         }
177         return runtime.getJRubyClassLoader().defineClass(name, code);
178     }
179
180     public Callback getMethod(String JavaDoc method) {
181         String JavaDoc mname = type.getName() + "Invoker" + method + "0";
182         String JavaDoc mnamePath = typePath + "Invoker" + method + "0";
183         Class JavaDoc c = tryClass(mname);
184         try {
185             if(c == null) {
186                 String JavaDoc ret = getReturnName(method, new Class JavaDoc[]{Block.class});
187                 ClassWriter cw = createCtor(mnamePath);
188                 MethodVisitor mv = startCall(cw);
189                 mv.visitVarInsn(ALOAD, 3);
190                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "(" + BLOCK_ID + ")L" + ret + ";");
191                 mv.visitInsn(ARETURN);
192                 mv.visitMaxs(1, 3);
193                 c = endCall(cw,mv,mname);
194             }
195             InvocationCallback ic = (InvocationCallback)c.newInstance();
196             ic.setArity(Arity.noArguments());
197             return ic;
198         } catch(IllegalArgumentException JavaDoc e) {
199             throw e;
200         } catch(Exception JavaDoc e) {
201             throw new IllegalArgumentException JavaDoc(e.getMessage());
202         }
203     }
204
205     public Callback getMethod(String JavaDoc method, Class JavaDoc arg1) {
206         String JavaDoc mname = type.getName() + "Invoker" + method + "1";
207         String JavaDoc mnamePath = typePath + "Invoker" + method + "1";
208         Class JavaDoc c = tryClass(mname);
209         try {
210             if(c == null) {
211                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1,Block.class});
212                 ClassWriter cw = createCtor(mnamePath);
213                 MethodVisitor mv = startCall(cw);
214                 mv.visitVarInsn(ALOAD, 2);
215                 mv.visitInsn(ICONST_0);
216                 mv.visitInsn(AALOAD);
217                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
218                 mv.visitVarInsn(ALOAD, 3);
219                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+BLOCK_ID+")L"+ret+";");
220                 mv.visitInsn(ARETURN);
221                 mv.visitMaxs(3, 3);
222                 c = endCall(cw,mv,mname);
223             }
224             InvocationCallback ic = (InvocationCallback)c.newInstance();
225             ic.setArity(Arity.singleArgument());
226             return ic;
227         } catch(IllegalArgumentException JavaDoc e) {
228             throw e;
229         } catch(Exception JavaDoc e) {
230             throw new IllegalArgumentException JavaDoc(e.getMessage());
231         }
232     }
233
234     public Callback getMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2) {
235         String JavaDoc mname = type.getName() + "Invoker" + method + "2";
236         String JavaDoc mnamePath = typePath + "Invoker" + method + "2";
237         Class JavaDoc c = tryClass(mname);
238         try {
239             if(c == null) {
240                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1,arg2,Block.class});
241                 ClassWriter cw = createCtor(mnamePath);
242                 MethodVisitor mv = startCall(cw);
243                 mv.visitVarInsn(ALOAD, 2);
244                 mv.visitInsn(ICONST_0);
245                 mv.visitInsn(AALOAD);
246                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
247                 mv.visitVarInsn(ALOAD, 2);
248                 mv.visitInsn(ICONST_1);
249                 mv.visitInsn(AALOAD);
250                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
251                 mv.visitVarInsn(ALOAD, 3);
252                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+cg.ci(arg2)+BLOCK_ID+")L"+ret+";");
253                 mv.visitInsn(ARETURN);
254                 mv.visitMaxs(4, 3);
255                 c = endCall(cw,mv,mname);
256             }
257             InvocationCallback ic = (InvocationCallback)c.newInstance();
258             ic.setArity(Arity.twoArguments());
259             return ic;
260         } catch(IllegalArgumentException JavaDoc e) {
261             throw e;
262         } catch(Exception JavaDoc e) {
263             throw new IllegalArgumentException JavaDoc(e.getMessage());
264         }
265     }
266     
267     public Callback getMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2, Class JavaDoc arg3) {
268         String JavaDoc mname = type.getName() + "Invoker" + method + "3";
269         String JavaDoc mnamePath = typePath + "Invoker" + method + "3";
270         Class JavaDoc c = tryClass(mname);
271         try {
272             if(c == null) {
273                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1,arg2,arg3,Block.class});
274                 ClassWriter cw = createCtor(mnamePath);
275                 MethodVisitor mv = startCall(cw);
276                 mv.visitVarInsn(ALOAD, 2);
277                 mv.visitInsn(ICONST_0);
278                 mv.visitInsn(AALOAD);
279                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
280                 mv.visitVarInsn(ALOAD, 2);
281                 mv.visitInsn(ICONST_1);
282                 mv.visitInsn(AALOAD);
283                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
284                 mv.visitVarInsn(ALOAD, 2);
285                 mv.visitInsn(ICONST_2);
286                 mv.visitInsn(AALOAD);
287                 mv.visitTypeInsn(CHECKCAST, cg.p(arg3));
288                 mv.visitVarInsn(ALOAD, 3);
289                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+cg.ci(arg2)+cg.ci(arg3)+BLOCK_ID+")L"+ret+";");
290                 mv.visitInsn(ARETURN);
291                 mv.visitMaxs(5, 3);
292                 c = endCall(cw,mv,mname);
293             }
294             InvocationCallback ic = (InvocationCallback)c.newInstance();
295             ic.setArity(Arity.fixed(3));
296             return ic;
297         } catch(IllegalArgumentException JavaDoc e) {
298             throw e;
299         } catch(Exception JavaDoc e) {
300             throw new IllegalArgumentException JavaDoc(e.getMessage());
301         }
302     }
303
304     public Callback getSingletonMethod(String JavaDoc method) {
305         String JavaDoc mname = type.getName() + "InvokerS" + method + "0";
306         String JavaDoc mnamePath = typePath + "InvokerS" + method + "0";
307         Class JavaDoc c = tryClass(mname);
308         try {
309             if(c == null) {
310                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,Block.class});
311                 ClassWriter cw = createCtor(mnamePath);
312                 MethodVisitor mv = startCallS(cw);
313                 mv.visitVarInsn(ALOAD, 3);
314                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + BLOCK_ID + ")L" + ret +";");
315                 mv.visitInsn(ARETURN);
316                 mv.visitMaxs(1, 3);
317                 c = endCall(cw,mv,mname);
318             }
319             InvocationCallback ic = (InvocationCallback)c.newInstance();
320             ic.setArity(Arity.noArguments());
321             return ic;
322         } catch(IllegalArgumentException JavaDoc e) {
323             throw e;
324         } catch(Exception JavaDoc e) {
325             throw new IllegalArgumentException JavaDoc(e.getMessage());
326         }
327     }
328
329     public Callback getSingletonMethod(String JavaDoc method, Class JavaDoc arg1) {
330         String JavaDoc mname = type.getName() + "InvokerS" + method + "1";
331         String JavaDoc mnamePath = typePath + "InvokerS" + method + "1";
332         Class JavaDoc c = tryClass(mname);
333         try {
334             if(c == null) {
335                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1,Block.class});
336                 ClassWriter cw = createCtor(mnamePath);
337                 MethodVisitor mv = startCallS(cw);
338                 mv.visitVarInsn(ALOAD, 2);
339                 mv.visitInsn(ICONST_0);
340                 mv.visitInsn(AALOAD);
341                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
342                 mv.visitVarInsn(ALOAD, 3);
343                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + BLOCK_ID + ")L" + ret + ";");
344                 mv.visitInsn(ARETURN);
345                 mv.visitMaxs(3, 3);
346                 c = endCall(cw,mv,mname);
347             }
348             InvocationCallback ic = (InvocationCallback)c.newInstance();
349             ic.setArity(Arity.singleArgument());
350             return ic;
351         } catch(IllegalArgumentException JavaDoc e) {
352             throw e;
353         } catch(Exception JavaDoc e) {
354             throw new IllegalArgumentException JavaDoc(e.getMessage());
355         }
356     }
357
358     public Callback getSingletonMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2) {
359         String JavaDoc mname = type.getName() + "InvokerS" + method + "2";
360         String JavaDoc mnamePath = typePath + "InvokerS" + method + "2";
361         Class JavaDoc c = tryClass(mname);
362         try {
363             if(c == null) {
364                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1,arg2,Block.class});
365                 ClassWriter cw = createCtor(mnamePath);
366                 MethodVisitor mv = startCallS(cw);
367                 mv.visitVarInsn(ALOAD, 2);
368                 mv.visitInsn(ICONST_0);
369                 mv.visitInsn(AALOAD);
370                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
371                 mv.visitVarInsn(ALOAD, 2);
372                 mv.visitInsn(ICONST_1);
373                 mv.visitInsn(AALOAD);
374                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
375                 mv.visitVarInsn(ALOAD, 3);
376                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + cg.ci(arg2) + BLOCK_ID + ")L" + ret + ";");
377                 mv.visitInsn(ARETURN);
378                 mv.visitMaxs(4, 4);
379                 c = endCall(cw,mv,mname);
380             }
381             InvocationCallback ic = (InvocationCallback)c.newInstance();
382             ic.setArity(Arity.twoArguments());
383             return ic;
384         } catch(IllegalArgumentException JavaDoc e) {
385             throw e;
386         } catch(Exception JavaDoc e) {
387             throw new IllegalArgumentException JavaDoc(e.getMessage());
388         }
389     }
390
391     public Callback getSingletonMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2, Class JavaDoc arg3) {
392         String JavaDoc mname = type.getName() + "InvokerS" + method + "3";
393         String JavaDoc mnamePath = typePath + "InvokerS" + method + "3";
394         Class JavaDoc c = tryClass(mname);
395         try {
396             if(c == null) {
397                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1,arg2,arg3,Block.class});
398                 ClassWriter cw = createCtor(mnamePath);
399                 MethodVisitor mv = startCallS(cw);
400                 mv.visitVarInsn(ALOAD, 2);
401                 mv.visitInsn(ICONST_0);
402                 mv.visitInsn(AALOAD);
403                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
404                 mv.visitVarInsn(ALOAD, 2);
405                 mv.visitInsn(ICONST_1);
406                 mv.visitInsn(AALOAD);
407                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
408                 mv.visitVarInsn(ALOAD, 2);
409                 mv.visitInsn(ICONST_2);
410                 mv.visitInsn(AALOAD);
411                 mv.visitTypeInsn(CHECKCAST, cg.p(arg3));
412                 mv.visitVarInsn(ALOAD, 3);
413                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + cg.ci(arg2) + cg.ci(arg3) + BLOCK_ID + ")L" + ret + ";");
414                 mv.visitInsn(ARETURN);
415                 mv.visitMaxs(5, 3);
416                 c = endCall(cw,mv,mname);
417             }
418             InvocationCallback ic = (InvocationCallback)c.newInstance();
419             ic.setArity(Arity.fixed(3));
420             return ic;
421         } catch(IllegalArgumentException JavaDoc e) {
422             throw e;
423         } catch(Exception JavaDoc e) {
424             throw new IllegalArgumentException JavaDoc(e.getMessage());
425         }
426     }
427
428     public Callback getBlockMethod(String JavaDoc method) {
429         // TODO: This is probably BAD...
430
return new ReflectionCallback(
431             type,
432             method,
433             new Class JavaDoc[] { RubyKernel.IRUBY_OBJECT, RubyKernel.IRUBY_OBJECT },
434             false,
435             true,
436             Arity.fixed(2), false);
437     }
438     
439     public CompiledBlockCallback getBlockCallback(String JavaDoc method) {
440         String JavaDoc mname = type.getName() + "Block" + method + "xx1";
441         String JavaDoc mnamePath = typePath + "Block" + method + "xx1";
442         Class JavaDoc c = tryClass(mname);
443         try {
444             if(c == null) {
445                 ClassWriter cw = createBlockCtor(mnamePath);
446                 MethodVisitor mv = startBlockCall(cw);
447                 mv.visitVarInsn(ALOAD, 1);
448                 mv.visitVarInsn(ALOAD, 2);
449                 mv.visitVarInsn(ALOAD, 3);
450                 mv.visitVarInsn(ALOAD, 4);
451                 mv.visitVarInsn(ALOAD, 5);
452                 mv.visitMethodInsn(INVOKESTATIC, typePath, method,
453                         cg.sig(RubyKernel.IRUBY_OBJECT, cg.params(ThreadContext.class, RubyKernel.IRUBY_OBJECT, IRubyObject[].class, Block.class, IRubyObject[][].class)));
454                 mv.visitInsn(ARETURN);
455                 mv.visitMaxs(2, 3);
456                 c = endCall(cw,mv,mname);
457             }
458             CompiledBlockCallback ic = (CompiledBlockCallback)c.newInstance();
459             return ic;
460         } catch(IllegalArgumentException JavaDoc e) {
461             throw e;
462         } catch(Exception JavaDoc e) {
463             throw new IllegalArgumentException JavaDoc(e.getMessage());
464         }
465     }
466
467     public Callback getOptSingletonMethod(String JavaDoc method) {
468         String JavaDoc mname = type.getName() + "InvokerS" + method + "xx1";
469         String JavaDoc mnamePath = typePath + "InvokerS" + method + "xx1";
470         Class JavaDoc c = tryClass(mname);
471         try {
472             if(c == null) {
473                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,IRubyObject[].class,Block.class});
474                 ClassWriter cw = createCtor(mnamePath);
475                 MethodVisitor mv = startCallS(cw);
476                 mv.visitVarInsn(ALOAD, 2);
477                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
478                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
479                 mv.visitVarInsn(ALOAD, 3);
480                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + "[" + IRUB_ID + BLOCK_ID + ")L"+ret+";");
481                 mv.visitInsn(ARETURN);
482                 mv.visitMaxs(2, 3);
483                 c = endCall(cw,mv,mname);
484             }
485             InvocationCallback ic = (InvocationCallback)c.newInstance();
486             ic.setArity(Arity.optional());
487             return ic;
488         } catch(IllegalArgumentException JavaDoc e) {
489             throw e;
490         } catch(Exception JavaDoc e) {
491             throw new IllegalArgumentException JavaDoc(e.getMessage());
492         }
493     }
494
495     public Callback getOptMethod(String JavaDoc method) {
496         String JavaDoc mname = type.getName() + "Invoker" + method + "xx1";
497         String JavaDoc mnamePath = typePath + "Invoker" + method + "xx1";
498         Class JavaDoc c = tryClass(mname);
499         try {
500             if(c == null) {
501                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{IRubyObject[].class, Block.class});
502                 ClassWriter cw = createCtor(mnamePath);
503                 MethodVisitor mv = startCall(cw);
504                 mv.visitVarInsn(ALOAD, 2);
505                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
506                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
507                 mv.visitVarInsn(ALOAD, 3);
508                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "([" + IRUB_ID + BLOCK_ID + ")L" + ret + ";");
509                 mv.visitInsn(ARETURN);
510                 mv.visitMaxs(2, 3);
511                 c = endCall(cw,mv,mname);
512             }
513             InvocationCallback ic = (InvocationCallback)c.newInstance();
514             ic.setArity(Arity.optional());
515             return ic;
516         } catch(IllegalArgumentException JavaDoc e) {
517             throw e;
518         } catch(Exception JavaDoc e) {
519             throw new IllegalArgumentException JavaDoc(e.getMessage());
520         }
521     }
522
523     public Callback getFastMethod(String JavaDoc method) {
524         String JavaDoc mname = type.getName() + "Invoker" + method + "0";
525         String JavaDoc mnamePath = typePath + "Invoker" + method + "0";
526         Class JavaDoc c = tryClass(mname);
527         try {
528             if(c == null) {
529                 String JavaDoc ret = getReturnName(method, null);
530                 ClassWriter cw = createCtorFast(mnamePath);
531                 MethodVisitor mv = startCallFast(cw);
532                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "()L" + ret + ";");
533                 mv.visitInsn(ARETURN);
534                 mv.visitMaxs(1, 3);
535                 c = endCall(cw,mv,mname);
536             }
537             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
538             ic.setArity(Arity.noArguments());
539             return ic;
540         } catch(IllegalArgumentException JavaDoc e) {
541             throw e;
542         } catch(Exception JavaDoc e) {
543             throw new IllegalArgumentException JavaDoc(e.getMessage());
544         }
545     }
546
547     public Callback getFastMethod(String JavaDoc method, Class JavaDoc arg1) {
548         String JavaDoc mname = type.getName() + "Invoker" + method + "1";
549         String JavaDoc mnamePath = typePath + "Invoker" + method + "1";
550         Class JavaDoc c = tryClass(mname);
551         try {
552             if(c == null) {
553                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1});
554                 ClassWriter cw = createCtorFast(mnamePath);
555                 MethodVisitor mv = startCallFast(cw);
556                 mv.visitVarInsn(ALOAD, 2);
557                 mv.visitInsn(ICONST_0);
558                 mv.visitInsn(AALOAD);
559                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
560                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+")L"+ret+";");
561                 mv.visitInsn(ARETURN);
562                 mv.visitMaxs(3, 3);
563                 c = endCall(cw,mv,mname);
564             }
565             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
566             ic.setArity(Arity.singleArgument());
567             return ic;
568         } catch(IllegalArgumentException JavaDoc e) {
569             throw e;
570         } catch(Exception JavaDoc e) {
571             throw new IllegalArgumentException JavaDoc(e.getMessage());
572         }
573     }
574
575     public Callback getFastMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2) {
576         String JavaDoc mname = type.getName() + "Invoker" + method + "2";
577         String JavaDoc mnamePath = typePath + "Invoker" + method + "2";
578         Class JavaDoc c = tryClass(mname);
579         try {
580             if(c == null) {
581                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1,arg2});
582                 ClassWriter cw = createCtorFast(mnamePath);
583                 MethodVisitor mv = startCallFast(cw);
584                 mv.visitVarInsn(ALOAD, 2);
585                 mv.visitInsn(ICONST_0);
586                 mv.visitInsn(AALOAD);
587                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
588                 mv.visitVarInsn(ALOAD, 2);
589                 mv.visitInsn(ICONST_1);
590                 mv.visitInsn(AALOAD);
591                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
592                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+cg.ci(arg2)+")L"+ret+";");
593                 mv.visitInsn(ARETURN);
594                 mv.visitMaxs(4, 3);
595                 c = endCall(cw,mv,mname);
596             }
597             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
598             ic.setArity(Arity.twoArguments());
599             return ic;
600         } catch(IllegalArgumentException JavaDoc e) {
601             throw e;
602         } catch(Exception JavaDoc e) {
603             throw new IllegalArgumentException JavaDoc(e.getMessage());
604         }
605     }
606
607     public Callback getFastMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2, Class JavaDoc arg3) {
608         String JavaDoc mname = type.getName() + "Invoker" + method + "3";
609         String JavaDoc mnamePath = typePath + "Invoker" + method + "3";
610         Class JavaDoc c = tryClass(mname);
611         try {
612             if(c == null) {
613                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{arg1,arg2,arg3});
614                 ClassWriter cw = createCtorFast(mnamePath);
615                 MethodVisitor mv = startCallFast(cw);
616                 mv.visitVarInsn(ALOAD, 2);
617                 mv.visitInsn(ICONST_0);
618                 mv.visitInsn(AALOAD);
619                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
620                 mv.visitVarInsn(ALOAD, 2);
621                 mv.visitInsn(ICONST_1);
622                 mv.visitInsn(AALOAD);
623                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
624                 mv.visitVarInsn(ALOAD, 2);
625                 mv.visitInsn(ICONST_2);
626                 mv.visitInsn(AALOAD);
627                 mv.visitTypeInsn(CHECKCAST, cg.p(arg3));
628                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "("+cg.ci(arg1)+cg.ci(arg2)+cg.ci(arg3)+")L"+ret+";");
629                 mv.visitInsn(ARETURN);
630                 mv.visitMaxs(5, 3);
631                 c = endCall(cw,mv,mname);
632             }
633             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
634             ic.setArity(Arity.fixed(3));
635             return ic;
636         } catch(IllegalArgumentException JavaDoc e) {
637             throw e;
638         } catch(Exception JavaDoc e) {
639             throw new IllegalArgumentException JavaDoc(e.getMessage());
640         }
641     }
642
643     public Callback getFastSingletonMethod(String JavaDoc method) {
644         String JavaDoc mname = type.getName() + "InvokerS" + method + "0";
645         String JavaDoc mnamePath = typePath + "InvokerS" + method + "0";
646         Class JavaDoc c = tryClass(mname);
647         try {
648             if(c == null) {
649                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT});
650                 ClassWriter cw = createCtorFast(mnamePath);
651                 MethodVisitor mv = startCallSFast(cw);
652                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + ")L" + ret +";");
653                 mv.visitInsn(ARETURN);
654                 mv.visitMaxs(1, 3);
655                 c = endCall(cw,mv,mname);
656             }
657             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
658             ic.setArity(Arity.noArguments());
659             return ic;
660         } catch(IllegalArgumentException JavaDoc e) {
661             throw e;
662         } catch(Exception JavaDoc e) {
663             throw new IllegalArgumentException JavaDoc(e.getMessage());
664         }
665     }
666
667     public Callback getFastSingletonMethod(String JavaDoc method, Class JavaDoc arg1) {
668         String JavaDoc mname = type.getName() + "InvokerS" + method + "1";
669         String JavaDoc mnamePath = typePath + "InvokerS" + method + "1";
670         Class JavaDoc c = tryClass(mname);
671         try {
672             if(c == null) {
673                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1});
674                 ClassWriter cw = createCtorFast(mnamePath);
675                 MethodVisitor mv = startCallSFast(cw);
676                 mv.visitVarInsn(ALOAD, 2);
677                 mv.visitInsn(ICONST_0);
678                 mv.visitInsn(AALOAD);
679                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
680                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + ")L" + ret + ";");
681                 mv.visitInsn(ARETURN);
682                 mv.visitMaxs(3, 3);
683                 c = endCall(cw,mv,mname);
684             }
685             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
686             ic.setArity(Arity.singleArgument());
687             return ic;
688         } catch(IllegalArgumentException JavaDoc e) {
689             throw e;
690         } catch(Exception JavaDoc e) {
691             throw new IllegalArgumentException JavaDoc(e.getMessage());
692         }
693     }
694
695     public Callback getFastSingletonMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2) {
696         String JavaDoc mname = type.getName() + "InvokerS" + method + "2";
697         String JavaDoc mnamePath = typePath + "InvokerS" + method + "2";
698         Class JavaDoc c = tryClass(mname);
699         try {
700             if(c == null) {
701                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1,arg2});
702                 ClassWriter cw = createCtorFast(mnamePath);
703                 MethodVisitor mv = startCallSFast(cw);
704                 mv.visitVarInsn(ALOAD, 2);
705                 mv.visitInsn(ICONST_0);
706                 mv.visitInsn(AALOAD);
707                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
708                 mv.visitVarInsn(ALOAD, 2);
709                 mv.visitInsn(ICONST_1);
710                 mv.visitInsn(AALOAD);
711                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
712                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + cg.ci(arg2) + ")L" + ret + ";");
713                 mv.visitInsn(ARETURN);
714                 mv.visitMaxs(4, 4);
715                 c = endCall(cw,mv,mname);
716             }
717             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
718             ic.setArity(Arity.twoArguments());
719             return ic;
720         } catch(IllegalArgumentException JavaDoc e) {
721             throw e;
722         } catch(Exception JavaDoc e) {
723             throw new IllegalArgumentException JavaDoc(e.getMessage());
724         }
725     }
726
727     public Callback getFastSingletonMethod(String JavaDoc method, Class JavaDoc arg1, Class JavaDoc arg2, Class JavaDoc arg3) {
728         String JavaDoc mname = type.getName() + "InvokerS" + method + "3";
729         String JavaDoc mnamePath = typePath + "InvokerS" + method + "3";
730         Class JavaDoc c = tryClass(mname);
731         try {
732             if(c == null) {
733                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,arg1,arg2,arg3});
734                 ClassWriter cw = createCtorFast(mnamePath);
735                 MethodVisitor mv = startCallSFast(cw);
736                 mv.visitVarInsn(ALOAD, 2);
737                 mv.visitInsn(ICONST_0);
738                 mv.visitInsn(AALOAD);
739                 mv.visitTypeInsn(CHECKCAST, cg.p(arg1));
740                 mv.visitVarInsn(ALOAD, 2);
741                 mv.visitInsn(ICONST_1);
742                 mv.visitInsn(AALOAD);
743                 mv.visitTypeInsn(CHECKCAST, cg.p(arg2));
744                 mv.visitVarInsn(ALOAD, 2);
745                 mv.visitInsn(ICONST_2);
746                 mv.visitInsn(AALOAD);
747                 mv.visitTypeInsn(CHECKCAST, cg.p(arg3));
748                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + cg.ci(arg1) + cg.ci(arg2) + cg.ci(arg3) + ")L" + ret + ";");
749                 mv.visitInsn(ARETURN);
750                 mv.visitMaxs(5, 3);
751                 c = endCall(cw,mv,mname);
752             }
753             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
754             ic.setArity(Arity.fixed(3));
755             return ic;
756         } catch(IllegalArgumentException JavaDoc e) {
757             throw e;
758         } catch(Exception JavaDoc e) {
759             throw new IllegalArgumentException JavaDoc(e.getMessage());
760         }
761     }
762
763     public Callback getFastOptMethod(String JavaDoc method) {
764         String JavaDoc mname = type.getName() + "Invoker" + method + "xx1";
765         String JavaDoc mnamePath = typePath + "Invoker" + method + "xx1";
766         Class JavaDoc c = tryClass(mname);
767         try {
768             if(c == null) {
769                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{IRubyObject[].class});
770                 ClassWriter cw = createCtorFast(mnamePath);
771                 MethodVisitor mv = startCallFast(cw);
772                 mv.visitVarInsn(ALOAD, 2);
773                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
774                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
775                 mv.visitMethodInsn(INVOKEVIRTUAL, typePath, method, "([" + IRUB_ID + ")L" + ret + ";");
776                 mv.visitInsn(ARETURN);
777                 mv.visitMaxs(2, 3);
778                 c = endCall(cw,mv,mname);
779             }
780             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
781             ic.setArity(Arity.optional());
782             return ic;
783         } catch(IllegalArgumentException JavaDoc e) {
784             throw e;
785         } catch(Exception JavaDoc e) {
786             throw new IllegalArgumentException JavaDoc(e.getMessage());
787         }
788     }
789
790     public Callback getFastOptSingletonMethod(String JavaDoc method) {
791         String JavaDoc mname = type.getName() + "InvokerS" + method + "xx1";
792         String JavaDoc mnamePath = typePath + "InvokerS" + method + "xx1";
793         Class JavaDoc c = tryClass(mname);
794         try {
795             if(c == null) {
796                 String JavaDoc ret = getReturnName(method,new Class JavaDoc[]{RubyKernel.IRUBY_OBJECT,IRubyObject[].class});
797                 ClassWriter cw = createCtorFast(mnamePath);
798                 MethodVisitor mv = startCallSFast(cw);
799                 mv.visitVarInsn(ALOAD, 2);
800                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
801                 mv.visitTypeInsn(CHECKCAST, "[" + IRUB_ID);
802                 mv.visitMethodInsn(INVOKESTATIC, typePath, method, "(" + IRUB_ID + "[" + IRUB_ID + ")L"+ret+";");
803                 mv.visitInsn(ARETURN);
804                 mv.visitMaxs(2, 3);
805                 c = endCall(cw,mv,mname);
806             }
807             FastInvocationCallback ic = (FastInvocationCallback)c.newInstance();
808             ic.setArity(Arity.optional());
809             return ic;
810         } catch(IllegalArgumentException JavaDoc e) {
811             throw e;
812         } catch(Exception JavaDoc e) {
813             throw new IllegalArgumentException JavaDoc(e.getMessage());
814         }
815     }
816 } //DumpingInvocationCallbackFactory
817
Popular Tags