blob: eb79e0ee7a9b4a38fe628992f8fba8cb7e3ef5ef [file] [log] [blame]
Elliott Hughes2faa5f12012-01-30 14:42:07 -08001/*
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 */
Brian Carlstrom3320cf42011-10-04 14:58:28 -070016
17#include "compiled_method.h"
18
19namespace art {
20
21CompiledMethod::CompiledMethod(InstructionSet instruction_set,
Brian Carlstrome7d856b2012-01-11 18:10:55 -080022 const std::vector<uint16_t>& short_code,
Brian Carlstrom3320cf42011-10-04 14:58:28 -070023 const size_t frame_size_in_bytes,
Brian Carlstrom3320cf42011-10-04 14:58:28 -070024 const uint32_t core_spill_mask,
25 const uint32_t fp_spill_mask,
Brian Carlstrome7d856b2012-01-11 18:10:55 -080026 const std::vector<uint32_t>& mapping_table,
27 const std::vector<uint16_t>& vmap_table)
Ian Rogers169c9a72011-11-13 20:13:17 -080028 : instruction_set_(instruction_set), frame_size_in_bytes_(frame_size_in_bytes),
29 core_spill_mask_(core_spill_mask), fp_spill_mask_(fp_spill_mask) {
Brian Carlstrom3320cf42011-10-04 14:58:28 -070030 CHECK_NE(short_code.size(), 0U);
Brian Carlstrom0dd7dda2011-10-25 15:47:53 -070031 CHECK_GE(vmap_table.size(), 1U); // should always contain an entry for LR
Brian Carlstrome7d856b2012-01-11 18:10:55 -080032 CHECK_LE(vmap_table.size(), (1U << 16) - 1); // length must fit in 2^16-1
Brian Carlstrom3320cf42011-10-04 14:58:28 -070033
34 size_t code_byte_count = short_code.size() * sizeof(short_code[0]);
35 std::vector<uint8_t> byte_code(code_byte_count);
36 memcpy(&byte_code[0], &short_code[0], code_byte_count);
37
38 std::vector<uint32_t> length_prefixed_mapping_table;
39 length_prefixed_mapping_table.push_back(mapping_table.size());
40 length_prefixed_mapping_table.insert(length_prefixed_mapping_table.end(),
41 mapping_table.begin(),
42 mapping_table.end());
43 DCHECK_EQ(mapping_table.size() + 1, length_prefixed_mapping_table.size());
44
45 std::vector<uint16_t> length_prefixed_vmap_table;
46 length_prefixed_vmap_table.push_back(vmap_table.size());
47 length_prefixed_vmap_table.insert(length_prefixed_vmap_table.end(),
48 vmap_table.begin(),
49 vmap_table.end());
50 DCHECK_EQ(vmap_table.size() + 1, length_prefixed_vmap_table.size());
Brian Carlstrom0dd7dda2011-10-25 15:47:53 -070051 DCHECK_EQ(vmap_table.size(), length_prefixed_vmap_table[0]);
Brian Carlstrom3320cf42011-10-04 14:58:28 -070052
Brian Carlstrom3320cf42011-10-04 14:58:28 -070053 code_ = byte_code;
Brian Carlstrom3320cf42011-10-04 14:58:28 -070054 mapping_table_ = length_prefixed_mapping_table;
55 vmap_table_ = length_prefixed_vmap_table;
Brian Carlstrom0dd7dda2011-10-25 15:47:53 -070056
57 DCHECK_EQ(vmap_table_[0], static_cast<uint32_t>(__builtin_popcount(core_spill_mask) + __builtin_popcount(fp_spill_mask)));
Brian Carlstrom3320cf42011-10-04 14:58:28 -070058}
59
Brian Carlstrome7d856b2012-01-11 18:10:55 -080060void CompiledMethod::SetGcMap(const std::vector<uint8_t>& gc_map) {
61 CHECK_NE(gc_map.size(), 0U);
62
63 // Should only be used with CompiledMethods created with oatCompileMethod
64 CHECK_NE(mapping_table_.size(), 0U);
65 CHECK_NE(vmap_table_.size(), 0U);
66
Brian Carlstrom75412882012-01-18 01:26:54 -080067 gc_map_ = gc_map;
Brian Carlstrome7d856b2012-01-11 18:10:55 -080068}
69
Brian Carlstrom3320cf42011-10-04 14:58:28 -070070CompiledMethod::CompiledMethod(InstructionSet instruction_set,
Brian Carlstrome7d856b2012-01-11 18:10:55 -080071 const std::vector<uint8_t>& code,
Brian Carlstrom3320cf42011-10-04 14:58:28 -070072 const size_t frame_size_in_bytes,
Brian Carlstrom3320cf42011-10-04 14:58:28 -070073 const uint32_t core_spill_mask,
Ian Rogers169c9a72011-11-13 20:13:17 -080074 const uint32_t fp_spill_mask)
75 : instruction_set_(instruction_set), code_(code), frame_size_in_bytes_(frame_size_in_bytes),
76 core_spill_mask_(core_spill_mask), fp_spill_mask_(fp_spill_mask) {
Brian Carlstrom3320cf42011-10-04 14:58:28 -070077 CHECK_NE(code.size(), 0U);
Brian Carlstrom3320cf42011-10-04 14:58:28 -070078}
79
80CompiledMethod::~CompiledMethod() {}
81
82InstructionSet CompiledMethod::GetInstructionSet() const {
83 return instruction_set_;
84}
85
86const std::vector<uint8_t>& CompiledMethod::GetCode() const {
87 return code_;
88}
89
90size_t CompiledMethod::GetFrameSizeInBytes() const {
91 return frame_size_in_bytes_;
92}
93
Brian Carlstrom3320cf42011-10-04 14:58:28 -070094uint32_t CompiledMethod::GetCoreSpillMask() const {
95 return core_spill_mask_;
96}
97
98uint32_t CompiledMethod::GetFpSpillMask() const {
99 return fp_spill_mask_;
100}
101
102const std::vector<uint32_t>& CompiledMethod::GetMappingTable() const {
103 return mapping_table_;
104}
105
106const std::vector<uint16_t>& CompiledMethod::GetVmapTable() const {
107 return vmap_table_;
108}
109
Brian Carlstrome7d856b2012-01-11 18:10:55 -0800110const std::vector<uint8_t>& CompiledMethod::GetGcMap() const {
111 return gc_map_;
112}
113
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700114uint32_t CompiledMethod::AlignCode(uint32_t offset) const {
115 return AlignCode(offset, instruction_set_);
116}
117
118uint32_t CompiledMethod::AlignCode(uint32_t offset, InstructionSet instruction_set) {
119 switch (instruction_set) {
120 case kArm:
121 case kThumb2:
122 return RoundUp(offset, kArmAlignment);
123 case kX86:
124 return offset;
125 default:
Elliott Hughesba8eee12012-01-24 20:25:24 -0800126 LOG(FATAL) << "Unknown InstructionSet: " << static_cast<int>(instruction_set);
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700127 return 0;
128 }
129}
130
131size_t CompiledMethod::CodeDelta() const {
132 switch (instruction_set_) {
133 case kArm:
134 case kX86:
135 return 0;
136 case kThumb2: {
137 // +1 to set the low-order bit so a BLX will switch to Thumb mode
138 return 1;
139 }
140 default:
Elliott Hughesba8eee12012-01-24 20:25:24 -0800141 LOG(FATAL) << "Unknown InstructionSet: " << static_cast<int>(instruction_set_);
Brian Carlstrom413f9e02012-01-09 22:24:30 -0800142 return 0;
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700143 }
144}
145
146const void* CompiledMethod::CodePointer(const void* code_pointer,
147 InstructionSet instruction_set) {
148 switch (instruction_set) {
149 case kArm:
150 case kX86:
151 return code_pointer;
152 case kThumb2: {
153 uintptr_t address = reinterpret_cast<uintptr_t>(code_pointer);
154 // Set the low-order bit so a BLX will switch to Thumb mode
155 address |= 0x1;
156 return reinterpret_cast<const void*>(address);
157 }
158 default:
Elliott Hughesba8eee12012-01-24 20:25:24 -0800159 LOG(FATAL) << "Unknown InstructionSet: " << static_cast<int>(instruction_set);
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700160 return NULL;
161 }
162}
163
Brian Carlstrom3320cf42011-10-04 14:58:28 -0700164CompiledInvokeStub::CompiledInvokeStub(std::vector<uint8_t>& code) {
165 CHECK_NE(code.size(), 0U);
166 code_ = code;
167}
168
169CompiledInvokeStub::~CompiledInvokeStub() {}
170
171const std::vector<uint8_t>& CompiledInvokeStub::GetCode() const {
172 return code_;
173}
174
175} // namespace art