compiled_method.cc revision 169c9a7f46776b235d0a37d5e0ff27682deffe06
13320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom// Copyright 2011 Google Inc. All Rights Reserved. 23320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 33320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom#include "compiled_method.h" 43320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 53320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromnamespace art { 63320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 73320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromCompiledMethod::CompiledMethod(InstructionSet instruction_set, 83320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<short>& short_code, 93320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom const size_t frame_size_in_bytes, 103320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom const uint32_t core_spill_mask, 113320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom const uint32_t fp_spill_mask, 123320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<uint32_t>& mapping_table, 13169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers std::vector<uint16_t>& vmap_table) 14169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers : instruction_set_(instruction_set), frame_size_in_bytes_(frame_size_in_bytes), 15169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers core_spill_mask_(core_spill_mask), fp_spill_mask_(fp_spill_mask) { 163320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom CHECK_NE(short_code.size(), 0U); 170dd7ddaa36a2cf37490dc166ebc21818364130a7Brian Carlstrom CHECK_GE(vmap_table.size(), 1U); // should always contain an entry for LR 183320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 193320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom size_t code_byte_count = short_code.size() * sizeof(short_code[0]); 203320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<uint8_t> byte_code(code_byte_count); 213320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom memcpy(&byte_code[0], &short_code[0], code_byte_count); 223320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 233320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<uint32_t> length_prefixed_mapping_table; 243320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom length_prefixed_mapping_table.push_back(mapping_table.size()); 253320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom length_prefixed_mapping_table.insert(length_prefixed_mapping_table.end(), 263320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom mapping_table.begin(), 273320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom mapping_table.end()); 283320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom DCHECK_EQ(mapping_table.size() + 1, length_prefixed_mapping_table.size()); 293320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 303320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<uint16_t> length_prefixed_vmap_table; 313320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom length_prefixed_vmap_table.push_back(vmap_table.size()); 323320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom length_prefixed_vmap_table.insert(length_prefixed_vmap_table.end(), 333320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom vmap_table.begin(), 343320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom vmap_table.end()); 353320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom DCHECK_EQ(vmap_table.size() + 1, length_prefixed_vmap_table.size()); 360dd7ddaa36a2cf37490dc166ebc21818364130a7Brian Carlstrom DCHECK_EQ(vmap_table.size(), length_prefixed_vmap_table[0]); 373320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 383320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom code_ = byte_code; 393320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom mapping_table_ = length_prefixed_mapping_table; 403320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom vmap_table_ = length_prefixed_vmap_table; 410dd7ddaa36a2cf37490dc166ebc21818364130a7Brian Carlstrom 420dd7ddaa36a2cf37490dc166ebc21818364130a7Brian Carlstrom DCHECK_EQ(vmap_table_[0], static_cast<uint32_t>(__builtin_popcount(core_spill_mask) + __builtin_popcount(fp_spill_mask))); 433320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 443320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 453320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromCompiledMethod::CompiledMethod(InstructionSet instruction_set, 463320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom std::vector<uint8_t>& code, 473320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom const size_t frame_size_in_bytes, 483320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom const uint32_t core_spill_mask, 49169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers const uint32_t fp_spill_mask) 50169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers : instruction_set_(instruction_set), code_(code), frame_size_in_bytes_(frame_size_in_bytes), 51169c9a7f46776b235d0a37d5e0ff27682deffe06Ian Rogers core_spill_mask_(core_spill_mask), fp_spill_mask_(fp_spill_mask) { 523320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom CHECK_NE(code.size(), 0U); 533320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 543320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 553320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromCompiledMethod::~CompiledMethod() {} 563320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 573320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromInstructionSet CompiledMethod::GetInstructionSet() const { 583320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return instruction_set_; 593320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 603320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 613320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromconst std::vector<uint8_t>& CompiledMethod::GetCode() const { 623320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return code_; 633320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 643320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 653320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromsize_t CompiledMethod::GetFrameSizeInBytes() const { 663320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return frame_size_in_bytes_; 673320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 683320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 693320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromuint32_t CompiledMethod::GetCoreSpillMask() const { 703320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return core_spill_mask_; 713320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 723320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 733320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromuint32_t CompiledMethod::GetFpSpillMask() const { 743320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return fp_spill_mask_; 753320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 763320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 773320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromconst std::vector<uint32_t>& CompiledMethod::GetMappingTable() const { 783320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return mapping_table_; 793320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 803320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 813320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromconst std::vector<uint16_t>& CompiledMethod::GetVmapTable() const { 823320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return vmap_table_; 833320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 843320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 853320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromuint32_t CompiledMethod::AlignCode(uint32_t offset) const { 863320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return AlignCode(offset, instruction_set_); 873320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 883320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 893320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromuint32_t CompiledMethod::AlignCode(uint32_t offset, InstructionSet instruction_set) { 903320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom switch (instruction_set) { 913320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kArm: 923320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kThumb2: 933320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return RoundUp(offset, kArmAlignment); 943320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kX86: 953320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return offset; 963320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom default: 973320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom LOG(FATAL) << "Unknown InstructionSet " << (int) instruction_set; 983320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return 0; 993320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom } 1003320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 1013320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1023320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromsize_t CompiledMethod::CodeDelta() const { 1033320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom switch (instruction_set_) { 1043320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kArm: 1053320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kX86: 1063320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return 0; 1073320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kThumb2: { 1083320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom // +1 to set the low-order bit so a BLX will switch to Thumb mode 1093320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return 1; 1103320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom } 1113320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom default: 1123320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom LOG(FATAL) << "Unknown InstructionSet " << (int) instruction_set_; 1133320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return NULL; 1143320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom } 1153320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 1163320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1173320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromconst void* CompiledMethod::CodePointer(const void* code_pointer, 1183320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom InstructionSet instruction_set) { 1193320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom switch (instruction_set) { 1203320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kArm: 1213320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kX86: 1223320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return code_pointer; 1233320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom case kThumb2: { 1243320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom uintptr_t address = reinterpret_cast<uintptr_t>(code_pointer); 1253320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom // Set the low-order bit so a BLX will switch to Thumb mode 1263320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom address |= 0x1; 1273320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return reinterpret_cast<const void*>(address); 1283320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom } 1293320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom default: 1303320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom LOG(FATAL) << "Unknown InstructionSet " << (int) instruction_set; 1313320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return NULL; 1323320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom } 1333320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 1343320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1353320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromCompiledInvokeStub::CompiledInvokeStub(std::vector<uint8_t>& code) { 1363320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom CHECK_NE(code.size(), 0U); 1373320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom code_ = code; 1383320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 1393320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1403320cf46afd082398aa401b246e6f301cebdf64dBrian CarlstromCompiledInvokeStub::~CompiledInvokeStub() {} 1413320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1423320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstromconst std::vector<uint8_t>& CompiledInvokeStub::GetCode() const { 1433320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom return code_; 1443320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} 1453320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom 1463320cf46afd082398aa401b246e6f301cebdf64dBrian Carlstrom} // namespace art 147