Source Code Cross Referenced for JavaAdapter.java in  » Scripting » rhino » org » mozilla » javascript » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Scripting » rhino » org.mozilla.javascript 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /* -*- Mode: java; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
0002:         *
0003:         * ***** BEGIN LICENSE BLOCK *****
0004:         * Version: MPL 1.1/GPL 2.0
0005:         *
0006:         * The contents of this file are subject to the Mozilla Public License Version
0007:         * 1.1 (the "License"); you may not use this file except in compliance with
0008:         * the License. You may obtain a copy of the License at
0009:         * http://www.mozilla.org/MPL/
0010:         *
0011:         * Software distributed under the License is distributed on an "AS IS" basis,
0012:         * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
0013:         * for the specific language governing rights and limitations under the
0014:         * License.
0015:         *
0016:         * The Original Code is Rhino code, released
0017:         * May 6, 1999.
0018:         *
0019:         * The Initial Developer of the Original Code is
0020:         * Netscape Communications Corporation.
0021:         * Portions created by the Initial Developer are Copyright (C) 1997-1999
0022:         * the Initial Developer. All Rights Reserved.
0023:         *
0024:         * Contributor(s):
0025:         *   Patrick Beard
0026:         *   Norris Boyd
0027:         *   Igor Bukanov
0028:         *   Mike McCabe
0029:         *   Matthias Radestock
0030:         *   Andi Vajda
0031:         *   Andrew Wason
0032:         *   Kemal Bayram
0033:         *
0034:         * Alternatively, the contents of this file may be used under the terms of
0035:         * the GNU General Public License Version 2 or later (the "GPL"), in which
0036:         * case the provisions of the GPL are applicable instead of those above. If
0037:         * you wish to allow use of your version of this file only under the terms of
0038:         * the GPL and not to allow others to use your version of this file under the
0039:         * MPL, indicate your decision by deleting the provisions above and replacing
0040:         * them with the notice and other provisions required by the GPL. If you do
0041:         * not delete the provisions above, a recipient may use your version of this
0042:         * file under either the MPL or the GPL.
0043:         *
0044:         * ***** END LICENSE BLOCK ***** */
0045:
0046:        package org.mozilla.javascript;
0047:
0048:        import org.mozilla.classfile.*;
0049:        import java.lang.reflect.*;
0050:        import java.io.*;
0051:        import java.security.*;
0052:        import java.util.*;
0053:
0054:        public final class JavaAdapter implements  IdFunctionCall {
0055:            /**
0056:             * Provides a key with which to distinguish previously generated
0057:             * adapter classes stored in a hash table.
0058:             */
0059:            static class JavaAdapterSignature {
0060:                Class super Class;
0061:                Class[] interfaces;
0062:                ObjToIntMap names;
0063:
0064:                JavaAdapterSignature(Class super Class, Class[] interfaces,
0065:                        ObjToIntMap names) {
0066:                    this .super Class = super Class;
0067:                    this .interfaces = interfaces;
0068:                    this .names = names;
0069:                }
0070:
0071:                public boolean equals(Object obj) {
0072:                    if (!(obj instanceof  JavaAdapterSignature))
0073:                        return false;
0074:                    JavaAdapterSignature sig = (JavaAdapterSignature) obj;
0075:                    if (super Class != sig.super Class)
0076:                        return false;
0077:                    if (interfaces != sig.interfaces) {
0078:                        if (interfaces.length != sig.interfaces.length)
0079:                            return false;
0080:                        for (int i = 0; i < interfaces.length; i++)
0081:                            if (interfaces[i] != sig.interfaces[i])
0082:                                return false;
0083:                    }
0084:                    if (names.size() != sig.names.size())
0085:                        return false;
0086:                    ObjToIntMap.Iterator iter = new ObjToIntMap.Iterator(names);
0087:                    for (iter.start(); !iter.done(); iter.next()) {
0088:                        String name = (String) iter.getKey();
0089:                        int arity = iter.getValue();
0090:                        if (arity != names.get(name, arity + 1))
0091:                            return false;
0092:                    }
0093:                    return true;
0094:                }
0095:
0096:                public int hashCode() {
0097:                    return super Class.hashCode()
0098:                            | (0x9e3779b9 * (names.size() | (interfaces.length << 16)));
0099:                }
0100:            }
0101:
0102:            public static void init(Context cx, Scriptable scope, boolean sealed) {
0103:                JavaAdapter obj = new JavaAdapter();
0104:                IdFunctionObject ctor = new IdFunctionObject(obj, FTAG,
0105:                        Id_JavaAdapter, "JavaAdapter", 1, scope);
0106:                ctor.markAsConstructor(null);
0107:                if (sealed) {
0108:                    ctor.sealObject();
0109:                }
0110:                ctor.exportAsScopeProperty();
0111:            }
0112:
0113:            public Object execIdCall(IdFunctionObject f, Context cx,
0114:                    Scriptable scope, Scriptable this Obj, Object[] args) {
0115:                if (f.hasTag(FTAG)) {
0116:                    if (f.methodId() == Id_JavaAdapter) {
0117:                        return js_createAdapter(cx, scope, args);
0118:                    }
0119:                }
0120:                throw f.unknown();
0121:            }
0122:
0123:            public static Object convertResult(Object result, Class c) {
0124:                if (result == Undefined.instance
0125:                        && (c != ScriptRuntime.ObjectClass && c != ScriptRuntime.StringClass)) {
0126:                    // Avoid an error for an undefined value; return null instead.
0127:                    return null;
0128:                }
0129:                return Context.jsToJava(result, c);
0130:            }
0131:
0132:            public static Scriptable createAdapterWrapper(Scriptable obj,
0133:                    Object adapter) {
0134:                Scriptable scope = ScriptableObject.getTopLevelScope(obj);
0135:                NativeJavaObject res = new NativeJavaObject(scope, adapter,
0136:                        null, true);
0137:                res.setPrototype(obj);
0138:                return res;
0139:            }
0140:
0141:            public static Object getAdapterSelf(Class adapterClass,
0142:                    Object adapter) throws NoSuchFieldException,
0143:                    IllegalAccessException {
0144:                Field self = adapterClass.getDeclaredField("self");
0145:                return self.get(adapter);
0146:            }
0147:
0148:            static Object js_createAdapter(Context cx, Scriptable scope,
0149:                    Object[] args) {
0150:                int N = args.length;
0151:                if (N == 0) {
0152:                    throw ScriptRuntime.typeError0("msg.adapter.zero.args");
0153:                }
0154:
0155:                Class super Class = null;
0156:                Class[] intfs = new Class[N - 1];
0157:                int interfaceCount = 0;
0158:                for (int i = 0; i != N - 1; ++i) {
0159:                    Object arg = args[i];
0160:                    if (!(arg instanceof  NativeJavaClass)) {
0161:                        throw ScriptRuntime.typeError2(
0162:                                "msg.not.java.class.arg", String.valueOf(i),
0163:                                ScriptRuntime.toString(arg));
0164:                    }
0165:                    Class c = ((NativeJavaClass) arg).getClassObject();
0166:                    if (!c.isInterface()) {
0167:                        if (super Class != null) {
0168:                            throw ScriptRuntime.typeError2(
0169:                                    "msg.only.one.super", super Class.getName(),
0170:                                    c.getName());
0171:                        }
0172:                        super Class = c;
0173:                    } else {
0174:                        intfs[interfaceCount++] = c;
0175:                    }
0176:                }
0177:
0178:                if (super Class == null)
0179:                    super Class = ScriptRuntime.ObjectClass;
0180:
0181:                Class[] interfaces = new Class[interfaceCount];
0182:                System.arraycopy(intfs, 0, interfaces, 0, interfaceCount);
0183:                Scriptable obj = ScriptRuntime.toObject(cx, scope, args[N - 1]);
0184:
0185:                Class adapterClass = getAdapterClass(scope, super Class,
0186:                        interfaces, obj);
0187:
0188:                Class[] ctorParms = { ScriptRuntime.ContextFactoryClass,
0189:                        ScriptRuntime.ScriptableClass };
0190:                Object[] ctorArgs = { cx.getFactory(), obj };
0191:                try {
0192:                    Object adapter = adapterClass.getConstructor(ctorParms)
0193:                            .newInstance(ctorArgs);
0194:                    return getAdapterSelf(adapterClass, adapter);
0195:                } catch (Exception ex) {
0196:                    throw Context.throwAsScriptRuntimeEx(ex);
0197:                }
0198:            }
0199:
0200:            // Needed by NativeJavaObject serializer
0201:            public static void writeAdapterObject(Object javaObject,
0202:                    ObjectOutputStream out) throws IOException {
0203:                Class cl = javaObject.getClass();
0204:                out.writeObject(cl.getSuperclass().getName());
0205:
0206:                Class[] interfaces = cl.getInterfaces();
0207:                String[] interfaceNames = new String[interfaces.length];
0208:
0209:                for (int i = 0; i < interfaces.length; i++)
0210:                    interfaceNames[i] = interfaces[i].getName();
0211:
0212:                out.writeObject(interfaceNames);
0213:
0214:                try {
0215:                    Object delegee = cl.getField("delegee").get(javaObject);
0216:                    out.writeObject(delegee);
0217:                    return;
0218:                } catch (IllegalAccessException e) {
0219:                } catch (NoSuchFieldException e) {
0220:                }
0221:                throw new IOException();
0222:            }
0223:
0224:            // Needed by NativeJavaObject de-serializer
0225:            public static Object readAdapterObject(Scriptable self,
0226:                    ObjectInputStream in) throws IOException,
0227:                    ClassNotFoundException {
0228:                ContextFactory factory;
0229:                Context cx = Context.getCurrentContext();
0230:                if (cx != null) {
0231:                    factory = cx.getFactory();
0232:                } else {
0233:                    factory = null;
0234:                }
0235:
0236:                Class super Class = Class.forName((String) in.readObject());
0237:
0238:                String[] interfaceNames = (String[]) in.readObject();
0239:                Class[] interfaces = new Class[interfaceNames.length];
0240:
0241:                for (int i = 0; i < interfaceNames.length; i++)
0242:                    interfaces[i] = Class.forName(interfaceNames[i]);
0243:
0244:                Scriptable delegee = (Scriptable) in.readObject();
0245:
0246:                Class adapterClass = getAdapterClass(self, super Class,
0247:                        interfaces, delegee);
0248:
0249:                Class[] ctorParms = { ScriptRuntime.ContextFactoryClass,
0250:                        ScriptRuntime.ScriptableClass,
0251:                        ScriptRuntime.ScriptableClass };
0252:                Object[] ctorArgs = { factory, delegee, self };
0253:                try {
0254:                    return adapterClass.getConstructor(ctorParms).newInstance(
0255:                            ctorArgs);
0256:                } catch (InstantiationException e) {
0257:                } catch (IllegalAccessException e) {
0258:                } catch (InvocationTargetException e) {
0259:                } catch (NoSuchMethodException e) {
0260:                }
0261:
0262:                throw new ClassNotFoundException("adapter");
0263:            }
0264:
0265:            private static ObjToIntMap getObjectFunctionNames(Scriptable obj) {
0266:                Object[] ids = ScriptableObject.getPropertyIds(obj);
0267:                ObjToIntMap map = new ObjToIntMap(ids.length);
0268:                for (int i = 0; i != ids.length; ++i) {
0269:                    if (!(ids[i] instanceof  String))
0270:                        continue;
0271:                    String id = (String) ids[i];
0272:                    Object value = ScriptableObject.getProperty(obj, id);
0273:                    if (value instanceof  Function) {
0274:                        Function f = (Function) value;
0275:                        int length = ScriptRuntime.toInt32(ScriptableObject
0276:                                .getProperty(f, "length"));
0277:                        if (length < 0) {
0278:                            length = 0;
0279:                        }
0280:                        map.put(id, length);
0281:                    }
0282:                }
0283:                return map;
0284:            }
0285:
0286:            private static Class getAdapterClass(Scriptable scope,
0287:                    Class super Class, Class[] interfaces, Scriptable obj) {
0288:                ClassCache cache = ClassCache.get(scope);
0289:                Map<JavaAdapterSignature, Class<?>> generated = cache
0290:                        .getInterfaceAdapterCacheMap();
0291:
0292:                ObjToIntMap names = getObjectFunctionNames(obj);
0293:                JavaAdapterSignature sig;
0294:                sig = new JavaAdapterSignature(super Class, interfaces, names);
0295:                Class<?> adapterClass = generated.get(sig);
0296:                if (adapterClass == null) {
0297:                    String adapterName = "adapter"
0298:                            + cache.newClassSerialNumber();
0299:                    byte[] code = createAdapterCode(names, adapterName,
0300:                            super Class, interfaces, null);
0301:
0302:                    adapterClass = loadAdapterClass(adapterName, code);
0303:                    if (cache.isCachingEnabled()) {
0304:                        generated.put(sig, adapterClass);
0305:                    }
0306:                }
0307:                return adapterClass;
0308:            }
0309:
0310:            public static byte[] createAdapterCode(ObjToIntMap functionNames,
0311:                    String adapterName, Class super Class, Class[] interfaces,
0312:                    String scriptClassName) {
0313:                ClassFileWriter cfw = new ClassFileWriter(adapterName,
0314:                        super Class.getName(), "<adapter>");
0315:                cfw
0316:                        .addField(
0317:                                "factory",
0318:                                "Lorg/mozilla/javascript/ContextFactory;",
0319:                                (short) (ClassFileWriter.ACC_PUBLIC | ClassFileWriter.ACC_FINAL));
0320:                cfw
0321:                        .addField(
0322:                                "delegee",
0323:                                "Lorg/mozilla/javascript/Scriptable;",
0324:                                (short) (ClassFileWriter.ACC_PUBLIC | ClassFileWriter.ACC_FINAL));
0325:                cfw
0326:                        .addField(
0327:                                "self",
0328:                                "Lorg/mozilla/javascript/Scriptable;",
0329:                                (short) (ClassFileWriter.ACC_PUBLIC | ClassFileWriter.ACC_FINAL));
0330:                int interfacesCount = interfaces == null ? 0
0331:                        : interfaces.length;
0332:                for (int i = 0; i < interfacesCount; i++) {
0333:                    if (interfaces[i] != null)
0334:                        cfw.addInterface(interfaces[i].getName());
0335:                }
0336:
0337:                String super Name = super Class.getName().replace('.', '/');
0338:                generateCtor(cfw, adapterName, super Name);
0339:                generateSerialCtor(cfw, adapterName, super Name);
0340:                if (scriptClassName != null)
0341:                    generateEmptyCtor(cfw, adapterName, super Name,
0342:                            scriptClassName);
0343:
0344:                ObjToIntMap generatedOverrides = new ObjToIntMap();
0345:                ObjToIntMap generatedMethods = new ObjToIntMap();
0346:
0347:                // generate methods to satisfy all specified interfaces.
0348:                for (int i = 0; i < interfacesCount; i++) {
0349:                    Method[] methods = interfaces[i].getMethods();
0350:                    for (int j = 0; j < methods.length; j++) {
0351:                        Method method = methods[j];
0352:                        int mods = method.getModifiers();
0353:                        if (Modifier.isStatic(mods) || Modifier.isFinal(mods)) {
0354:                            continue;
0355:                        }
0356:                        String methodName = method.getName();
0357:                        Class[] argTypes = method.getParameterTypes();
0358:                        if (!functionNames.has(methodName)) {
0359:                            try {
0360:                                super Class.getMethod(methodName, argTypes);
0361:                                // The class we're extending implements this method and
0362:                                // the JavaScript object doesn't have an override. See
0363:                                // bug 61226.
0364:                                continue;
0365:                            } catch (NoSuchMethodException e) {
0366:                                // Not implemented by superclass; fall through
0367:                            }
0368:                        }
0369:                        // make sure to generate only one instance of a particular
0370:                        // method/signature.
0371:                        String methodSignature = getMethodSignature(method,
0372:                                argTypes);
0373:                        String methodKey = methodName + methodSignature;
0374:                        if (!generatedOverrides.has(methodKey)) {
0375:                            generateMethod(cfw, adapterName, methodName,
0376:                                    argTypes, method.getReturnType());
0377:                            generatedOverrides.put(methodKey, 0);
0378:                            generatedMethods.put(methodName, 0);
0379:                        }
0380:                    }
0381:                }
0382:
0383:                // Now, go through the superclass's methods, checking for abstract
0384:                // methods or additional methods to override.
0385:
0386:                // generate any additional overrides that the object might contain.
0387:                Method[] methods = getOverridableMethods(super Class);
0388:                for (int j = 0; j < methods.length; j++) {
0389:                    Method method = methods[j];
0390:                    int mods = method.getModifiers();
0391:                    // if a method is marked abstract, must implement it or the
0392:                    // resulting class won't be instantiable. otherwise, if the object
0393:                    // has a property of the same name, then an override is intended.
0394:                    boolean isAbstractMethod = Modifier.isAbstract(mods);
0395:                    String methodName = method.getName();
0396:                    if (isAbstractMethod || functionNames.has(methodName)) {
0397:                        // make sure to generate only one instance of a particular
0398:                        // method/signature.
0399:                        Class[] argTypes = method.getParameterTypes();
0400:                        String methodSignature = getMethodSignature(method,
0401:                                argTypes);
0402:                        String methodKey = methodName + methodSignature;
0403:                        if (!generatedOverrides.has(methodKey)) {
0404:                            generateMethod(cfw, adapterName, methodName,
0405:                                    argTypes, method.getReturnType());
0406:                            generatedOverrides.put(methodKey, 0);
0407:                            generatedMethods.put(methodName, 0);
0408:
0409:                            // if a method was overridden, generate a "super$method"
0410:                            // which lets the delegate call the superclass' version.
0411:                            if (!isAbstractMethod) {
0412:                                generateSuper(cfw, adapterName, super Name,
0413:                                        methodName, methodSignature, argTypes,
0414:                                        method.getReturnType());
0415:                            }
0416:                        }
0417:                    }
0418:                }
0419:
0420:                // Generate Java methods for remaining properties that are not
0421:                // overrides.
0422:                ObjToIntMap.Iterator iter = new ObjToIntMap.Iterator(
0423:                        functionNames);
0424:                for (iter.start(); !iter.done(); iter.next()) {
0425:                    String functionName = (String) iter.getKey();
0426:                    if (generatedMethods.has(functionName))
0427:                        continue;
0428:                    int length = iter.getValue();
0429:                    Class[] parms = new Class[length];
0430:                    for (int k = 0; k < length; k++)
0431:                        parms[k] = ScriptRuntime.ObjectClass;
0432:                    generateMethod(cfw, adapterName, functionName, parms,
0433:                            ScriptRuntime.ObjectClass);
0434:                }
0435:                return cfw.toByteArray();
0436:            }
0437:
0438:            static Method[] getOverridableMethods(Class c) {
0439:                ArrayList<Method> list = new ArrayList<Method>();
0440:                HashSet<String> skip = new HashSet<String>();
0441:                while (c != null) {
0442:                    Method[] methods = c.getDeclaredMethods();
0443:                    for (int i = 0; i < methods.length; i++) {
0444:                        String methodKey = methods[i].getName()
0445:                                + getMethodSignature(methods[i], methods[i]
0446:                                        .getParameterTypes());
0447:                        if (skip.contains(methodKey))
0448:                            continue; // skip this method
0449:                        int mods = methods[i].getModifiers();
0450:                        if (Modifier.isStatic(mods))
0451:                            continue;
0452:                        if (Modifier.isFinal(mods)) {
0453:                            // Make sure we don't add a final method to the list
0454:                            // of overridable methods.
0455:                            skip.add(methodKey);
0456:                            continue;
0457:                        }
0458:                        if (Modifier.isPublic(mods)
0459:                                || Modifier.isProtected(mods)) {
0460:                            list.add(methods[i]);
0461:                            skip.add(methodKey);
0462:                        }
0463:                    }
0464:                    c = c.getSuperclass();
0465:                }
0466:                return list.toArray(new Method[list.size()]);
0467:            }
0468:
0469:            static Class loadAdapterClass(String className, byte[] classBytes) {
0470:                Object staticDomain;
0471:                Class domainClass = SecurityController
0472:                        .getStaticSecurityDomainClass();
0473:                if (domainClass == CodeSource.class
0474:                        || domainClass == ProtectionDomain.class) {
0475:                    ProtectionDomain protectionDomain = JavaAdapter.class
0476:                            .getProtectionDomain();
0477:                    if (domainClass == CodeSource.class) {
0478:                        staticDomain = protectionDomain == null ? null
0479:                                : protectionDomain.getCodeSource();
0480:                    } else {
0481:                        staticDomain = protectionDomain;
0482:                    }
0483:                } else {
0484:                    staticDomain = null;
0485:                }
0486:                GeneratedClassLoader loader = SecurityController.createLoader(
0487:                        null, staticDomain);
0488:                Class result = loader.defineClass(className, classBytes);
0489:                loader.linkClass(result);
0490:                return result;
0491:            }
0492:
0493:            public static Function getFunction(Scriptable obj,
0494:                    String functionName) {
0495:                Object x = ScriptableObject.getProperty(obj, functionName);
0496:                if (x == Scriptable.NOT_FOUND) {
0497:                    // This method used to swallow the exception from calling
0498:                    // an undefined method. People have come to depend on this
0499:                    // somewhat dubious behavior. It allows people to avoid
0500:                    // implementing listener methods that they don't care about,
0501:                    // for instance.
0502:                    return null;
0503:                }
0504:                if (!(x instanceof  Function))
0505:                    throw ScriptRuntime.notFunctionError(x, functionName);
0506:
0507:                return (Function) x;
0508:            }
0509:
0510:            /**
0511:             * Utility method which dynamically binds a Context to the current thread,
0512:             * if none already exists.
0513:             */
0514:            public static Object callMethod(ContextFactory factory,
0515:                    final Scriptable this Obj, final Function f,
0516:                    final Object[] args, final long argsToWrap) {
0517:                if (f == null) {
0518:                    // See comments in getFunction
0519:                    return Undefined.instance;
0520:                }
0521:                if (factory == null) {
0522:                    factory = ContextFactory.getGlobal();
0523:                }
0524:
0525:                final Scriptable scope = f.getParentScope();
0526:                if (argsToWrap == 0) {
0527:                    return Context.call(factory, f, scope, this Obj, args);
0528:                }
0529:
0530:                Context cx = Context.getCurrentContext();
0531:                if (cx != null) {
0532:                    return doCall(cx, scope, this Obj, f, args, argsToWrap);
0533:                } else {
0534:                    return factory.call(new ContextAction() {
0535:                        public Object run(Context cx) {
0536:                            return doCall(cx, scope, this Obj, f, args,
0537:                                    argsToWrap);
0538:                        }
0539:                    });
0540:                }
0541:            }
0542:
0543:            private static Object doCall(Context cx, Scriptable scope,
0544:                    Scriptable this Obj, Function f, Object[] args,
0545:                    long argsToWrap) {
0546:                // Wrap the rest of objects
0547:                for (int i = 0; i != args.length; ++i) {
0548:                    if (0 != (argsToWrap & (1 << i))) {
0549:                        Object arg = args[i];
0550:                        if (!(arg instanceof  Scriptable)) {
0551:                            args[i] = cx.getWrapFactory().wrap(cx, scope, arg,
0552:                                    null);
0553:                        }
0554:                    }
0555:                }
0556:                return f.call(cx, scope, this Obj, args);
0557:            }
0558:
0559:            public static Scriptable runScript(final Script script) {
0560:                return (Scriptable) Context.call(new ContextAction() {
0561:                    public Object run(Context cx) {
0562:                        ScriptableObject global = ScriptRuntime.getGlobal(cx);
0563:                        script.exec(cx, global);
0564:                        return global;
0565:                    }
0566:                });
0567:            }
0568:
0569:            private static void generateCtor(ClassFileWriter cfw,
0570:                    String adapterName, String super Name) {
0571:                cfw.startMethod("<init>",
0572:                        "(Lorg/mozilla/javascript/ContextFactory;"
0573:                                + "Lorg/mozilla/javascript/Scriptable;)V",
0574:                        ClassFileWriter.ACC_PUBLIC);
0575:
0576:                // Invoke base class constructor
0577:                cfw.add(ByteCode.ALOAD_0); // this
0578:                cfw.addInvoke(ByteCode.INVOKESPECIAL, super Name, "<init>",
0579:                        "()V");
0580:
0581:                // Save parameter in instance variable "factory"
0582:                cfw.add(ByteCode.ALOAD_0); // this
0583:                cfw.add(ByteCode.ALOAD_1); // first arg: ContextFactory instance
0584:                cfw.add(ByteCode.PUTFIELD, adapterName, "factory",
0585:                        "Lorg/mozilla/javascript/ContextFactory;");
0586:
0587:                // Save parameter in instance variable "delegee"
0588:                cfw.add(ByteCode.ALOAD_0); // this
0589:                cfw.add(ByteCode.ALOAD_2); // second arg: Scriptable delegee
0590:                cfw.add(ByteCode.PUTFIELD, adapterName, "delegee",
0591:                        "Lorg/mozilla/javascript/Scriptable;");
0592:
0593:                cfw.add(ByteCode.ALOAD_0); // this for the following PUTFIELD for self
0594:                // create a wrapper object to be used as "this" in method calls
0595:                cfw.add(ByteCode.ALOAD_2); // the Scriptable delegee
0596:                cfw.add(ByteCode.ALOAD_0); // this
0597:                cfw.addInvoke(ByteCode.INVOKESTATIC,
0598:                        "org/mozilla/javascript/JavaAdapter",
0599:                        "createAdapterWrapper",
0600:                        "(Lorg/mozilla/javascript/Scriptable;"
0601:                                + "Ljava/lang/Object;"
0602:                                + ")Lorg/mozilla/javascript/Scriptable;");
0603:                cfw.add(ByteCode.PUTFIELD, adapterName, "self",
0604:                        "Lorg/mozilla/javascript/Scriptable;");
0605:
0606:                cfw.add(ByteCode.RETURN);
0607:                cfw.stopMethod((short) 3); // 3: this + factory + delegee
0608:            }
0609:
0610:            private static void generateSerialCtor(ClassFileWriter cfw,
0611:                    String adapterName, String super Name) {
0612:                cfw.startMethod("<init>",
0613:                        "(Lorg/mozilla/javascript/ContextFactory;"
0614:                                + "Lorg/mozilla/javascript/Scriptable;"
0615:                                + "Lorg/mozilla/javascript/Scriptable;" + ")V",
0616:                        ClassFileWriter.ACC_PUBLIC);
0617:
0618:                // Invoke base class constructor
0619:                cfw.add(ByteCode.ALOAD_0); // this
0620:                cfw.addInvoke(ByteCode.INVOKESPECIAL, super Name, "<init>",
0621:                        "()V");
0622:
0623:                // Save parameter in instance variable "factory"
0624:                cfw.add(ByteCode.ALOAD_0); // this
0625:                cfw.add(ByteCode.ALOAD_1); // first arg: ContextFactory instance
0626:                cfw.add(ByteCode.PUTFIELD, adapterName, "factory",
0627:                        "Lorg/mozilla/javascript/ContextFactory;");
0628:
0629:                // Save parameter in instance variable "delegee"
0630:                cfw.add(ByteCode.ALOAD_0); // this
0631:                cfw.add(ByteCode.ALOAD_2); // second arg: Scriptable delegee
0632:                cfw.add(ByteCode.PUTFIELD, adapterName, "delegee",
0633:                        "Lorg/mozilla/javascript/Scriptable;");
0634:                // save self
0635:                cfw.add(ByteCode.ALOAD_0); // this
0636:                cfw.add(ByteCode.ALOAD_3); // second arg: Scriptable self
0637:                cfw.add(ByteCode.PUTFIELD, adapterName, "self",
0638:                        "Lorg/mozilla/javascript/Scriptable;");
0639:
0640:                cfw.add(ByteCode.RETURN);
0641:                cfw.stopMethod((short) 4); // 4: this + factory + delegee + self
0642:            }
0643:
0644:            private static void generateEmptyCtor(ClassFileWriter cfw,
0645:                    String adapterName, String super Name, String scriptClassName) {
0646:                cfw.startMethod("<init>", "()V", ClassFileWriter.ACC_PUBLIC);
0647:
0648:                // Invoke base class constructor
0649:                cfw.add(ByteCode.ALOAD_0); // this
0650:                cfw.addInvoke(ByteCode.INVOKESPECIAL, super Name, "<init>",
0651:                        "()V");
0652:
0653:                // Set factory to null to use current global when necessary
0654:                cfw.add(ByteCode.ALOAD_0);
0655:                cfw.add(ByteCode.ACONST_NULL);
0656:                cfw.add(ByteCode.PUTFIELD, adapterName, "factory",
0657:                        "Lorg/mozilla/javascript/ContextFactory;");
0658:
0659:                // Load script class
0660:                cfw.add(ByteCode.NEW, scriptClassName);
0661:                cfw.add(ByteCode.DUP);
0662:                cfw.addInvoke(ByteCode.INVOKESPECIAL, scriptClassName,
0663:                        "<init>", "()V");
0664:
0665:                // Run script and save resulting scope
0666:                cfw.addInvoke(ByteCode.INVOKESTATIC,
0667:                        "org/mozilla/javascript/JavaAdapter", "runScript",
0668:                        "(Lorg/mozilla/javascript/Script;"
0669:                                + ")Lorg/mozilla/javascript/Scriptable;");
0670:                cfw.add(ByteCode.ASTORE_1);
0671:
0672:                // Save the Scriptable in instance variable "delegee"
0673:                cfw.add(ByteCode.ALOAD_0); // this
0674:                cfw.add(ByteCode.ALOAD_1); // the Scriptable
0675:                cfw.add(ByteCode.PUTFIELD, adapterName, "delegee",
0676:                        "Lorg/mozilla/javascript/Scriptable;");
0677:
0678:                cfw.add(ByteCode.ALOAD_0); // this for the following PUTFIELD for self
0679:                // create a wrapper object to be used as "this" in method calls
0680:                cfw.add(ByteCode.ALOAD_1); // the Scriptable
0681:                cfw.add(ByteCode.ALOAD_0); // this
0682:                cfw.addInvoke(ByteCode.INVOKESTATIC,
0683:                        "org/mozilla/javascript/JavaAdapter",
0684:                        "createAdapterWrapper",
0685:                        "(Lorg/mozilla/javascript/Scriptable;"
0686:                                + "Ljava/lang/Object;"
0687:                                + ")Lorg/mozilla/javascript/Scriptable;");
0688:                cfw.add(ByteCode.PUTFIELD, adapterName, "self",
0689:                        "Lorg/mozilla/javascript/Scriptable;");
0690:
0691:                cfw.add(ByteCode.RETURN);
0692:                cfw.stopMethod((short) 2); // this + delegee
0693:            }
0694:
0695:            /**
0696:             * Generates code to wrap Java arguments into Object[].
0697:             * Non-primitive Java types are left as-is pending conversion
0698:             * in the helper method. Leaves the array object on the top of the stack.
0699:             */
0700:            static void generatePushWrappedArgs(ClassFileWriter cfw,
0701:                    Class[] argTypes, int arrayLength) {
0702:                // push arguments
0703:                cfw.addPush(arrayLength);
0704:                cfw.add(ByteCode.ANEWARRAY, "java/lang/Object");
0705:                int paramOffset = 1;
0706:                for (int i = 0; i != argTypes.length; ++i) {
0707:                    cfw.add(ByteCode.DUP); // duplicate array reference
0708:                    cfw.addPush(i);
0709:                    paramOffset += generateWrapArg(cfw, paramOffset,
0710:                            argTypes[i]);
0711:                    cfw.add(ByteCode.AASTORE);
0712:                }
0713:            }
0714:
0715:            /**
0716:             * Generates code to wrap Java argument into Object.
0717:             * Non-primitive Java types are left unconverted pending conversion
0718:             * in the helper method. Leaves the wrapper object on the top of the stack.
0719:             */
0720:            private static int generateWrapArg(ClassFileWriter cfw,
0721:                    int paramOffset, Class argType) {
0722:                int size = 1;
0723:                if (!argType.isPrimitive()) {
0724:                    cfw.add(ByteCode.ALOAD, paramOffset);
0725:
0726:                } else if (argType == Boolean.TYPE) {
0727:                    // wrap boolean values with java.lang.Boolean.
0728:                    cfw.add(ByteCode.NEW, "java/lang/Boolean");
0729:                    cfw.add(ByteCode.DUP);
0730:                    cfw.add(ByteCode.ILOAD, paramOffset);
0731:                    cfw.addInvoke(ByteCode.INVOKESPECIAL, "java/lang/Boolean",
0732:                            "<init>", "(Z)V");
0733:
0734:                } else if (argType == Character.TYPE) {
0735:                    // Create a string of length 1 using the character parameter.
0736:                    cfw.add(ByteCode.ILOAD, paramOffset);
0737:                    cfw.addInvoke(ByteCode.INVOKESTATIC, "java/lang/String",
0738:                            "valueOf", "(C)Ljava/lang/String;");
0739:
0740:                } else {
0741:                    // convert all numeric values to java.lang.Double.
0742:                    cfw.add(ByteCode.NEW, "java/lang/Double");
0743:                    cfw.add(ByteCode.DUP);
0744:                    String typeName = argType.getName();
0745:                    switch (typeName.charAt(0)) {
0746:                    case 'b':
0747:                    case 's':
0748:                    case 'i':
0749:                        // load an int value, convert to double.
0750:                        cfw.add(ByteCode.ILOAD, paramOffset);
0751:                        cfw.add(ByteCode.I2D);
0752:                        break;
0753:                    case 'l':
0754:                        // load a long, convert to double.
0755:                        cfw.add(ByteCode.LLOAD, paramOffset);
0756:                        cfw.add(ByteCode.L2D);
0757:                        size = 2;
0758:                        break;
0759:                    case 'f':
0760:                        // load a float, convert to double.
0761:                        cfw.add(ByteCode.FLOAD, paramOffset);
0762:                        cfw.add(ByteCode.F2D);
0763:                        break;
0764:                    case 'd':
0765:                        cfw.add(ByteCode.DLOAD, paramOffset);
0766:                        size = 2;
0767:                        break;
0768:                    }
0769:                    cfw.addInvoke(ByteCode.INVOKESPECIAL, "java/lang/Double",
0770:                            "<init>", "(D)V");
0771:                }
0772:                return size;
0773:            }
0774:
0775:            /**
0776:             * Generates code to convert a wrapped value type to a primitive type.
0777:             * Handles unwrapping java.lang.Boolean, and java.lang.Number types.
0778:             * Generates the appropriate RETURN bytecode.
0779:             */
0780:            static void generateReturnResult(ClassFileWriter cfw,
0781:                    Class retType, boolean callConvertResult) {
0782:                // wrap boolean values with java.lang.Boolean, convert all other
0783:                // primitive values to java.lang.Double.
0784:                if (retType == Void.TYPE) {
0785:                    cfw.add(ByteCode.POP);
0786:                    cfw.add(ByteCode.RETURN);
0787:
0788:                } else if (retType == Boolean.TYPE) {
0789:                    cfw.addInvoke(ByteCode.INVOKESTATIC,
0790:                            "org/mozilla/javascript/Context", "toBoolean",
0791:                            "(Ljava/lang/Object;)Z");
0792:                    cfw.add(ByteCode.IRETURN);
0793:
0794:                } else if (retType == Character.TYPE) {
0795:                    // characters are represented as strings in JavaScript.
0796:                    // return the first character.
0797:                    // first convert the value to a string if possible.
0798:                    cfw.addInvoke(ByteCode.INVOKESTATIC,
0799:                            "org/mozilla/javascript/Context", "toString",
0800:                            "(Ljava/lang/Object;)Ljava/lang/String;");
0801:                    cfw.add(ByteCode.ICONST_0);
0802:                    cfw.addInvoke(ByteCode.INVOKEVIRTUAL, "java/lang/String",
0803:                            "charAt", "(I)C");
0804:                    cfw.add(ByteCode.IRETURN);
0805:
0806:                } else if (retType.isPrimitive()) {
0807:                    cfw.addInvoke(ByteCode.INVOKESTATIC,
0808:                            "org/mozilla/javascript/Context", "toNumber",
0809:                            "(Ljava/lang/Object;)D");
0810:                    String typeName = retType.getName();
0811:                    switch (typeName.charAt(0)) {
0812:                    case 'b':
0813:                    case 's':
0814:                    case 'i':
0815:                        cfw.add(ByteCode.D2I);
0816:                        cfw.add(ByteCode.IRETURN);
0817:                        break;
0818:                    case 'l':
0819:                        cfw.add(ByteCode.D2L);
0820:                        cfw.add(ByteCode.LRETURN);
0821:                        break;
0822:                    case 'f':
0823:                        cfw.add(ByteCode.D2F);
0824:                        cfw.add(ByteCode.FRETURN);
0825:                        break;
0826:                    case 'd':
0827:                        cfw.add(ByteCode.DRETURN);
0828:                        break;
0829:                    default:
0830:                        throw new RuntimeException("Unexpected return type "
0831:                                + retType.toString());
0832:                    }
0833:
0834:                } else {
0835:                    String retTypeStr = retType.getName();
0836:                    if (callConvertResult) {
0837:                        cfw.addLoadConstant(retTypeStr);
0838:                        cfw.addInvoke(ByteCode.INVOKESTATIC, "java/lang/Class",
0839:                                "forName",
0840:                                "(Ljava/lang/String;)Ljava/lang/Class;");
0841:
0842:                        cfw.addInvoke(ByteCode.INVOKESTATIC,
0843:                                "org/mozilla/javascript/JavaAdapter",
0844:                                "convertResult", "(Ljava/lang/Object;"
0845:                                        + "Ljava/lang/Class;"
0846:                                        + ")Ljava/lang/Object;");
0847:                    }
0848:                    // Now cast to return type
0849:                    cfw.add(ByteCode.CHECKCAST, retTypeStr);
0850:                    cfw.add(ByteCode.ARETURN);
0851:                }
0852:            }
0853:
0854:            private static void generateMethod(ClassFileWriter cfw,
0855:                    String genName, String methodName, Class[] parms,
0856:                    Class returnType) {
0857:                StringBuffer sb = new StringBuffer();
0858:                int paramsEnd = appendMethodSignature(parms, returnType, sb);
0859:                String methodSignature = sb.toString();
0860:                cfw.startMethod(methodName, methodSignature,
0861:                        ClassFileWriter.ACC_PUBLIC);
0862:
0863:                // Prepare stack to call method
0864:
0865:                // push factory
0866:                cfw.add(ByteCode.ALOAD_0);
0867:                cfw.add(ByteCode.GETFIELD, genName, "factory",
0868:                        "Lorg/mozilla/javascript/ContextFactory;");
0869:
0870:                // push self
0871:                cfw.add(ByteCode.ALOAD_0);
0872:                cfw.add(ByteCode.GETFIELD, genName, "self",
0873:                        "Lorg/mozilla/javascript/Scriptable;");
0874:
0875:                // push function
0876:                cfw.add(ByteCode.ALOAD_0);
0877:                cfw.add(ByteCode.GETFIELD, genName, "delegee",
0878:                        "Lorg/mozilla/javascript/Scriptable;");
0879:                cfw.addPush(methodName);
0880:                cfw.addInvoke(ByteCode.INVOKESTATIC,
0881:                        "org/mozilla/javascript/JavaAdapter", "getFunction",
0882:                        "(Lorg/mozilla/javascript/Scriptable;"
0883:                                + "Ljava/lang/String;"
0884:                                + ")Lorg/mozilla/javascript/Function;");
0885:
0886:                // push arguments
0887:                generatePushWrappedArgs(cfw, parms, parms.length);
0888:
0889:                // push bits to indicate which parameters should be wrapped
0890:                if (parms.length > 64) {
0891:                    // If it will be an issue, then passing a static boolean array
0892:                    // can be an option, but for now using simple bitmask
0893:                    throw Context
0894:                            .reportRuntimeError0("JavaAdapter can not subclass methods with more then"
0895:                                    + " 64 arguments.");
0896:                }
0897:                long convertionMask = 0;
0898:                for (int i = 0; i != parms.length; ++i) {
0899:                    if (!parms[i].isPrimitive()) {
0900:                        convertionMask |= (1 << i);
0901:                    }
0902:                }
0903:                cfw.addPush(convertionMask);
0904:
0905:                // go through utility method, which creates a Context to run the
0906:                // method in.
0907:                cfw.addInvoke(ByteCode.INVOKESTATIC,
0908:                        "org/mozilla/javascript/JavaAdapter", "callMethod",
0909:                        "(Lorg/mozilla/javascript/ContextFactory;"
0910:                                + "Lorg/mozilla/javascript/Scriptable;"
0911:                                + "Lorg/mozilla/javascript/Function;"
0912:                                + "[Ljava/lang/Object;" + "J"
0913:                                + ")Ljava/lang/Object;");
0914:
0915:                generateReturnResult(cfw, returnType, true);
0916:
0917:                cfw.stopMethod((short) paramsEnd);
0918:            }
0919:
0920:            /**
0921:             * Generates code to push typed parameters onto the operand stack
0922:             * prior to a direct Java method call.
0923:             */
0924:            private static int generatePushParam(ClassFileWriter cfw,
0925:                    int paramOffset, Class paramType) {
0926:                if (!paramType.isPrimitive()) {
0927:                    cfw.addALoad(paramOffset);
0928:                    return 1;
0929:                }
0930:                String typeName = paramType.getName();
0931:                switch (typeName.charAt(0)) {
0932:                case 'z':
0933:                case 'b':
0934:                case 'c':
0935:                case 's':
0936:                case 'i':
0937:                    // load an int value, convert to double.
0938:                    cfw.addILoad(paramOffset);
0939:                    return 1;
0940:                case 'l':
0941:                    // load a long, convert to double.
0942:                    cfw.addLLoad(paramOffset);
0943:                    return 2;
0944:                case 'f':
0945:                    // load a float, convert to double.
0946:                    cfw.addFLoad(paramOffset);
0947:                    return 1;
0948:                case 'd':
0949:                    cfw.addDLoad(paramOffset);
0950:                    return 2;
0951:                }
0952:                throw Kit.codeBug();
0953:            }
0954:
0955:            /**
0956:             * Generates code to return a Java type, after calling a Java method
0957:             * that returns the same type.
0958:             * Generates the appropriate RETURN bytecode.
0959:             */
0960:            private static void generatePopResult(ClassFileWriter cfw,
0961:                    Class retType) {
0962:                if (retType.isPrimitive()) {
0963:                    String typeName = retType.getName();
0964:                    switch (typeName.charAt(0)) {
0965:                    case 'b':
0966:                    case 'c':
0967:                    case 's':
0968:                    case 'i':
0969:                    case 'z':
0970:                        cfw.add(ByteCode.IRETURN);
0971:                        break;
0972:                    case 'l':
0973:                        cfw.add(ByteCode.LRETURN);
0974:                        break;
0975:                    case 'f':
0976:                        cfw.add(ByteCode.FRETURN);
0977:                        break;
0978:                    case 'd':
0979:                        cfw.add(ByteCode.DRETURN);
0980:                        break;
0981:                    }
0982:                } else {
0983:                    cfw.add(ByteCode.ARETURN);
0984:                }
0985:            }
0986:
0987:            /**
0988:             * Generates a method called "super$methodName()" which can be called
0989:             * from JavaScript that is equivalent to calling "super.methodName()"
0990:             * from Java. Eventually, this may be supported directly in JavaScript.
0991:             */
0992:            private static void generateSuper(ClassFileWriter cfw,
0993:                    String genName, String super Name, String methodName,
0994:                    String methodSignature, Class[] parms, Class returnType) {
0995:                cfw.startMethod("super$" + methodName, methodSignature,
0996:                        ClassFileWriter.ACC_PUBLIC);
0997:
0998:                // push "this"
0999:                cfw.add(ByteCode.ALOAD, 0);
1000:
1001:                // push the rest of the parameters.
1002:                int paramOffset = 1;
1003:                for (int i = 0; i < parms.length; i++) {
1004:                    paramOffset += generatePushParam(cfw, paramOffset, parms[i]);
1005:                }
1006:
1007:                // call the superclass implementation of the method.
1008:                cfw.addInvoke(ByteCode.INVOKESPECIAL, super Name, methodName,
1009:                        methodSignature);
1010:
1011:                // now, handle the return type appropriately.
1012:                Class retType = returnType;
1013:                if (!retType.equals(Void.TYPE)) {
1014:                    generatePopResult(cfw, retType);
1015:                } else {
1016:                    cfw.add(ByteCode.RETURN);
1017:                }
1018:                cfw.stopMethod((short) (paramOffset + 1));
1019:            }
1020:
1021:            /**
1022:             * Returns a fully qualified method name concatenated with its signature.
1023:             */
1024:            private static String getMethodSignature(Method method,
1025:                    Class[] argTypes) {
1026:                StringBuffer sb = new StringBuffer();
1027:                appendMethodSignature(argTypes, method.getReturnType(), sb);
1028:                return sb.toString();
1029:            }
1030:
1031:            static int appendMethodSignature(Class[] argTypes,
1032:                    Class returnType, StringBuffer sb) {
1033:                sb.append('(');
1034:                int firstLocal = 1 + argTypes.length; // includes this.
1035:                for (int i = 0; i < argTypes.length; i++) {
1036:                    Class type = argTypes[i];
1037:                    appendTypeString(sb, type);
1038:                    if (type == Long.TYPE || type == Double.TYPE) {
1039:                        // adjust for duble slot
1040:                        ++firstLocal;
1041:                    }
1042:                }
1043:                sb.append(')');
1044:                appendTypeString(sb, returnType);
1045:                return firstLocal;
1046:            }
1047:
1048:            private static StringBuffer appendTypeString(StringBuffer sb,
1049:                    Class type) {
1050:                while (type.isArray()) {
1051:                    sb.append('[');
1052:                    type = type.getComponentType();
1053:                }
1054:                if (type.isPrimitive()) {
1055:                    char typeLetter;
1056:                    if (type == Boolean.TYPE) {
1057:                        typeLetter = 'Z';
1058:                    } else if (type == Long.TYPE) {
1059:                        typeLetter = 'J';
1060:                    } else {
1061:                        String typeName = type.getName();
1062:                        typeLetter = Character.toUpperCase(typeName.charAt(0));
1063:                    }
1064:                    sb.append(typeLetter);
1065:                } else {
1066:                    sb.append('L');
1067:                    sb.append(type.getName().replace('.', '/'));
1068:                    sb.append(';');
1069:                }
1070:                return sb;
1071:            }
1072:
1073:            static int[] getArgsToConvert(Class[] argTypes) {
1074:                int count = 0;
1075:                for (int i = 0; i != argTypes.length; ++i) {
1076:                    if (!argTypes[i].isPrimitive())
1077:                        ++count;
1078:                }
1079:                if (count == 0)
1080:                    return null;
1081:                int[] array = new int[count];
1082:                count = 0;
1083:                for (int i = 0; i != argTypes.length; ++i) {
1084:                    if (!argTypes[i].isPrimitive())
1085:                        array[count++] = i;
1086:                }
1087:                return array;
1088:            }
1089:
1090:            private static final Object FTAG = new Object();
1091:            private static final int Id_JavaAdapter = 1;
1092:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.