scoped_java_ref.h revision c5cede9ae108bb15f6b7a8aea21c7e1fefa2834c
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef BASE_ANDROID_SCOPED_JAVA_REF_H_ 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define BASE_ANDROID_SCOPED_JAVA_REF_H_ 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <jni.h> 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <stddef.h> 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/base_export.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/basictypes.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace base { 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace android { 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 17c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch// Creates a new local reference frame, in which at least a given number of 18c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch// local references can be created. Note that local references already created 19c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch// in previous local frames are still valid in the current local frame. 20c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdochclass BASE_EXPORT ScopedJavaLocalFrame { 21c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch public: 22c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch explicit ScopedJavaLocalFrame(JNIEnv* env); 23c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch ScopedJavaLocalFrame(JNIEnv* env, int capacity); 24c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch ~ScopedJavaLocalFrame(); 25c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 26c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch private: 27c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // This class is only good for use on the thread it was created on so 28c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // it's safe to cache the non-threadsafe JNIEnv* inside this object. 29c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch JNIEnv* env_; 30c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 31c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch DISALLOW_COPY_AND_ASSIGN(ScopedJavaLocalFrame); 32c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch}; 33c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Forward declare the generic java reference template class. 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> class JavaRef; 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Template specialization of JavaRef, which acts as the base class for all 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// other JavaRef<> template types. This allows you to e.g. pass 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// ScopedJavaLocalRef<jstring> into a function taking const JavaRef<jobject>& 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<> 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class BASE_EXPORT JavaRef<jobject> { 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) jobject obj() const { return obj_; } 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool is_null() const { return obj_ == NULL; } 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Initializes a NULL reference. 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JavaRef(); 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Takes ownership of the |obj| reference passed; requires it to be a local 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // reference type. 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JavaRef(JNIEnv* env, jobject obj); 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~JavaRef(); 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The following are implementation detail convenience methods, for 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // use by the sub-classes. 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JNIEnv* SetNewLocalRef(JNIEnv* env, jobject obj); 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SetNewGlobalRef(JNIEnv* env, jobject obj); 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void ResetLocalRef(JNIEnv* env); 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void ResetGlobalRef(); 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) jobject ReleaseInternal(); 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) jobject obj_; 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(JavaRef); 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Generic base class for ScopedJavaLocalRef and ScopedJavaGlobalRef. Useful 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// for allowing functions to accept a reference without having to mandate 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// whether it is a local or global type. 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class JavaRef : public JavaRef<jobject> { 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) T obj() const { return static_cast<T>(JavaRef<jobject>::obj()); } 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JavaRef() {} 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~JavaRef() {} 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JavaRef(JNIEnv* env, T obj) : JavaRef<jobject>(env, obj) {} 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(JavaRef); 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Holds a local reference to a Java object. The local reference is scoped 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// to the lifetime of this object. 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Instances of this class may hold onto any JNIEnv passed into it until 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// destroyed. Therefore, since a JNIEnv is only suitable for use on a single 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// thread, objects of this class must be created, used, and destroyed, on a 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// single thread. 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Therefore, this class should only be used as a stack-based object and from a 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// single thread. If you wish to have the reference outlive the current 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// callstack (e.g. as a class member) or you wish to pass it across threads, 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// use a ScopedJavaGlobalRef instead. 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ScopedJavaLocalRef : public JavaRef<T> { 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ScopedJavaLocalRef() : env_(NULL) {} 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Non-explicit copy constructor, to allow ScopedJavaLocalRef to be returned 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // by value as this is the normal usage pattern. 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ScopedJavaLocalRef(const ScopedJavaLocalRef<T>& other) 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : env_(other.env_) { 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->SetNewLocalRef(env_, other.obj()); 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) explicit ScopedJavaLocalRef(const U& other) 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : env_(NULL) { 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(other); 1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Assumes that |obj| is a local reference to a Java object and takes 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // ownership of this local reference. 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ScopedJavaLocalRef(JNIEnv* env, T obj) : JavaRef<T>(env, obj), env_(env) {} 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~ScopedJavaLocalRef() { 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(); 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Overloaded assignment operator defined for consistency with the implicit 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // copy constructor. 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void operator=(const ScopedJavaLocalRef<T>& other) { 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(other); 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset() { 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->ResetLocalRef(env_); 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset(const ScopedJavaLocalRef<U>& other) { 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We can copy over env_ here as |other| instance must be from the same 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // thread as |this| local ref. (See class comment for multi-threading 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // limitations, and alternatives). 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(other.env_, other.obj()); 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset(const U& other) { 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // If |env_| was not yet set (is still NULL) it will be attached to the 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // current thread in SetNewLocalRef(). 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(env_, other.obj()); 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset(JNIEnv* env, U obj) { 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) implicit_cast<T>(obj); // Ensure U is assignable to T 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) env_ = this->SetNewLocalRef(env, obj); 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Releases the local reference to the caller. The caller *must* delete the 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // local reference when it is done with it. 1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) T Release() { 1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return static_cast<T>(this->ReleaseInternal()); 1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // This class is only good for use on the thread it was created on so 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // it's safe to cache the non-threadsafe JNIEnv* inside this object. 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) JNIEnv* env_; 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Holds a global reference to a Java object. The global reference is scoped 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// to the lifetime of this object. This class does not hold onto any JNIEnv* 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// passed to it, hence it is safe to use across threads (within the constraints 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// imposed by the underlying Java object that it references). 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ScopedJavaGlobalRef : public JavaRef<T> { 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ScopedJavaGlobalRef() {} 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) explicit ScopedJavaGlobalRef(const ScopedJavaGlobalRef<T>& other) { 1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(other); 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) explicit ScopedJavaGlobalRef(const U& other) { 1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(other); 1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~ScopedJavaGlobalRef() { 1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(); 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset() { 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->ResetGlobalRef(); 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset(const U& other) { 1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->Reset(NULL, other.obj()); 1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) template<typename U> 2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Reset(JNIEnv* env, U obj) { 2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) implicit_cast<T>(obj); // Ensure U is assignable to T 2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this->SetNewGlobalRef(env, obj); 2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Releases the global reference to the caller. The caller *must* delete the 2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // global reference when it is done with it. 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) T Release() { 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return static_cast<T>(this->ReleaseInternal()); 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace android 2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace base 2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif // BASE_ANDROID_SCOPED_JAVA_REF_H_ 216