1/* 2 * Copyright (C) 2003, 2008, 2010 Apple Inc. All rights reserved. 3 * Copyright 2010, The Android Open Source Project 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * * Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * * Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 14 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``AS IS'' AND ANY 15 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 17 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR 18 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 19 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 20 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 21 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 22 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 24 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26 27#include "config.h" 28#include "JavaInstanceJobjectV8.h" 29 30#if ENABLE(JAVA_BRIDGE) 31 32#include "JNIUtilityPrivate.h" 33#include "JavaClassJobjectV8.h" 34#include "JavaFieldV8.h" 35#include "JavaMethod.h" 36 37#include <wtf/OwnArrayPtr.h> 38#include <wtf/PassOwnPtr.h> 39#include <wtf/text/CString.h> 40#include <wtf/text/StringBuilder.h> 41 42using namespace JSC::Bindings; 43 44#if PLATFORM(ANDROID) 45JavaInstanceJobject::JavaInstanceJobject(jobject instance, bool requireAnnotation) 46#else 47JavaInstanceJobject::JavaInstanceJobject(jobject instance) 48#endif 49 : m_instance(new JobjectWrapper(instance)) 50#if PLATFORM(ANDROID) 51 , m_requireAnnotation(requireAnnotation) 52#endif 53{ 54} 55 56#define NUM_LOCAL_REFS 64 57 58void JavaInstanceJobject::begin() 59{ 60 getJNIEnv()->PushLocalFrame(NUM_LOCAL_REFS); 61} 62 63void JavaInstanceJobject::end() 64{ 65 getJNIEnv()->PopLocalFrame(0); 66} 67 68JavaClass* JavaInstanceJobject::getClass() const 69{ 70 if (!m_class) 71#if PLATFORM(ANDROID) 72 m_class = adoptPtr(new JavaClassJobject(javaInstance(), m_requireAnnotation)); 73#else 74 m_class = adoptPtr(new JavaClassJobject(javaInstance())); 75#endif 76 return m_class.get(); 77} 78 79// ANDROID 80JavaValue JavaInstanceJobject::invokeMethod(const JavaMethod* method, JavaValue* args, bool& didRaiseUncaughtException) 81{ 82 didRaiseUncaughtException = false; 83// END ANDROID 84 85 ASSERT(getClass()->methodsNamed(method->name().utf8().data()).find(method) != notFound); 86 unsigned int numParams = method->numParameters(); 87 OwnArrayPtr<jvalue> jvalueArgs = adoptArrayPtr(new jvalue[numParams]); 88 for (unsigned int i = 0; i < numParams; ++i) 89 jvalueArgs[i] = javaValueToJvalue(args[i]); 90 jvalue result = callJNIMethod(javaInstance(), method->returnType(), method->name().utf8().data(), method->signature(), jvalueArgs.get()); 91 92// ANDROID 93 JNIEnv* env = getJNIEnv(); 94 if (env->ExceptionCheck() != JNI_FALSE) { 95 env->ExceptionClear(); 96 didRaiseUncaughtException = true; 97 return JavaValue(); 98 } 99 100 return jvalueToJavaValue(result, method->returnType(), m_requireAnnotation); 101// END ANDROID 102} 103 104static void appendClassName(StringBuilder& builder, const char* className) 105{ 106 char* c = fastStrDup(className); 107 char* result = c; 108 while (*c) { 109 if (*c == '.') 110 *c = '/'; 111 c++; 112 } 113 builder.append(result); 114 fastFree(result); 115} 116 117JavaValue JavaInstanceJobject::getField(const JavaField* field) 118{ 119 ASSERT(getClass()->fieldNamed(field->name().utf8().data()) == field); 120 121 StringBuilder signature; 122 signature.append(signatureFromJavaType(field->type())); 123 if (field->type() == JavaTypeObject || field->type() == JavaTypeString) { 124 appendClassName(signature, field->typeClassName()); 125 signature.append(';'); 126 } 127#if PLATFORM(ANDROID) 128 return jvalueToJavaValue(getJNIField(javaInstance(), field->type(), field->name().utf8().data(), signature.toString().utf8().data()), field->type(), m_requireAnnotation); 129#else 130 return jvalueToJavaValue(getJNIField(javaInstance(), field->type(), field->name().utf8().data(), signature.toString().utf8().data()), field->type()); 131#endif 132} 133 134#endif // ENABLE(JAVA_BRIDGE) 135