1 /* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ART_RUNTIME_STACK_INDIRECT_REFERENCE_TABLE_H_ 18 #define ART_RUNTIME_STACK_INDIRECT_REFERENCE_TABLE_H_ 19 20 #include "base/logging.h" 21 #include "base/macros.h" 22 23 namespace art { 24 namespace mirror { 25 class Object; 26 } 27 class Thread; 28 29 // Stack allocated indirect reference table. It can allocated within 30 // the bridge frame between managed and native code backed by stack 31 // storage or manually allocated by SirtRef to hold one reference. 32 class StackIndirectReferenceTable { 33 public: StackIndirectReferenceTable(mirror::Object * object)34 explicit StackIndirectReferenceTable(mirror::Object* object) : 35 number_of_references_(1), link_(NULL) { 36 references_[0] = object; 37 } 38 ~StackIndirectReferenceTable()39 ~StackIndirectReferenceTable() {} 40 41 // Number of references contained within this SIRT NumberOfReferences()42 size_t NumberOfReferences() const { 43 return number_of_references_; 44 } 45 46 // Link to previous SIRT or NULL GetLink()47 StackIndirectReferenceTable* GetLink() const { 48 return link_; 49 } 50 SetLink(StackIndirectReferenceTable * sirt)51 void SetLink(StackIndirectReferenceTable* sirt) { 52 DCHECK_NE(this, sirt); 53 link_ = sirt; 54 } 55 GetReference(size_t i)56 mirror::Object* GetReference(size_t i) const { 57 DCHECK_LT(i, number_of_references_); 58 return references_[i]; 59 } 60 SetReference(size_t i,mirror::Object * object)61 void SetReference(size_t i, mirror::Object* object) { 62 DCHECK_LT(i, number_of_references_); 63 references_[i] = object; 64 } 65 Contains(mirror::Object ** sirt_entry)66 bool Contains(mirror::Object** sirt_entry) const { 67 // A SIRT should always contain something. One created by the 68 // jni_compiler should have a jobject/jclass as a native method is 69 // passed in a this pointer or a class 70 DCHECK_GT(number_of_references_, 0U); 71 return ((&references_[0] <= sirt_entry) 72 && (sirt_entry <= (&references_[number_of_references_ - 1]))); 73 } 74 75 // Offset of length within SIRT, used by generated code NumberOfReferencesOffset()76 static size_t NumberOfReferencesOffset() { 77 return OFFSETOF_MEMBER(StackIndirectReferenceTable, number_of_references_); 78 } 79 80 // Offset of link within SIRT, used by generated code LinkOffset()81 static size_t LinkOffset() { 82 return OFFSETOF_MEMBER(StackIndirectReferenceTable, link_); 83 } 84 85 private: StackIndirectReferenceTable()86 StackIndirectReferenceTable() {} 87 88 size_t number_of_references_; 89 StackIndirectReferenceTable* link_; 90 91 // number_of_references_ are available if this is allocated and filled in by jni_compiler. 92 mirror::Object* references_[1]; 93 94 DISALLOW_COPY_AND_ASSIGN(StackIndirectReferenceTable); 95 }; 96 97 } // namespace art 98 99 #endif // ART_RUNTIME_STACK_INDIRECT_REFERENCE_TABLE_H_ 100